S
Supabase2mo ago
Dmitri

Failing auth in Edge Function

Calling auth.getClaims() returns null despite request containing valid JWT which I've checked using JWK. Calling auth.getUser(), returns a user object fine too. I am using supabase/supabase-js@2.57.4 on both client and server. Any thoughts on what may be causing it? Also, please let me know what additional info I can provide that may help
7 Replies
garyaustin
garyaustin2mo ago
How are you calling getClaims in the edge function? How are you getting a user JWT to the edge function and then to your supabase client? Are you calling getClaims(token) similar to getUser shown here https://supabase.com/docs/guides/functions/auth#fetching-the-user
Dmitri
DmitriOP2mo ago
I am using Hono middleware and the JWT is on Authorization header. See code below
export const withSupabase = createMiddleware<{
Variables: {
supabase: SupabaseClient
}
}>(async (c, next) => {
const Authorization = c.req.header('Authorization') ?? Deno.env.get('SUPABASE_ANON_KEY')!

const supabase = createClient(Deno.env.get('SUPABASE_URL')!, Deno.env.get('SUPABASE_ANON_KEY')!, {
global: { headers: { Authorization: Authorization } }
})

c.set('supabase', supabase)

await next()
})

export const withClaims = createMiddleware<{
Variables: {
supabase: SupabaseClient
claims: JwtPayload
}
}>(async (c, next) => {
const { data, error } = await c.get('supabase').auth.getClaims()

if (error) {
throw error
}

console.log('claims', data)
console.log('error', error)

invariant(data?.claims, 'Claims are required')

c.set('claims', data.claims)

await next()
})
export const withSupabase = createMiddleware<{
Variables: {
supabase: SupabaseClient
}
}>(async (c, next) => {
const Authorization = c.req.header('Authorization') ?? Deno.env.get('SUPABASE_ANON_KEY')!

const supabase = createClient(Deno.env.get('SUPABASE_URL')!, Deno.env.get('SUPABASE_ANON_KEY')!, {
global: { headers: { Authorization: Authorization } }
})

c.set('supabase', supabase)

await next()
})

export const withClaims = createMiddleware<{
Variables: {
supabase: SupabaseClient
claims: JwtPayload
}
}>(async (c, next) => {
const { data, error } = await c.get('supabase').auth.getClaims()

if (error) {
throw error
}

console.log('claims', data)
console.log('error', error)

invariant(data?.claims, 'Claims are required')

c.set('claims', data.claims)

await next()
})
I just updated the call to getClaims() with
const jwt = c.req.header('Authorization')?.replace('Bearer ', '')
const { data, error } = await c.get('supabase').auth.getClaims(jwt)
const jwt = c.req.header('Authorization')?.replace('Bearer ', '')
const { data, error } = await c.get('supabase').auth.getClaims(jwt)
And it looks like it's working now. Code in the docs does shows const { data, error } = await supabase.auth.getClaims(). Why the difference?
garyaustin
garyaustin2mo ago
Not sure what doc. Edge functions don't have a users session so you have to supply the jwt from the authorization header. A normal client where you used a signin method would have a session and not need the jwt.
Dmitri
DmitriOP2mo ago
JavaScript: Get user claims from verified JWT | Supabase Docs
Supabase API reference for JavaScript: Get user claims from verified JWT
Dmitri
DmitriOP2mo ago
Anyway, I appreciate your help getting things working again ❤️
garyaustin
garyaustin2mo ago
It has it:
No description
garyaustin
garyaustin2mo ago
A createClient in an edge function will not have a session as you did not signin the user. You passed it a jwt.

Did you find this page helpful?