UNPKG

@lokalise/api-contracts

Version:
103 lines 3.83 kB
import { z } from 'zod/v4'; import { SUCCESSFUL_HTTP_STATUS_CODES } from "../HttpStatusCodes.js"; import { ContractNoBody } from "./constants.js"; import { isAnyOfResponses, isBlobResponse, isNoBodyResponse, isSseResponse, isTextResponse, } from "./contractResponse.js"; export const defineApiContract = (contract) => contract; export const mapApiContractToPath = (routeConfig) => { if (!routeConfig.requestPathParamsSchema) { return routeConfig.pathResolver(undefined); } const resolverParams = Object.keys(routeConfig.requestPathParamsSchema.shape).reduce((acc, key) => { acc[key] = `:${key}`; return acc; }, {}); return routeConfig.pathResolver(resolverParams); }; export const describeApiContract = (routeConfig) => { return `${routeConfig.method.toUpperCase()} ${mapApiContractToPath(routeConfig)}`; }; export const getSseSchemaByEventName = (routeConfig) => { const result = {}; for (const value of Object.values(routeConfig.responsesByStatusCode)) { if (isSseResponse(value)) { Object.assign(result, value.schemaByEventName); } else if (isAnyOfResponses(value)) { for (const response of value.responses) { if (isSseResponse(response)) { Object.assign(result, response.schemaByEventName); } } } } return Object.keys(result).length > 0 ? result : null; }; export const hasAnySuccessSseResponse = (apiContract) => { for (const code of [...SUCCESSFUL_HTTP_STATUS_CODES, '2xx', 'default']) { const value = apiContract.responsesByStatusCode[code]; if (!value) { continue; } if (isSseResponse(value)) { return true; } else if (isAnyOfResponses(value)) { for (const response of value.responses) { if (isSseResponse(response)) { return true; } } } } return false; }; /** @deprecated No known consumers — will be removed in a future release. */ // biome-ignore lint/complexity/noExcessiveCognitiveComplexity: it is acceptable export const getSuccessResponseSchema = (routeConfig) => { const schemas = []; let hasDirectNonJsonEntry = false; for (const code of SUCCESSFUL_HTTP_STATUS_CODES) { const value = routeConfig.responsesByStatusCode[code]; if (!value) { continue; } if (isAnyOfResponses(value)) { for (const response of value.responses) { if (!isSseResponse(response) && !isTextResponse(response) && !isBlobResponse(response)) { schemas.push(response); } } } else if (value === ContractNoBody || isNoBodyResponse(value) || isSseResponse(value) || isTextResponse(value) || isBlobResponse(value)) { hasDirectNonJsonEntry = true; } else { schemas.push(value); } } if (schemas.length > 1) { return z.union(schemas); } const firstSchema = schemas.at(0); if (firstSchema) { return firstSchema; } return hasDirectNonJsonEntry ? z.never() : null; }; /** @deprecated No known consumers — will be removed in a future release. */ export const getIsEmptyResponseExpected = (routeConfig) => { let isEmptyResponseExpected = true; for (const code of SUCCESSFUL_HTTP_STATUS_CODES) { const value = routeConfig.responsesByStatusCode[code]; if (value && value !== ContractNoBody && !isNoBodyResponse(value)) { isEmptyResponseExpected = false; break; } } return isEmptyResponseExpected; }; //# sourceMappingURL=defineApiContract.js.map