From 4f82fc4be34cdf7a19b35852ea0db21592317ed7 Mon Sep 17 00:00:00 2001 From: Morten Date: Tue, 9 Sep 2025 21:34:06 +0000 Subject: [PATCH] Api improvements --- packages/server/src/api/api.ts | 12 +++++-- .../src/api/endpoints/endpoints.documents.ts | 31 ++++++++++++++++- ...ndpoints.search.ts => endpoints.stream.ts} | 33 ++++--------------- 3 files changed, 46 insertions(+), 30 deletions(-) rename packages/server/src/api/endpoints/{endpoints.search.ts => endpoints.stream.ts} (66%) diff --git a/packages/server/src/api/api.ts b/packages/server/src/api/api.ts index a4075c3..89326b2 100644 --- a/packages/server/src/api/api.ts +++ b/packages/server/src/api/api.ts @@ -5,7 +5,7 @@ import { jsonSchemaTransform, serializerCompiler, validatorCompiler } from 'fast import type { Services } from '@morten-olsen/fluxcurrent-core/utils/services.ts'; import { FastifySSEPlugin } from 'fastify-sse-v2'; -import { searchEndpoint } from './endpoints/endpoints.search.ts'; +import { streamEndpoint } from './endpoints/endpoints.stream.ts'; import { documentsEndpoint } from './endpoints/endpoints.documents.ts'; type CreateApiOptions = { @@ -20,10 +20,16 @@ const createApi = async (options: CreateApiOptions) => { app.register(fastifySwagger, { openapi: { info: { - title: 'SampleApi', + title: 'FluxCurrent', description: 'Sample backend service', version: '1.0.0', }, + tags: [ + { + name: 'documents', + description: 'Documents', + }, + ], servers: [], }, transform: jsonSchemaTransform, @@ -35,7 +41,7 @@ const createApi = async (options: CreateApiOptions) => { await app.register(FastifySSEPlugin); - await app.register(searchEndpoint, { services: options.services, prefix: '/search' }); + await app.register(streamEndpoint, { services: options.services, prefix: '/streaming' }); await app.register(documentsEndpoint, { services: options.services, prefix: '/documents' }); await app.ready(); diff --git a/packages/server/src/api/endpoints/endpoints.documents.ts b/packages/server/src/api/endpoints/endpoints.documents.ts index f402471..d6bd245 100644 --- a/packages/server/src/api/endpoints/endpoints.documents.ts +++ b/packages/server/src/api/endpoints/endpoints.documents.ts @@ -2,13 +2,20 @@ import type { FastifyPluginAsyncZod } from 'fastify-type-provider-zod'; import { z } from 'zod/v4'; import type { Services } from '@morten-olsen/fluxcurrent-core/utils/services.ts'; import { DocumentsService } from '@morten-olsen/fluxcurrent-core/services/documents/documents.ts'; -import { documentUpsertSchema } from '@morten-olsen/fluxcurrent-core/services/documents/documents.schemas.ts'; +import { + documentSearchResultSchema, + documentUpsertSchema, +} from '@morten-olsen/fluxcurrent-core/services/documents/documents.schemas.ts'; +import { parseDSL } from '@morten-olsen/fluxcurrent-core/services/documents/documents.dsl.ts'; const documentsEndpoint: FastifyPluginAsyncZod<{ services: Services }> = async (fastify, { services }) => { fastify.route({ method: 'POST', url: '', schema: { + operationId: 'post.documents', + summary: 'Upsert a document', + tags: ['documents'], body: z.object({ document: documentUpsertSchema, }), @@ -19,6 +26,28 @@ const documentsEndpoint: FastifyPluginAsyncZod<{ services: Services }> = async ( res.send(documents); }, }); + + fastify.route({ + method: 'GET', + url: '', + schema: { + operationId: 'get.documents', + summary: 'Find documents', + tags: ['documents'], + querystring: z.object({ + query: z.string().optional(), + }), + response: { + 200: documentSearchResultSchema, + }, + }, + handler: async (req, res) => { + const query = req.query.query ? parseDSL(req.query.query) : {}; + const documentsService = services.get(DocumentsService); + const documents = await documentsService.search(query); + res.send(documents); + }, + }); }; export { documentsEndpoint }; diff --git a/packages/server/src/api/endpoints/endpoints.search.ts b/packages/server/src/api/endpoints/endpoints.stream.ts similarity index 66% rename from packages/server/src/api/endpoints/endpoints.search.ts rename to packages/server/src/api/endpoints/endpoints.stream.ts index ae8a52c..1666c30 100644 --- a/packages/server/src/api/endpoints/endpoints.search.ts +++ b/packages/server/src/api/endpoints/endpoints.stream.ts @@ -3,36 +3,17 @@ import { z } from 'zod/v4'; import type { Services } from '@morten-olsen/fluxcurrent-core/utils/services.ts'; import { parseDSL } from '@morten-olsen/fluxcurrent-core/services/documents/documents.dsl.ts'; import { DocumentsService } from '@morten-olsen/fluxcurrent-core/services/documents/documents.ts'; -import { - documentSearchResultSchema, - type DocumentUpsertEvent, -} from '@morten-olsen/fluxcurrent-core/services/documents/documents.schemas.ts'; +import { type DocumentUpsertEvent } from '@morten-olsen/fluxcurrent-core/services/documents/documents.schemas.ts'; import { filterDocument } from '@morten-olsen/fluxcurrent-core/services/documents/documents.filter.ts'; -const searchEndpoint: FastifyPluginAsyncZod<{ services: Services }> = async (fastify, { services }) => { - fastify.route({ - method: 'POST', - url: '', - schema: { - body: z.object({ - query: z.string().optional(), - }), - response: { - 200: documentSearchResultSchema, - }, - }, - handler: async (req, res) => { - const query = req.body.query ? parseDSL(req.body.query) : {}; - const documentsService = services.get(DocumentsService); - const documents = await documentsService.search(query); - res.send(documents); - }, - }); - +const streamEndpoint: FastifyPluginAsyncZod<{ services: Services }> = async (fastify, { services }) => { fastify.route({ method: 'GET', - url: '/stream', + url: '/documents', schema: { + operationId: 'get.stream.documents', + summary: 'Stream documents matching a query', + tags: ['streams', 'documents'], querystring: z.object({ query: z.string().optional(), }), @@ -59,4 +40,4 @@ const searchEndpoint: FastifyPluginAsyncZod<{ services: Services }> = async (fas }); }; -export { searchEndpoint }; +export { streamEndpoint };