Compare commits

...

2 Commits

Author SHA1 Message Date
pluja
3afa824c18 Release 202505311149 2025-05-31 11:49:38 +00:00
pluja
9a68112e24 Release 202505311113 2025-05-31 11:13:24 +00:00
4 changed files with 89 additions and 3 deletions

View File

@@ -24,7 +24,7 @@ export const apiServiceActions = {
.optional(),
url: zodUrlOptionalProtocol.optional(),
}),
handler: async (input) => {
handler: async (input, context) => {
if (!input.id && !input.slug && !input.url) {
throw new ActionError({
code: 'BAD_REQUEST',
@@ -122,7 +122,7 @@ export const apiServiceActions = {
(url) => url + (service.referral ?? '')
),
tosUrls: service.tosUrls,
kycnotmeUrl: `https://kycnot.me/service/${service.slug}`,
kycnotmeUrl: new URL(`/service/${service.slug}`, context.url).href,
}
},
}),

View File

@@ -114,7 +114,13 @@ export class ErrorBanners {
return result
} catch (error) {
this.handler(uiMessage)(error)
return fallback as F
return fallback as F extends never[]
? T extends [infer _First, ...infer _Rest]
? []
: T extends unknown[]
? T[number][]
: F
: F
}
}

View File

@@ -0,0 +1,50 @@
import type { Misc } from 'ts-toolbelt'
export async function makeAdminApiCallInfo<T extends Misc.JSON.Object>({
method,
path,
input,
baseUrl,
}: {
method: 'POST' | 'QUERY'
path: `/${string}`
input: T
baseUrl: URL | string
}) {
const fullPath = new URL(`/api/v1${path}`, baseUrl).href
const fetchProsmise = fetch(fullPath, {
method,
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(input),
}).then((res) => {
try {
return res.json() as Promise<Misc.JSON.Value>
} catch (errJson: unknown) {
console.error(errJson)
try {
return res.text()
} catch (errText: unknown) {
console.error(errText)
return ''
}
}
})
let output: Misc.JSON.Value = ''
try {
output = await fetchProsmise
} catch (err: unknown) {
console.error(err)
output = err instanceof Error ? err.message : String(err)
}
return {
method,
path,
fullPath,
input,
output,
}
}

View File

@@ -2,6 +2,7 @@
import { Icon } from 'astro-icon/components'
import { Markdown } from 'astro-remote'
import { actions, isInputError } from 'astro:actions'
import { Code } from 'astro:components'
import { orderBy } from 'lodash-es'
import BadgeSmall from '../../../../components/BadgeSmall.astro'
@@ -33,6 +34,7 @@ import {
verificationStepStatuses,
} from '../../../../constants/verificationStepStatus'
import BaseLayout from '../../../../layouts/BaseLayout.astro'
import { makeAdminApiCallInfo } from '../../../../lib/makeAdminApiCallInfo'
import { pluralize } from '../../../../lib/pluralize'
import { prisma } from '../../../../lib/prisma'
@@ -181,6 +183,20 @@ const [service, categories, attributes] = await Astro.locals.banners.tryMany([
])
if (!service) return Astro.rewrite('/404')
const apiCalls = await Astro.locals.banners.try(
'Error fetching api calls',
() =>
Promise.all([
makeAdminApiCallInfo({
method: 'QUERY',
path: '/service/get',
input: { slug: service.slug },
baseUrl: Astro.url,
}),
]),
[]
)
---
<BaseLayout pageTitle={`Edit Service: ${service.name}`}>
@@ -1100,5 +1116,19 @@ if (!service) return Astro.rewrite('/404')
</form>
</FormSubSection>
</FormSection>
<FormSection title="API">
{
apiCalls.map((call) => (
<FormSubSection title={`${call.method} ${call.path}`}>
<p class="text-day-400 text-sm">Input:</p>
<Code code={JSON.stringify(call.input, null, 2)} lang="json" class="rounded-lg p-4 text-xs" />
<p class="text-day-400 text-sm">Output:</p>
<Code code={JSON.stringify(call.output, null, 2)} lang="json" class="rounded-lg p-4 text-xs" />
</FormSubSection>
))
}
</FormSection>
</div>
</BaseLayout>