@scalar/express-api-reference 0.9.3 → 0.9.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +8 -0
- package/dist/apiReference.js +18 -14
- package/dist/apiReference.test.js +83 -0
- package/dist/index.js +1 -5
- package/dist/types.js +1 -1
- package/package.json +7 -13
- package/dist/apiReference.js.map +0 -7
- package/dist/index.js.map +0 -7
- package/dist/types.js.map +0 -7
package/CHANGELOG.md
CHANGED
package/dist/apiReference.js
CHANGED
|
@@ -1,17 +1,21 @@
|
|
|
1
|
-
import { getHtmlDocument } from
|
|
1
|
+
import { getHtmlDocument } from '@scalar/core/libs/html-rendering';
|
|
2
|
+
/**
|
|
3
|
+
* The default configuration for the API Reference.
|
|
4
|
+
*/
|
|
2
5
|
const DEFAULT_CONFIGURATION = {
|
|
3
|
-
|
|
6
|
+
_integration: 'express',
|
|
4
7
|
};
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
8
|
+
/**
|
|
9
|
+
* The route handler to render the Scalar API Reference.
|
|
10
|
+
*/
|
|
11
|
+
export function apiReference(givenConfiguration) {
|
|
12
|
+
// Merge the defaults
|
|
13
|
+
const configuration = {
|
|
14
|
+
...DEFAULT_CONFIGURATION,
|
|
15
|
+
...givenConfiguration,
|
|
16
|
+
};
|
|
17
|
+
// Respond with the HTML document
|
|
18
|
+
return (_, res) => {
|
|
19
|
+
res.type('text/html').send(getHtmlDocument(configuration));
|
|
20
|
+
};
|
|
13
21
|
}
|
|
14
|
-
export {
|
|
15
|
-
apiReference
|
|
16
|
-
};
|
|
17
|
-
//# sourceMappingURL=apiReference.js.map
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
import express from 'express';
|
|
2
|
+
import request from 'supertest';
|
|
3
|
+
import { describe, expect, it } from 'vitest';
|
|
4
|
+
import { apiReference } from './apiReference.js';
|
|
5
|
+
describe('apiReference', () => {
|
|
6
|
+
it('should handle missing spec content gracefully', async () => {
|
|
7
|
+
const app = express();
|
|
8
|
+
const options = {
|
|
9
|
+
cdn: 'https://cdn.example.com',
|
|
10
|
+
};
|
|
11
|
+
app.use(apiReference(options));
|
|
12
|
+
const response = await request(app).get('/');
|
|
13
|
+
expect(response.status).toBe(200);
|
|
14
|
+
expect(response.type).toBe('text/html');
|
|
15
|
+
expect(response.text).toContain('<title>Scalar API Reference</title>');
|
|
16
|
+
expect(response.text).toContain('https://cdn.example.com');
|
|
17
|
+
// Ensure no undefined content
|
|
18
|
+
expect(response.text).not.toContain('undefined');
|
|
19
|
+
});
|
|
20
|
+
it('should use default CDN when no CDN is provided', async () => {
|
|
21
|
+
const app = express();
|
|
22
|
+
const options = {
|
|
23
|
+
content: { info: { title: 'Test API' } },
|
|
24
|
+
};
|
|
25
|
+
app.use(apiReference(options));
|
|
26
|
+
const response = await request(app).get('/');
|
|
27
|
+
expect(response.status).toBe(200);
|
|
28
|
+
expect(response.type).toBe('text/html');
|
|
29
|
+
expect(response.text).toContain('<title>Scalar API Reference</title>');
|
|
30
|
+
expect(response.text).toContain('https://cdn.jsdelivr.net/npm/@scalar/api-reference');
|
|
31
|
+
});
|
|
32
|
+
it('does not have the content twice', async () => {
|
|
33
|
+
const app = express();
|
|
34
|
+
app.use(apiReference({ content: { info: { title: 'Test API' } } }));
|
|
35
|
+
const response = await request(app).get('/');
|
|
36
|
+
expect(response.status).toBe(200);
|
|
37
|
+
// Check the title is present
|
|
38
|
+
expect(response.text).toContain('Test API');
|
|
39
|
+
// Check that the title is only present once
|
|
40
|
+
const text = response.text;
|
|
41
|
+
const titleCount = (text.match(/Test API/g) || []).length;
|
|
42
|
+
expect(titleCount).toBe(1);
|
|
43
|
+
});
|
|
44
|
+
it('keeps the URL in the configuration', async () => {
|
|
45
|
+
const app = express();
|
|
46
|
+
app.use(apiReference({
|
|
47
|
+
url: 'https://registry.scalar.com/@scalar/apis/galaxy?format=json',
|
|
48
|
+
}));
|
|
49
|
+
const response = await request(app).get('/');
|
|
50
|
+
// Check the URL is present
|
|
51
|
+
expect(response.text).toContain('https://registry.scalar.com/@scalar/apis/galaxy?format=json');
|
|
52
|
+
});
|
|
53
|
+
it('includes _integration: "express" in configuration', async () => {
|
|
54
|
+
const app = express();
|
|
55
|
+
app.use(apiReference({}));
|
|
56
|
+
const response = await request(app).get('/');
|
|
57
|
+
expect(response.text).toContain('"_integration": "express"');
|
|
58
|
+
});
|
|
59
|
+
it('handles content as function', async () => {
|
|
60
|
+
const app = express();
|
|
61
|
+
const contentFn = () => ({ info: { title: 'Function API' } });
|
|
62
|
+
app.use(apiReference({ content: contentFn }));
|
|
63
|
+
const response = await request(app).get('/');
|
|
64
|
+
expect(response.text).toContain('Function API');
|
|
65
|
+
});
|
|
66
|
+
it('removes spec.content when spec.url is provided', async () => {
|
|
67
|
+
const app = express();
|
|
68
|
+
app.use(apiReference({
|
|
69
|
+
url: 'https://example.com/api.json',
|
|
70
|
+
content: { info: { title: 'Test API' } },
|
|
71
|
+
}));
|
|
72
|
+
const response = await request(app).get('/');
|
|
73
|
+
expect(response.text).toContain('https://example.com/api.json');
|
|
74
|
+
expect(response.text).not.toContain('Test API');
|
|
75
|
+
});
|
|
76
|
+
it('sets correct content type and status', async () => {
|
|
77
|
+
const app = express();
|
|
78
|
+
app.use(apiReference({}));
|
|
79
|
+
const response = await request(app).get('/');
|
|
80
|
+
expect(response.status).toBe(200);
|
|
81
|
+
expect(response.type).toBe('text/html');
|
|
82
|
+
});
|
|
83
|
+
});
|
package/dist/index.js
CHANGED
package/dist/types.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
|
|
1
|
+
export {};
|
package/package.json
CHANGED
|
@@ -10,7 +10,7 @@
|
|
|
10
10
|
"url": "git+https://github.com/scalar/scalar.git",
|
|
11
11
|
"directory": "integrations/express"
|
|
12
12
|
},
|
|
13
|
-
"version": "0.9.
|
|
13
|
+
"version": "0.9.5",
|
|
14
14
|
"engines": {
|
|
15
15
|
"node": ">=22"
|
|
16
16
|
},
|
|
@@ -45,7 +45,7 @@
|
|
|
45
45
|
"documentation": "https://scalar.com/products/api-references/integrations/express"
|
|
46
46
|
},
|
|
47
47
|
"dependencies": {
|
|
48
|
-
"@scalar/core": "0.4.
|
|
48
|
+
"@scalar/core": "0.4.5"
|
|
49
49
|
},
|
|
50
50
|
"devDependencies": {
|
|
51
51
|
"@types/express": "5.0.3",
|
|
@@ -54,22 +54,16 @@
|
|
|
54
54
|
"express": "5.1.0",
|
|
55
55
|
"supertest": "7.2.2",
|
|
56
56
|
"swagger-jsdoc": "^6.2.8",
|
|
57
|
-
"vite": "
|
|
58
|
-
"vitest": "4.0
|
|
59
|
-
"@scalar/build-tooling": "0.5.0"
|
|
57
|
+
"vite": "8.0.0",
|
|
58
|
+
"vitest": "4.1.0"
|
|
60
59
|
},
|
|
61
60
|
"scripts": {
|
|
62
|
-
"build": "
|
|
61
|
+
"build": "tsc -p tsconfig.build.json && tsc-alias -p tsconfig.build.json",
|
|
63
62
|
"build:playground": "cd playground && pnpm build",
|
|
64
|
-
"dev": "
|
|
63
|
+
"dev": "tsx watch playground/index.ts",
|
|
65
64
|
"docker:build": "docker build --build-arg BASE_IMAGE=scalar-base -t express-api-reference -f Dockerfile .",
|
|
66
65
|
"docker:run": "docker run -p 5055:5055 express-api-reference",
|
|
67
|
-
"format": "scalar-format",
|
|
68
|
-
"format:check": "scalar-format-check",
|
|
69
|
-
"lint:check": "scalar-lint-check",
|
|
70
|
-
"lint:fix": "scalar-lint-fix",
|
|
71
66
|
"test": "vitest",
|
|
72
|
-
"types:
|
|
73
|
-
"types:check": "scalar-types-check"
|
|
67
|
+
"types:check": "tsc --noEmit"
|
|
74
68
|
}
|
|
75
69
|
}
|
package/dist/apiReference.js.map
DELETED
|
@@ -1,7 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"version": 3,
|
|
3
|
-
"sources": ["../src/apiReference.ts"],
|
|
4
|
-
"sourcesContent": ["import { getHtmlDocument } from '@scalar/core/libs/html-rendering'\nimport type { RequestHandler } from 'express'\n\nimport type { ApiReferenceConfiguration } from './types'\n\n/**\n * The default configuration for the API Reference.\n */\nconst DEFAULT_CONFIGURATION: Partial<ApiReferenceConfiguration> = {\n _integration: 'express',\n}\n\n/**\n * The route handler to render the Scalar API Reference.\n */\nexport function apiReference(givenConfiguration: Partial<ApiReferenceConfiguration>): RequestHandler<never, string> {\n // Merge the defaults\n const configuration = {\n ...DEFAULT_CONFIGURATION,\n ...givenConfiguration,\n }\n\n // Respond with the HTML document\n return (_, res) => {\n res.type('text/html').send(getHtmlDocument(configuration))\n }\n}\n"],
|
|
5
|
-
"mappings": "AAAA,SAAS,uBAAuB;AAQhC,MAAM,wBAA4D;AAAA,EAChE,cAAc;AAChB;AAKO,SAAS,aAAa,oBAAuF;AAElH,QAAM,gBAAgB;AAAA,IACpB,GAAG;AAAA,IACH,GAAG;AAAA,EACL;AAGA,SAAO,CAAC,GAAG,QAAQ;AACjB,QAAI,KAAK,WAAW,EAAE,KAAK,gBAAgB,aAAa,CAAC;AAAA,EAC3D;AACF;",
|
|
6
|
-
"names": []
|
|
7
|
-
}
|
package/dist/index.js.map
DELETED