pocketbase / js-sdk

PocketBase JavaScript SDK

Home Page:https://www.npmjs.com/package/pocketbase

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

How do I use the authStore asynchronously? Undefined `isValid` when using with Nuxt 3

fayazara opened this issue · comments

I have written a middleware in Nuxt 3 as below.

import { usePocketBaseClient } from '@/composables/pocketBaseClient'
export default defineNuxtRouteMiddleware(() => {
  const pocketbase = usePocketBaseClient();
  const isUserLoggedIn = pocketbase?.authStore.isValid;
  console.log('isUserLoggedIn', isUserLoggedIn)
  if (!isUserLoggedIn) {
    return navigateTo('/auth/login')
  }
})

The pocketbase client is initiated correctly, but the isValid is always false, I can access the user data when I use it with a page. Is there a way to wait till I get the pocketbase user to check if they're valid in this middleware?

I'm not sure that I understand what do you mean by asynchronously.

What is usePocketBaseClient()?
Where and when the above code is being executed (eg. is it in the browser, server or both)?

If the above is for SSR, you can check some of the examples in https://github.com/pocketbase/js-sdk#ssr-integration.

I'll close the issue for now as I don't think there is an actionable item or something related to the JS SDK, but feel free to provide more details about your use case and I'll have a look.

@ganigeorgiev Sorry about not being clear.

The usePocketbaseClient() is a nuxt composable running in the client

import PocketBase from 'pocketbase';
const pb = new PocketBase('http://127.0.0.1:8090');

export const usePocketBaseClient = () => {
  return pb as PocketBase;
}

Let me try to reproduce this and share a link.

I don't think your issue is JS SDK related.

By default pb.authStore uses LocalStorage and all its operations are synchronous.

I'm not very familiar with Nuxt, but are you even sure that the pocketbase variable in your example is being set to the JS SDK instance? If Yes, then why do you need the ? optional access?

Yes, but I think i found out the issue, its running on the server, not on client
Screenshot 04-11 at 17

Basically I was trying to create a nuxt module for pocketbase similar to nuxt/supabase https://supabase.nuxtjs.org/

Let me see if there's any other way to do this.

But I don't think you need a dedicated module, especially if your code is executed on the client-side (aka. browser).

Also why do the JS SDK instance actually needs to be composable in the first place?

In your example you can directly return export default pb, and then import it in your code without the need of usePocketBaseClient (eg. import pb from "/src/yourclient.js").

Having a single global PocketBase SDK instance is safe when executed in the browser.
For an SSR example see https://github.com/pocketbase/js-sdk#ssr-integration.

Yes, I just created a composable so I could reuse it in other pages and components etc.

I've updated my auth middleware, which seems to be working now.

import { usePocketBaseClient } from '@/composables/pocketBaseClient'
export default defineNuxtRouteMiddleware(async () => {
  if (process.server) return;
  const pocketbase = usePocketBaseClient();
  const isUserLoggedIn = await pocketbase?.authStore.isValid;
  if (!isUserLoggedIn) {
    return navigateTo('/auth/login')
  }
})

Might not be the correct way since the page is shown first then redirected back to the login page. Just testing what works best, will figure out a better way to handle this since, or just go the SSR way you mentioned in the docs link above.

Thank you for he help!

Here's the test project I made to test out pocketbase with the composables I mentioned above.

https://github.com/fayazara/pocketbase-nuxt

As mentioned earlier in #256 (comment), returning a function in https://github.com/fayazara/pocketbase-nuxt/blob/main/composables/pocketBaseClient.ts#L5C4-L5C4 is not really necessary as it doesn't really do anything.

You can directly return export default pb and then you can directly import it in your client-side code like:

import pb from "/path/to/client.js"

...

const records = await pb.collection("example").getList(1, 20)