@@ -1,99 +0,0 @@
1−import { describe, test, expect } from 'vitest';
2−import OpenAPISchemaValidator from 'openapi-schema-validator';
3−
4−// Import PureScript compiled modules
5−const TestOperators = await import('../output/Test.Operators/index.js');
6−const YogaRoute = await import('../output/Yoga.HTTP.API.Route/index.js');
7−const YogaAuth = await import('../output/Yoga.HTTP.API.Route.Auth/index.js');
8−const YogaJSON = await import('../output/Yoga.JSON/index.js');
9−
10−const validator = new OpenAPISchemaValidator({ version: 3 });
11−
12−// Helper to build and validate OpenAPI spec
13−function buildAndValidateSpec(apiType, config) {
14− const spec = YogaRoute.buildOpenAPISpec(apiType)(config)();
15− const json = YogaJSON.writeJSON(spec);
16− const parsed = JSON.parse(json);
17− const result = validator.validate(parsed);
18− return { spec: parsed, errors: result.errors };
19−}
20−
21−describe('OpenAPI Schema Validation', () => {
22− test('BearerToken API generates valid OpenAPI 3.0 spec', () => {
23− // Note: We can't easily construct the type in JS, so we'll validate the JSON directly
24− // by building a spec from PureScript and checking it
25− const json = `{"openapi":"3.0.0","info":{"title":"Auth API","version":"1.0.0"},"paths":{"/protected":{"get":{"tags":[],"security":[{"bearerAuth":[]}],"responses":{"200":{"headers":{},"description":"Successful response","content":{"application/json":{"schema":{"type":"object","required":["message"],"properties":{"message":{"type":"string"}}}}}}},"parameters":[],"operationId":"getProtected"}}},"components":{"securitySchemes":{"bearerAuth":{"type":"http","scheme":"bearer","bearerFormat":"JWT"}}}}`;
26− const parsed = JSON.parse(json);
27− const result = validator.validate(parsed);
28−
29− expect(result.errors).toEqual([]);
30− expect(parsed.components.securitySchemes.bearerAuth).toEqual({
31− type: 'http',
32− scheme: 'bearer',
33− bearerFormat: 'JWT'
34− });
35− });
36−
37− test('BasicAuth API generates valid OpenAPI 3.0 spec', () => {
38− const json = `{"openapi":"3.0.0","info":{"title":"Auth API","version":"1.0.0"},"paths":{"/protected":{"get":{"tags":[],"security":[{"basicAuth":[]}],"responses":{"200":{"headers":{},"description":"Successful response","content":{"application/json":{"schema":{"type":"object","required":["message"],"properties":{"message":{"type":"string"}}}}}}},"parameters":[],"operationId":"getProtected"}}},"components":{"securitySchemes":{"basicAuth":{"type":"http","scheme":"basic"}}}}`;
39− const parsed = JSON.parse(json);
40− const result = validator.validate(parsed);
41−
42− expect(result.errors).toEqual([]);
43− expect(parsed.components.securitySchemes.basicAuth).toEqual({
44− type: 'http',
45− scheme: 'basic'
46− });
47− });
48−
49− test('ApiKey API generates valid OpenAPI 3.0 spec', () => {
50− const json = `{"openapi":"3.0.0","info":{"title":"Auth API","version":"1.0.0"},"paths":{"/protected":{"get":{"tags":[],"security":[{"apiKeyApiKey":[]}],"responses":{"200":{"headers":{},"description":"Successful response","content":{"application/json":{"schema":{"type":"object","required":["message"],"properties":{"message":{"type":"string"}}}}}}},"parameters":[],"operationId":"getProtected"}}},"components":{"securitySchemes":{"apiKeyApiKey":{"type":"apiKey","in":"header","name":"apiKey"}}}}`;
51− const parsed = JSON.parse(json);
52− const result = validator.validate(parsed);
53−
54− expect(result.errors).toEqual([]);
55− expect(parsed.components.securitySchemes.apiKeyApiKey).toEqual({
56− type: 'apiKey',
57− in: 'header',
58− name: 'apiKey'
59− });
60− });
61−
62− test('DigestAuth API generates valid OpenAPI 3.0 spec', () => {
63− const json = `{"openapi":"3.0.0","info":{"title":"Auth API","version":"1.0.0"},"paths":{"/protected":{"get":{"tags":[],"security":[{"digestAuth":[]}],"responses":{"200":{"headers":{},"description":"Successful response","content":{"application/json":{"schema":{"type":"object","required":["message"],"properties":{"message":{"type":"string"}}}}}}},"parameters":[],"operationId":"getProtected"}}},"components":{"securitySchemes":{"digestAuth":{"type":"http","scheme":"digest"}}}}`;
64− const parsed = JSON.parse(json);
65− const result = validator.validate(parsed);
66−
67− expect(result.errors).toEqual([]);
68− expect(parsed.components.securitySchemes.digestAuth).toEqual({
69− type: 'http',
70− scheme: 'digest'
71− });
72− });
73−
74− test('Multi-auth API generates valid OpenAPI 3.0 spec with multiple security schemes', () => {
75− const json = `{"openapi":"3.0.0","info":{"title":"Auth API","version":"1.0.0"},"paths":{"/bearer":{"get":{"tags":[],"security":[{"bearerAuth":[]}],"responses":{"200":{"headers":{},"description":"Successful response","content":{"application/json":{"schema":{"type":"object","required":["message"],"properties":{"message":{"type":"string"}}}}}}},"parameters":[],"operationId":"bearerEndpoint"}},"/basic":{"get":{"tags":[],"security":[{"basicAuth":[]}],"responses":{"200":{"headers":{},"description":"Successful response","content":{"application/json":{"schema":{"type":"object","required":["message"],"properties":{"message":{"type":"string"}}}}}}},"parameters":[],"operationId":"basicEndpoint"}},"/apikey":{"get":{"tags":[],"security":[{"xApiKeyApiKey":[]}],"responses":{"200":{"headers":{},"description":"Successful response","content":{"application/json":{"schema":{"type":"object","required":["message"],"properties":{"message":{"type":"string"}}}}}}},"parameters":[],"operationId":"apiKeyEndpoint"}}},"components":{"securitySchemes":{"bearerAuth":{"type":"http","scheme":"bearer","bearerFormat":"JWT"},"basicAuth":{"type":"http","scheme":"basic"},"xApiKeyApiKey":{"type":"apiKey","in":"header","name":"xApiKey"}}}}`;
76− const parsed = JSON.parse(json);
77− const result = validator.validate(parsed);
78−
79− expect(result.errors).toEqual([]);
80− expect(Object.keys(parsed.components.securitySchemes)).toContain('bearerAuth');
81− expect(Object.keys(parsed.components.securitySchemes)).toContain('basicAuth');
82− expect(Object.keys(parsed.components.securitySchemes)).toContain('xApiKeyApiKey');
83− });
84−
85− test('Security schemes are not in parameters array', () => {
86− const json = `{"openapi":"3.0.0","info":{"title":"Auth API","version":"1.0.0"},"paths":{"/protected":{"get":{"tags":[],"security":[{"bearerAuth":[]}],"responses":{"200":{"headers":{},"description":"Successful response","content":{"application/json":{"schema":{"type":"object","required":["message"],"properties":{"message":{"type":"string"}}}}}}},"parameters":[],"operationId":"getProtected"}}},"components":{"securitySchemes":{"bearerAuth":{"type":"http","scheme":"bearer","bearerFormat":"JWT"}}}}`;
87− const parsed = JSON.parse(json);
88− const result = validator.validate(parsed);
89−
90− expect(result.errors).toEqual([]);
91−
92− // Check that authorization is not in parameters
93− const getOperation = parsed.paths['/protected'].get;
94− expect(getOperation.parameters).toEqual([]);
95−
96− // But IS in security
97− expect(getOperation.security).toEqual([{ bearerAuth: [] }]);
98− });
99−});