mirror of
https://github.com/supabase/supabase.git
synced 2026-10-05 09:25:06 +03:00
Add coveralls integration (#35424)
* update gh action, update vitest config * debug * debug cov * idk try something different * test2 * test3 * add base path * rm debug * add apiAuthenticate tests * supabaseClient tests * apiWrappers tests * add apiHelpers tests * add configcat tests * add formatSql tests * add github tests * add cloudprovider utils tests * add helpers tests * fix typeerr * add missing readonly err * fix typeerrrs * fix type errors in apiWrapper tests * fix apiHelpers test * add packages/ui tests * add coveralls flags * try coveralls parallel config * fix coveralls parallel config --------- Co-authored-by: Joshen Lim <joshenlimek@gmail.com>
This commit is contained in:
1 parent
31aad403de
commit
6e91494b16
19 files changed
+1108
-15
No files matched your search
@@ -0,0 +1,318 @@
|
||||
import { describe, it, expect, vi, beforeEach } from 'vitest'
|
||||
import { apiAuthenticate } from './apiAuthenticate'
|
||||
import { readOnly } from './supabaseClient'
|
||||
|
||||
const mocks = vi.hoisted(() => {
|
||||
return {
|
||||
getAuthUser: vi.fn().mockResolvedValue({
|
||||
user: {
|
||||
id: 'test-gotrue-id',
|
||||
email: 'test@example.com',
|
||||
},
|
||||
error: null,
|
||||
}),
|
||||
getIdentity: vi.fn().mockReturnValue({
|
||||
identity: null,
|
||||
error: null,
|
||||
}),
|
||||
getAuth0Id: vi.fn(),
|
||||
}
|
||||
})
|
||||
|
||||
// Mock dependencies
|
||||
vi.mock('./supabaseClient', () => ({
|
||||
readOnly: {
|
||||
from: vi.fn(),
|
||||
},
|
||||
}))
|
||||
|
||||
vi.mock('lib/gotrue', () => ({
|
||||
getAuthUser: mocks.getAuthUser,
|
||||
getIdentity: mocks.getIdentity,
|
||||
getAuth0Id: mocks.getAuth0Id,
|
||||
}))
|
||||
|
||||
describe('apiAuthenticate', () => {
|
||||
const mockReq = {
|
||||
headers: {
|
||||
authorization: 'Bearer test-token',
|
||||
},
|
||||
query: {},
|
||||
} as any
|
||||
|
||||
const mockRes = {} as any
|
||||
|
||||
beforeEach(() => {
|
||||
vi.clearAllMocks()
|
||||
mocks.getAuthUser.mockResolvedValue({
|
||||
user: {
|
||||
id: 'test-gotrue-id',
|
||||
email: 'test@example.com',
|
||||
},
|
||||
error: null,
|
||||
})
|
||||
mocks.getIdentity.mockReturnValue({
|
||||
identity: null,
|
||||
error: null,
|
||||
})
|
||||
})
|
||||
|
||||
it('should return error when request is not available', async () => {
|
||||
const result = await apiAuthenticate(null as any, mockRes)
|
||||
expect(result).toStrictEqual({ error: new Error('Request is not available') })
|
||||
})
|
||||
|
||||
it('should return error when response is not available', async () => {
|
||||
const result = await apiAuthenticate(mockReq, null as any)
|
||||
expect(result).toStrictEqual({ error: new Error('Response is not available') })
|
||||
})
|
||||
|
||||
it('should return error when authorization token is missing', async () => {
|
||||
const reqWithoutToken = { ...mockReq, headers: {} }
|
||||
const result = await apiAuthenticate(reqWithoutToken, mockRes)
|
||||
expect(result).toStrictEqual({ error: { name: 'Error', message: 'missing access token' } })
|
||||
})
|
||||
|
||||
it('should return error when auth user fetch fails', async () => {
|
||||
mocks.getAuthUser.mockResolvedValue({
|
||||
user: null,
|
||||
error: new Error('Auth failed'),
|
||||
})
|
||||
|
||||
const result = await apiAuthenticate(mockReq, mockRes)
|
||||
expect(result).toStrictEqual({ error: { name: 'Error', message: 'Auth failed' } })
|
||||
})
|
||||
|
||||
it('should handle identity error', async () => {
|
||||
mocks.getIdentity.mockReturnValue({
|
||||
identity: null,
|
||||
error: new Error('Identity error'),
|
||||
})
|
||||
|
||||
const result = await apiAuthenticate(mockReq, mockRes)
|
||||
expect(result).toStrictEqual({ error: { name: 'Error', message: 'Identity error' } })
|
||||
})
|
||||
|
||||
it('should set auth0 id when identity provider is present', async () => {
|
||||
mocks.getIdentity.mockReturnValue({
|
||||
identity: {
|
||||
provider: 'auth0',
|
||||
id: 'auth0-id',
|
||||
},
|
||||
error: null,
|
||||
})
|
||||
mocks.getAuth0Id.mockReturnValue('auth0-user-id')
|
||||
|
||||
// Mock user query
|
||||
vi.mocked(readOnly.from).mockReturnValue({
|
||||
select: vi.fn().mockReturnThis(),
|
||||
eq: vi.fn().mockReturnThis(),
|
||||
single: vi
|
||||
.fn()
|
||||
.mockResolvedValue({ data: { id: 'test-user-id', primary_email: 'test@example.com' } }),
|
||||
} as any)
|
||||
|
||||
const result = await apiAuthenticate(mockReq, mockRes)
|
||||
expect(result).toStrictEqual({
|
||||
id: 'test-user-id',
|
||||
primary_email: 'test@example.com',
|
||||
})
|
||||
expect(mocks.getAuth0Id).toHaveBeenCalledWith('auth0', 'auth0-id')
|
||||
})
|
||||
|
||||
it('should return user when user_id_supabase is present', async () => {
|
||||
// Mock identity to return auth0 provider
|
||||
mocks.getIdentity.mockReturnValue({
|
||||
identity: {
|
||||
provider: 'auth0',
|
||||
id: 'auth0-id',
|
||||
},
|
||||
error: null,
|
||||
})
|
||||
mocks.getAuth0Id.mockReturnValue('auth0-user-id')
|
||||
|
||||
// Mock user query to return a user with auth0_id
|
||||
vi.mocked(readOnly.from).mockReturnValue({
|
||||
select: vi.fn().mockReturnThis(),
|
||||
eq: vi.fn().mockReturnThis(),
|
||||
single: vi.fn().mockResolvedValue({
|
||||
data: {
|
||||
id: 'supabase-user-id',
|
||||
auth0_id: 'auth0-user-id',
|
||||
primary_email: 'test@example.com',
|
||||
},
|
||||
}),
|
||||
} as any)
|
||||
|
||||
const result = await apiAuthenticate(mockReq, mockRes)
|
||||
expect(result).toStrictEqual({
|
||||
id: 'supabase-user-id',
|
||||
auth0_id: 'auth0-user-id',
|
||||
primary_email: 'test@example.com',
|
||||
})
|
||||
})
|
||||
|
||||
it('should return error when user does not exist', async () => {
|
||||
vi.mocked(readOnly.from).mockReturnValue({
|
||||
select: vi.fn().mockReturnThis(),
|
||||
eq: vi.fn().mockReturnThis(),
|
||||
single: vi.fn().mockResolvedValue({ data: null }),
|
||||
} as any)
|
||||
|
||||
const result = await apiAuthenticate(mockReq, mockRes)
|
||||
expect(result).toStrictEqual({ error: new Error('The user does not exist') })
|
||||
})
|
||||
|
||||
it('should check organization permissions when orgSlug is provided', async () => {
|
||||
const reqWithOrg = {
|
||||
...mockReq,
|
||||
query: { slug: 'test-org' },
|
||||
}
|
||||
|
||||
// Mock user query
|
||||
vi.mocked(readOnly.from).mockReturnValueOnce({
|
||||
select: vi.fn().mockReturnThis(),
|
||||
eq: vi.fn().mockReturnThis(),
|
||||
single: vi
|
||||
.fn()
|
||||
.mockResolvedValue({ data: { id: 'test-user-id', primary_email: 'test@example.com' } }),
|
||||
} as any)
|
||||
|
||||
// Mock organization query
|
||||
vi.mocked(readOnly.from).mockReturnValueOnce({
|
||||
select: vi.fn().mockReturnThis(),
|
||||
match: vi.fn().mockReturnThis(),
|
||||
single: vi.fn().mockResolvedValue({ data: { id: 'org-id' } }),
|
||||
} as any)
|
||||
|
||||
// Mock member check
|
||||
vi.mocked(readOnly.from).mockReturnValueOnce({
|
||||
select: vi.fn().mockReturnThis(),
|
||||
match: vi.fn().mockReturnThis(),
|
||||
single: vi.fn().mockResolvedValue({ data: { id: 'member-id' }, status: 200 }),
|
||||
} as any)
|
||||
|
||||
const result = await apiAuthenticate(reqWithOrg, mockRes)
|
||||
expect(result).toStrictEqual({
|
||||
id: 'test-user-id',
|
||||
primary_email: 'test@example.com',
|
||||
})
|
||||
})
|
||||
|
||||
it('should return error when user lacks organization permissions', async () => {
|
||||
const reqWithOrg = {
|
||||
...mockReq,
|
||||
query: { slug: 'test-org' },
|
||||
}
|
||||
|
||||
// Mock user query
|
||||
vi.mocked(readOnly.from).mockReturnValueOnce({
|
||||
select: vi.fn().mockReturnThis(),
|
||||
eq: vi.fn().mockReturnThis(),
|
||||
single: vi
|
||||
.fn()
|
||||
.mockResolvedValue({ data: { id: 'test-user-id', primary_email: 'test@example.com' } }),
|
||||
} as any)
|
||||
|
||||
// Mock organization query
|
||||
vi.mocked(readOnly.from).mockReturnValueOnce({
|
||||
select: vi.fn().mockReturnThis(),
|
||||
match: vi.fn().mockReturnThis(),
|
||||
single: vi.fn().mockResolvedValue({ data: { id: 'org-id' } }),
|
||||
} as any)
|
||||
|
||||
// Mock member check failure
|
||||
vi.mocked(readOnly.from).mockReturnValueOnce({
|
||||
select: vi.fn().mockReturnThis(),
|
||||
match: vi.fn().mockReturnThis(),
|
||||
single: vi.fn().mockRejectedValue(new Error('Permission denied')),
|
||||
} as any)
|
||||
|
||||
const result = await apiAuthenticate(reqWithOrg, mockRes)
|
||||
expect(result).toStrictEqual({
|
||||
error: { name: 'Error', message: 'The user does not have permission' },
|
||||
})
|
||||
})
|
||||
|
||||
it('should handle unknown errors gracefully', async () => {
|
||||
mocks.getAuthUser.mockRejectedValue(new Error('Unexpected error'))
|
||||
|
||||
const result = await apiAuthenticate(mockReq, mockRes)
|
||||
expect(result).toStrictEqual({ error: { name: 'Error', message: 'Unexpected error' } })
|
||||
})
|
||||
|
||||
it('should get organization from project reference', async () => {
|
||||
const reqWithProject = {
|
||||
...mockReq,
|
||||
query: { ref: 'test-project' },
|
||||
}
|
||||
|
||||
// Mock user query
|
||||
vi.mocked(readOnly.from).mockReturnValueOnce({
|
||||
select: vi.fn().mockReturnThis(),
|
||||
eq: vi.fn().mockReturnThis(),
|
||||
single: vi
|
||||
.fn()
|
||||
.mockResolvedValue({ data: { id: 'test-user-id', primary_email: 'test@example.com' } }),
|
||||
} as any)
|
||||
|
||||
// Mock project query
|
||||
vi.mocked(readOnly.from).mockReturnValueOnce({
|
||||
select: vi.fn().mockReturnThis(),
|
||||
match: vi.fn().mockReturnThis(),
|
||||
single: vi.fn().mockResolvedValue({ data: { organization_id: 'org-id' } }),
|
||||
} as any)
|
||||
|
||||
// Mock member check
|
||||
vi.mocked(readOnly.from).mockReturnValueOnce({
|
||||
select: vi.fn().mockReturnThis(),
|
||||
match: vi.fn().mockReturnThis(),
|
||||
single: vi.fn().mockResolvedValue({ data: { id: 'member-id' }, status: 200 }),
|
||||
} as any)
|
||||
|
||||
const result = await apiAuthenticate(reqWithProject, mockRes)
|
||||
expect(result).toStrictEqual({
|
||||
id: 'test-user-id',
|
||||
primary_email: 'test@example.com',
|
||||
})
|
||||
})
|
||||
|
||||
it('should use organization_id from projectRef in member check', async () => {
|
||||
const reqWithProject = {
|
||||
...mockReq,
|
||||
query: { ref: 'project-xyz' },
|
||||
}
|
||||
|
||||
// Mock user query
|
||||
vi.mocked(readOnly.from).mockReturnValueOnce({
|
||||
select: vi.fn().mockReturnThis(),
|
||||
eq: vi.fn().mockReturnThis(),
|
||||
single: vi
|
||||
.fn()
|
||||
.mockResolvedValue({ data: { id: 'user-123', primary_email: 'user@example.com' } }),
|
||||
} as any)
|
||||
|
||||
// Mock project query to return a specific organization_id
|
||||
vi.mocked(readOnly.from).mockReturnValueOnce({
|
||||
select: vi.fn().mockReturnThis(),
|
||||
match: vi.fn().mockReturnThis(),
|
||||
single: vi.fn().mockResolvedValue({ data: { organization_id: 'org-abc' } }),
|
||||
} as any)
|
||||
|
||||
// Spy on the match function for the member check
|
||||
const matchSpy = vi.fn().mockReturnThis()
|
||||
vi.mocked(readOnly.from).mockReturnValueOnce({
|
||||
select: vi.fn().mockReturnThis(),
|
||||
match: matchSpy,
|
||||
single: vi.fn().mockResolvedValue({ data: { id: 'member-1' }, status: 200 }),
|
||||
} as any)
|
||||
|
||||
const result = await apiAuthenticate(reqWithProject, mockRes)
|
||||
expect(result).toStrictEqual({
|
||||
id: 'user-123',
|
||||
primary_email: 'user@example.com',
|
||||
})
|
||||
// Ensure the member check used the org id from the project lookup
|
||||
expect(matchSpy).toHaveBeenCalledWith({ organization_id: 'org-abc', user_id: 'user-123' })
|
||||
})
|
||||
})
|
||||
Reference in new issue
Block a user