Skip to content

Built for people who want to own their automations. Join the waitlist for an invite.

Package listing

@kody/supabase

src/management-request.ts

76 lines · 2.5 KB · TypeScript
import { managementAuth } from './setup.ts'
import { assertMutationAllowed, readMutationFlags } from './safety.ts'
import { managementRequest as sendManagement } from './client.ts'
import {
	isReadMethod,
	isRecord,
	normalizeHttpMethod,
	optionalBoolean,
	optionalString,
	requireString,
	type HttpMethod,
	type Json,
	type SupabaseAuthInput,
} from './types.ts'

export type ManagementRequestInput = SupabaseAuthInput & {
	path: string
	method?: HttpMethod
	query?: Record<string, string | number | boolean | undefined>
	body?: Json
	dryRun?: boolean
	confirm?: boolean
}

function normalizeManagementPath(path: string): string {
	const trimmed = path.startsWith('/') ? path : `/${path}`
	if (trimmed.startsWith('/v1/') || trimmed === '/v1') return trimmed
	return `/v1${trimmed}`
}

/**
 * Call the Supabase Management API (`https://api.supabase.com`).
 * Prefer named helpers. Mutating methods require `dryRun: true` or `confirm: true`.
 * @example
 * import managementRequest from 'kody:@kody/supabase/management-request'
 * const result = await managementRequest({ path: '/v1/projects' })
 */
export async function managementRequest(input: ManagementRequestInput) {
	const method = normalizeHttpMethod(input.method, 'GET')
	if (!isReadMethod(method)) {
		assertMutationAllowed(readMutationFlags(input), `management-request ${method}`)
	}
	return await sendManagement({
		auth: managementAuth(input),
		method,
		path: normalizeManagementPath(requireString(input.path, 'path')),
		query: input.query,
		body: input.body,
		dryRun: input.dryRun === true,
	})
}

/**
 * Call the Supabase Management API. Prefer named helpers.
 * Mutating methods require `dryRun: true` or `confirm: true`.
 * @example
 * import managementRequest from 'kody:@kody/supabase/management-request'
 * const result = await managementRequest({ path: '/projects' })
 */
export default async function managementRequestEntrypoint(
	params: Partial<ManagementRequestInput> & Record<string, unknown> = {},
) {
	return await managementRequest({
		account: optionalString(params.account, 'account'),
		secretName: optionalString(params.secretName, 'secretName'),
		patSecretName: optionalString(params.patSecretName, 'patSecretName'),
		path: requireString(params.path, 'path'),
		method: normalizeHttpMethod(params.method, 'GET'),
		query: isRecord(params.query)
			? (params.query as Record<string, string | number | boolean | undefined>)
			: undefined,
		body: params.body as Json | undefined,
		dryRun: optionalBoolean(params.dryRun, 'dryRun'),
		confirm: optionalBoolean(params.confirm, 'confirm'),
	})
}