Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
97 changes: 97 additions & 0 deletions src/generator/ApiParser.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
import { describe, expect, it } from "vitest";

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Keep Vitest tests out of the server build

Because this test is placed under src/generator, it matches tsconfig.server.json's src/generator/**/* include and will be emitted by npm run build:server into dist/server/generator/ApiParser.test.js with a test-only vitest import. In deploy or publish contexts that consume the server build artifact without devDependencies, this leaves a production artifact that can fail if loaded or packaged; move the test under an excluded test location or exclude *.test.ts from the server tsconfig.

Useful? React with 👍 / 👎.

import { ApiParser } from "./ApiParser";

describe("ApiParser", () => {
it("parses an OpenAPI 3.1 API-key search endpoint", async () => {
const spec = {
openapi: "3.1.0",
info: {
title: "Xquik API",
version: "1.0.0",
},
servers: [{ url: "https://xquik.com" }],
paths: {
"/api/v1/x/tweets/search": {
get: {
operationId: "searchTweets",
summary: "Search tweets",
description: "Search public posts with query, limit, and cursor parameters.",
parameters: [
{
name: "query",
in: "query",
required: true,
schema: { type: "string" },
description: "Search query.",
},
{
name: "limit",
in: "query",
required: false,
schema: { type: "integer" },
description: "Maximum number of results.",
},
{
name: "cursor",
in: "query",
required: false,
schema: { type: "string" },
description: "Pagination cursor.",
},
],
responses: {
"200": {
description: "Search results.",
},
},
},
},
},
components: {
securitySchemes: {
apiKey: {
type: "apiKey",
in: "header",
name: "x-api-key",
},
},
},
security: [{ apiKey: [] }],
};

const parsed = await new ApiParser().parseOpenApi(JSON.stringify(spec));

expect(parsed.name).toBe("Xquik API");
expect(parsed.baseUrl).toBe("https://xquik.com");
expect(parsed.authType).toBe("apiKey");
expect(parsed.endpoints).toHaveLength(1);
expect(parsed.endpoints?.[0]).toMatchObject({
path: "/api/v1/x/tweets/search",
method: "GET",
operationId: "searchTweets",
parameters: [
{
name: "query",
in: "query",
type: "string",
required: true,
description: "Search query.",
},
{
name: "limit",
in: "query",
type: "integer",
required: false,
description: "Maximum number of results.",
},
{
name: "cursor",
in: "query",
type: "string",
required: false,
description: "Pagination cursor.",
},
],
});
});
});