@furystack/rest-service 12.3.5 → 14.0.0
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 +55 -0
- package/README.md +47 -28
- package/esm/actions/get-current-user.spec.js +10 -6
- package/esm/actions/get-current-user.spec.js.map +1 -1
- package/esm/actions/index.d.ts +0 -1
- package/esm/actions/index.d.ts.map +1 -1
- package/esm/actions/index.js +0 -1
- package/esm/actions/index.js.map +1 -1
- package/esm/actions/is-authenticated.spec.js +10 -6
- package/esm/actions/is-authenticated.spec.js.map +1 -1
- package/esm/actions/logout-action.spec.js +11 -9
- package/esm/actions/logout-action.spec.js.map +1 -1
- package/esm/actions/logout.js +1 -1
- package/esm/actions/logout.js.map +1 -1
- package/esm/actions/password-login-action.js +1 -1
- package/esm/actions/password-login-action.js.map +1 -1
- package/esm/actions/password-login-action.spec.js +23 -28
- package/esm/actions/password-login-action.spec.js.map +1 -1
- package/esm/authenticate.js +1 -1
- package/esm/authenticate.js.map +1 -1
- package/esm/authenticate.spec.js +41 -33
- package/esm/authenticate.spec.js.map +1 -1
- package/esm/authorize.spec.js +34 -29
- package/esm/authorize.spec.js.map +1 -1
- package/esm/endpoint-generators/create-delete-endpoint.d.ts +6 -11
- package/esm/endpoint-generators/create-delete-endpoint.d.ts.map +1 -1
- package/esm/endpoint-generators/create-delete-endpoint.js +7 -11
- package/esm/endpoint-generators/create-delete-endpoint.js.map +1 -1
- package/esm/endpoint-generators/create-delete-endpoint.spec.js +14 -21
- package/esm/endpoint-generators/create-delete-endpoint.spec.js.map +1 -1
- package/esm/endpoint-generators/create-get-collection-endpoint.d.ts +11 -11
- package/esm/endpoint-generators/create-get-collection-endpoint.d.ts.map +1 -1
- package/esm/endpoint-generators/create-get-collection-endpoint.js +13 -12
- package/esm/endpoint-generators/create-get-collection-endpoint.js.map +1 -1
- package/esm/endpoint-generators/create-get-collection-endpoint.spec.js +43 -70
- package/esm/endpoint-generators/create-get-collection-endpoint.spec.js.map +1 -1
- package/esm/endpoint-generators/create-get-entity-endpoint.d.ts +6 -11
- package/esm/endpoint-generators/create-get-entity-endpoint.d.ts.map +1 -1
- package/esm/endpoint-generators/create-get-entity-endpoint.js +7 -11
- package/esm/endpoint-generators/create-get-entity-endpoint.js.map +1 -1
- package/esm/endpoint-generators/create-get-entity-endpoint.spec.js +16 -33
- package/esm/endpoint-generators/create-get-entity-endpoint.spec.js.map +1 -1
- package/esm/endpoint-generators/create-get-openapi-document-action.d.ts +1 -15
- package/esm/endpoint-generators/create-get-openapi-document-action.d.ts.map +1 -1
- package/esm/endpoint-generators/create-get-openapi-document-action.js +1 -24
- package/esm/endpoint-generators/create-get-openapi-document-action.js.map +1 -1
- package/esm/endpoint-generators/create-get-schema-action.d.ts +1 -1
- package/esm/endpoint-generators/create-get-schema-action.d.ts.map +1 -1
- package/esm/endpoint-generators/create-get-schema-action.js.map +1 -1
- package/esm/endpoint-generators/create-patch-endpoint.d.ts +7 -13
- package/esm/endpoint-generators/create-patch-endpoint.d.ts.map +1 -1
- package/esm/endpoint-generators/create-patch-endpoint.js +8 -13
- package/esm/endpoint-generators/create-patch-endpoint.js.map +1 -1
- package/esm/endpoint-generators/create-patch-endpoint.spec.js +10 -17
- package/esm/endpoint-generators/create-patch-endpoint.spec.js.map +1 -1
- package/esm/endpoint-generators/create-post-endpoint.d.ts +7 -13
- package/esm/endpoint-generators/create-post-endpoint.d.ts.map +1 -1
- package/esm/endpoint-generators/create-post-endpoint.js +8 -13
- package/esm/endpoint-generators/create-post-endpoint.js.map +1 -1
- package/esm/endpoint-generators/create-post-endpoint.spec.js +41 -14
- package/esm/endpoint-generators/create-post-endpoint.spec.js.map +1 -1
- package/esm/endpoint-generators/utils.d.ts +17 -2
- package/esm/endpoint-generators/utils.d.ts.map +1 -1
- package/esm/endpoint-generators/utils.js +33 -20
- package/esm/endpoint-generators/utils.js.map +1 -1
- package/esm/endpoint-generators/with-schema-and-openapi-action.d.ts +0 -2
- package/esm/endpoint-generators/with-schema-and-openapi-action.d.ts.map +1 -1
- package/esm/get-schema-from-api.d.ts +1 -1
- package/esm/get-schema-from-api.d.ts.map +1 -1
- package/esm/get-schema-from-api.spec.js.map +1 -1
- package/esm/helpers.d.ts +53 -87
- package/esm/helpers.d.ts.map +1 -1
- package/esm/helpers.js +91 -92
- package/esm/helpers.js.map +1 -1
- package/esm/helpers.spec.d.ts +2 -1
- package/esm/helpers.spec.d.ts.map +1 -1
- package/esm/helpers.spec.js +41 -38
- package/esm/helpers.spec.js.map +1 -1
- package/esm/http-authentication-settings.d.ts +35 -12
- package/esm/http-authentication-settings.d.ts.map +1 -1
- package/esm/http-authentication-settings.js +21 -29
- package/esm/http-authentication-settings.js.map +1 -1
- package/esm/http-server-pool.d.ts +64 -0
- package/esm/http-server-pool.d.ts.map +1 -0
- package/esm/http-server-pool.js +95 -0
- package/esm/http-server-pool.js.map +1 -0
- package/esm/http-server-pool.spec.d.ts +2 -0
- package/esm/http-server-pool.spec.d.ts.map +1 -0
- package/esm/http-server-pool.spec.js +193 -0
- package/esm/http-server-pool.spec.js.map +1 -0
- package/esm/http-user-context.d.ts +31 -44
- package/esm/http-user-context.d.ts.map +1 -1
- package/esm/http-user-context.js +76 -95
- package/esm/http-user-context.js.map +1 -1
- package/esm/http-user-context.spec.d.ts +8 -2
- package/esm/http-user-context.spec.d.ts.map +1 -1
- package/esm/http-user-context.spec.js +189 -337
- package/esm/http-user-context.spec.js.map +1 -1
- package/esm/index.d.ts +6 -4
- package/esm/index.d.ts.map +1 -1
- package/esm/index.js +6 -4
- package/esm/index.js.map +1 -1
- package/esm/login-response-strategy.d.ts +11 -10
- package/esm/login-response-strategy.d.ts.map +1 -1
- package/esm/login-response-strategy.js +7 -6
- package/esm/login-response-strategy.js.map +1 -1
- package/esm/login-response-strategy.spec.js +25 -29
- package/esm/login-response-strategy.spec.js.map +1 -1
- package/esm/openapi/generate-openapi-document.d.ts +0 -8
- package/esm/openapi/generate-openapi-document.d.ts.map +1 -1
- package/esm/openapi/generate-openapi-document.js +0 -2
- package/esm/openapi/generate-openapi-document.js.map +1 -1
- package/esm/proxy-manager.spec.js +152 -176
- package/esm/proxy-manager.spec.js.map +1 -1
- package/esm/proxy-runtime.d.ts +27 -0
- package/esm/proxy-runtime.d.ts.map +1 -0
- package/esm/proxy-runtime.js +45 -0
- package/esm/proxy-runtime.js.map +1 -0
- package/esm/proxy-runtime.spec.d.ts +2 -0
- package/esm/proxy-runtime.spec.d.ts.map +1 -0
- package/esm/proxy-runtime.spec.js +39 -0
- package/esm/proxy-runtime.spec.js.map +1 -0
- package/esm/rest-api-runtime.d.ts +76 -0
- package/esm/rest-api-runtime.d.ts.map +1 -0
- package/esm/rest-api-runtime.js +131 -0
- package/esm/rest-api-runtime.js.map +1 -0
- package/esm/rest-api-runtime.spec.d.ts +2 -0
- package/esm/rest-api-runtime.spec.d.ts.map +1 -0
- package/esm/rest-api-runtime.spec.js +58 -0
- package/esm/rest-api-runtime.spec.js.map +1 -0
- package/esm/rest-service.integration.spec.d.ts +1 -1
- package/esm/rest-service.integration.spec.d.ts.map +1 -1
- package/esm/rest-service.integration.spec.js +60 -82
- package/esm/rest-service.integration.spec.js.map +1 -1
- package/esm/rest.integration.test.js +26 -84
- package/esm/rest.integration.test.js.map +1 -1
- package/esm/server-telemetry.d.ts +57 -0
- package/esm/server-telemetry.d.ts.map +1 -0
- package/esm/server-telemetry.js +26 -0
- package/esm/server-telemetry.js.map +1 -0
- package/esm/server-telemetry.spec.d.ts +2 -0
- package/esm/server-telemetry.spec.d.ts.map +1 -0
- package/esm/server-telemetry.spec.js +52 -0
- package/esm/server-telemetry.spec.js.map +1 -0
- package/esm/static-server-manager.spec.js +60 -125
- package/esm/static-server-manager.spec.js.map +1 -1
- package/esm/static-site-runtime.d.ts +21 -0
- package/esm/static-site-runtime.d.ts.map +1 -0
- package/esm/static-site-runtime.js +48 -0
- package/esm/static-site-runtime.js.map +1 -0
- package/esm/static-site-runtime.spec.d.ts +2 -0
- package/esm/static-site-runtime.spec.d.ts.map +1 -0
- package/esm/static-site-runtime.spec.js +30 -0
- package/esm/static-site-runtime.spec.js.map +1 -0
- package/esm/user-store.d.ts +39 -0
- package/esm/user-store.d.ts.map +1 -0
- package/esm/user-store.js +62 -0
- package/esm/user-store.js.map +1 -0
- package/esm/user-store.spec.d.ts +2 -0
- package/esm/user-store.spec.d.ts.map +1 -0
- package/esm/user-store.spec.js +72 -0
- package/esm/user-store.spec.js.map +1 -0
- package/esm/validate.integration.spec.js +26 -83
- package/esm/validate.integration.spec.js.map +1 -1
- package/package.json +8 -8
- package/src/actions/get-current-user.spec.ts +11 -10
- package/src/actions/index.ts +0 -1
- package/src/actions/is-authenticated.spec.ts +12 -7
- package/src/actions/logout-action.spec.ts +12 -12
- package/src/actions/logout.ts +1 -1
- package/src/actions/password-login-action.spec.ts +30 -30
- package/src/actions/password-login-action.ts +1 -1
- package/src/authenticate.spec.ts +45 -51
- package/src/authenticate.ts +1 -1
- package/src/authorize.spec.ts +37 -39
- package/src/endpoint-generators/create-delete-endpoint.spec.ts +16 -24
- package/src/endpoint-generators/create-delete-endpoint.ts +11 -17
- package/src/endpoint-generators/create-get-collection-endpoint.spec.ts +45 -78
- package/src/endpoint-generators/create-get-collection-endpoint.ts +17 -19
- package/src/endpoint-generators/create-get-entity-endpoint.spec.ts +17 -33
- package/src/endpoint-generators/create-get-entity-endpoint.ts +11 -17
- package/src/endpoint-generators/create-get-openapi-document-action.ts +2 -38
- package/src/endpoint-generators/create-get-schema-action.ts +1 -1
- package/src/endpoint-generators/create-patch-endpoint.spec.ts +11 -18
- package/src/endpoint-generators/create-patch-endpoint.ts +12 -23
- package/src/endpoint-generators/create-post-endpoint.spec.ts +45 -14
- package/src/endpoint-generators/create-post-endpoint.ts +13 -23
- package/src/endpoint-generators/utils.ts +36 -28
- package/src/endpoint-generators/with-schema-and-openapi-action.ts +0 -3
- package/src/get-schema-from-api.spec.ts +1 -1
- package/src/get-schema-from-api.ts +1 -1
- package/src/helpers.spec.ts +51 -41
- package/src/helpers.ts +140 -109
- package/src/http-authentication-settings.ts +51 -25
- package/src/http-server-pool.spec.ts +220 -0
- package/src/http-server-pool.ts +169 -0
- package/src/http-user-context.spec.ts +203 -383
- package/src/http-user-context.ts +114 -91
- package/src/index.ts +6 -4
- package/src/login-response-strategy.spec.ts +32 -31
- package/src/login-response-strategy.ts +13 -12
- package/src/openapi/generate-openapi-document.ts +0 -3
- package/src/proxy-manager.spec.ts +152 -182
- package/src/proxy-runtime.spec.ts +50 -0
- package/src/proxy-runtime.ts +75 -0
- package/src/rest-api-runtime.spec.ts +77 -0
- package/src/rest-api-runtime.ts +204 -0
- package/src/rest-service.integration.spec.ts +68 -87
- package/src/rest.integration.test.ts +27 -87
- package/src/server-telemetry.spec.ts +56 -0
- package/src/server-telemetry.ts +51 -0
- package/src/static-server-manager.spec.ts +63 -151
- package/src/static-site-runtime.spec.ts +39 -0
- package/src/static-site-runtime.ts +75 -0
- package/src/user-store.spec.ts +86 -0
- package/src/user-store.ts +68 -0
- package/src/validate.integration.spec.ts +39 -97
- package/esm/actions/login-action.spec.d.ts +0 -2
- package/esm/actions/login-action.spec.d.ts.map +0 -1
- package/esm/actions/login-action.spec.js +0 -34
- package/esm/actions/login-action.spec.js.map +0 -1
- package/esm/actions/login.d.ts +0 -19
- package/esm/actions/login.d.ts.map +0 -1
- package/esm/actions/login.js +0 -27
- package/esm/actions/login.js.map +0 -1
- package/esm/api-manager.d.ts +0 -104
- package/esm/api-manager.d.ts.map +0 -1
- package/esm/api-manager.js +0 -180
- package/esm/api-manager.js.map +0 -1
- package/esm/proxy-manager.d.ts +0 -53
- package/esm/proxy-manager.d.ts.map +0 -1
- package/esm/proxy-manager.js +0 -84
- package/esm/proxy-manager.js.map +0 -1
- package/esm/server-manager.d.ts +0 -48
- package/esm/server-manager.d.ts.map +0 -1
- package/esm/server-manager.js +0 -100
- package/esm/server-manager.js.map +0 -1
- package/esm/static-server-manager.d.ts +0 -19
- package/esm/static-server-manager.d.ts.map +0 -1
- package/esm/static-server-manager.js +0 -65
- package/esm/static-server-manager.js.map +0 -1
- package/esm/swagger/generate-swagger-json.spec.d.ts +0 -2
- package/esm/swagger/generate-swagger-json.spec.d.ts.map +0 -1
- package/esm/swagger/generate-swagger-json.spec.js +0 -215
- package/esm/swagger/generate-swagger-json.spec.js.map +0 -1
- package/src/actions/login-action.spec.ts +0 -42
- package/src/actions/login.ts +0 -32
- package/src/api-manager.ts +0 -308
- package/src/proxy-manager.ts +0 -102
- package/src/server-manager.ts +0 -135
- package/src/static-server-manager.ts +0 -90
- package/src/swagger/generate-swagger-json.spec.ts +0 -250
|
@@ -1,10 +1,16 @@
|
|
|
1
1
|
/* eslint-disable @typescript-eslint/no-unsafe-assignment */
|
|
2
|
-
import {
|
|
2
|
+
import { InMemoryStore, User as UserModel } from '@furystack/core'
|
|
3
3
|
import { getPort } from '@furystack/core/port-generator'
|
|
4
|
-
import {
|
|
5
|
-
import { getRepository } from '@furystack/repository'
|
|
4
|
+
import { createInjector } from '@furystack/inject'
|
|
6
5
|
import type { OpenApiDocument, WithSchemaAction } from '@furystack/rest'
|
|
7
6
|
import { createClient, ResponseError } from '@furystack/rest-client-fetch'
|
|
7
|
+
import {
|
|
8
|
+
PasswordCredential,
|
|
9
|
+
PasswordCredentialStore,
|
|
10
|
+
PasswordResetToken,
|
|
11
|
+
PasswordResetTokenStore,
|
|
12
|
+
usePasswordPolicy,
|
|
13
|
+
} from '@furystack/security'
|
|
8
14
|
import { usingAsync } from '@furystack/utils'
|
|
9
15
|
import type Ajv from 'ajv'
|
|
10
16
|
import { describe, expect, it } from 'vitest'
|
|
@@ -13,10 +19,11 @@ import { createGetCollectionEndpoint } from './endpoint-generators/create-get-co
|
|
|
13
19
|
import { createGetEntityEndpoint } from './endpoint-generators/create-get-entity-endpoint.js'
|
|
14
20
|
import { createPatchEndpoint } from './endpoint-generators/create-patch-endpoint.js'
|
|
15
21
|
import { createPostEndpoint } from './endpoint-generators/create-post-endpoint.js'
|
|
16
|
-
import {
|
|
22
|
+
import { MockDataSet, setupContext } from './endpoint-generators/utils.js'
|
|
17
23
|
import { useHttpAuthentication, useRestService } from './helpers.js'
|
|
18
24
|
import { DefaultSession } from './models/default-session.js'
|
|
19
25
|
import { JsonResult } from './request-action-implementation.js'
|
|
26
|
+
import { SessionStore, UserStore } from './user-store.js'
|
|
20
27
|
import type { ValidationApi } from './validate.integration.schema.js'
|
|
21
28
|
import schema from './validate.integration.spec.schema.json' with { type: 'json' }
|
|
22
29
|
import { Validate } from './validate.js'
|
|
@@ -28,15 +35,12 @@ const description = crypto.randomUUID()
|
|
|
28
35
|
const version = crypto.randomUUID()
|
|
29
36
|
|
|
30
37
|
const createValidateApi = async (options = { enableGetSchema: false }) => {
|
|
31
|
-
const injector =
|
|
38
|
+
const injector = createInjector()
|
|
32
39
|
const port = getPort()
|
|
33
40
|
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
getRepository(injector).createDataSet(MockClass, 'id')
|
|
38
|
-
getRepository(injector).createDataSet(User, 'username')
|
|
39
|
-
getRepository(injector).createDataSet(DefaultSession, 'sessionId')
|
|
41
|
+
injector.bind(UserStore, () => new InMemoryStore({ model: UserModel, primaryKey: 'username' }))
|
|
42
|
+
injector.bind(SessionStore, () => new InMemoryStore({ model: DefaultSession, primaryKey: 'sessionId' }))
|
|
43
|
+
setupContext(injector)
|
|
40
44
|
|
|
41
45
|
const api = await useRestService<ValidationApi>({
|
|
42
46
|
injector,
|
|
@@ -61,11 +65,11 @@ const createValidateApi = async (options = { enableGetSchema: false }) => {
|
|
|
61
65
|
'/mock': Validate({
|
|
62
66
|
schema,
|
|
63
67
|
schemaName: 'GetMockCollectionEndpoint',
|
|
64
|
-
})(createGetCollectionEndpoint(
|
|
68
|
+
})(createGetCollectionEndpoint(MockDataSet)),
|
|
65
69
|
'/mock/:id': Validate({
|
|
66
70
|
schema,
|
|
67
71
|
schemaName: 'GetMockEntityEndpoint',
|
|
68
|
-
})(createGetEntityEndpoint(
|
|
72
|
+
})(createGetEntityEndpoint(MockDataSet)),
|
|
69
73
|
},
|
|
70
74
|
POST: {
|
|
71
75
|
'/validate-body': Validate({
|
|
@@ -78,19 +82,19 @@ const createValidateApi = async (options = { enableGetSchema: false }) => {
|
|
|
78
82
|
'/mock': Validate({
|
|
79
83
|
schema,
|
|
80
84
|
schemaName: 'PostMockEndpoint',
|
|
81
|
-
})(createPostEndpoint(
|
|
85
|
+
})(createPostEndpoint(MockDataSet)),
|
|
82
86
|
},
|
|
83
87
|
PATCH: {
|
|
84
88
|
'/mock/:id': Validate({
|
|
85
89
|
schema,
|
|
86
90
|
schemaName: 'PatchMockEndpoint',
|
|
87
|
-
})(createPatchEndpoint(
|
|
91
|
+
})(createPatchEndpoint(MockDataSet)),
|
|
88
92
|
},
|
|
89
93
|
DELETE: {
|
|
90
94
|
'/mock/:id': Validate({
|
|
91
95
|
schema,
|
|
92
96
|
schemaName: 'DeleteMockEndpoint',
|
|
93
|
-
})(createDeleteEndpoint(
|
|
97
|
+
})(createDeleteEndpoint(MockDataSet)),
|
|
94
98
|
},
|
|
95
99
|
},
|
|
96
100
|
port,
|
|
@@ -179,51 +183,6 @@ describe('Validation integration tests', () => {
|
|
|
179
183
|
})
|
|
180
184
|
})
|
|
181
185
|
|
|
182
|
-
describe('swagger.json backward compatibility', () => {
|
|
183
|
-
it('Should serve the same OpenAPI document at /swagger.json when enabled', async () => {
|
|
184
|
-
await usingAsync(await createValidateApi({ enableGetSchema: true }), async ({ client }) => {
|
|
185
|
-
const result = await (client as ReturnType<typeof createClient<any>>)({
|
|
186
|
-
method: 'GET',
|
|
187
|
-
action: '/swagger.json',
|
|
188
|
-
})
|
|
189
|
-
|
|
190
|
-
expect(result.response.status).toBe(200)
|
|
191
|
-
expect(result.result).toBeDefined()
|
|
192
|
-
|
|
193
|
-
const openApiDoc = result.result as OpenApiDocument
|
|
194
|
-
expect(openApiDoc.openapi).toBe('3.1.0')
|
|
195
|
-
expect(openApiDoc.info?.title).toBe(name)
|
|
196
|
-
})
|
|
197
|
-
})
|
|
198
|
-
|
|
199
|
-
it('Should include Deprecation header on /swagger.json', async () => {
|
|
200
|
-
await usingAsync(await createValidateApi({ enableGetSchema: true }), async ({ client }) => {
|
|
201
|
-
const result = await (client as ReturnType<typeof createClient<any>>)({
|
|
202
|
-
method: 'GET',
|
|
203
|
-
action: '/swagger.json',
|
|
204
|
-
})
|
|
205
|
-
|
|
206
|
-
expect(result.response.headers.get('deprecation')).toBe('true')
|
|
207
|
-
expect(result.response.headers.get('link')).toContain('/openapi.json')
|
|
208
|
-
})
|
|
209
|
-
})
|
|
210
|
-
|
|
211
|
-
it('Should return a 404 for /swagger.json when not enabled', async () => {
|
|
212
|
-
await usingAsync(await createValidateApi({ enableGetSchema: false }), async ({ client }) => {
|
|
213
|
-
try {
|
|
214
|
-
await (client as ReturnType<typeof createClient<any>>)({
|
|
215
|
-
method: 'GET',
|
|
216
|
-
action: '/swagger.json',
|
|
217
|
-
})
|
|
218
|
-
expect.fail('Expected response error but got success')
|
|
219
|
-
} catch (error) {
|
|
220
|
-
expect(error).toBeInstanceOf(ResponseError)
|
|
221
|
-
expect((error as ResponseError).response.status).toBe(404)
|
|
222
|
-
}
|
|
223
|
-
})
|
|
224
|
-
})
|
|
225
|
-
})
|
|
226
|
-
|
|
227
186
|
describe('Validation metadata', () => {
|
|
228
187
|
it('Should return 404 when not enabled', async () => {
|
|
229
188
|
expect.assertions(2)
|
|
@@ -492,16 +451,22 @@ describe('Validation integration tests', () => {
|
|
|
492
451
|
|
|
493
452
|
describe('OpenAPI security schemes from authentication providers', () => {
|
|
494
453
|
const createApiWithAuth = async () => {
|
|
495
|
-
const injector =
|
|
454
|
+
const injector = createInjector()
|
|
496
455
|
const port = getPort()
|
|
497
456
|
|
|
498
|
-
|
|
499
|
-
|
|
500
|
-
|
|
501
|
-
|
|
502
|
-
|
|
503
|
-
|
|
504
|
-
|
|
457
|
+
injector.bind(UserStore, () => new InMemoryStore({ model: UserModel, primaryKey: 'username' }))
|
|
458
|
+
injector.bind(SessionStore, () => new InMemoryStore({ model: DefaultSession, primaryKey: 'sessionId' }))
|
|
459
|
+
injector.bind(
|
|
460
|
+
PasswordCredentialStore,
|
|
461
|
+
() => new InMemoryStore({ model: PasswordCredential, primaryKey: 'userName' }),
|
|
462
|
+
)
|
|
463
|
+
injector.bind(
|
|
464
|
+
PasswordResetTokenStore,
|
|
465
|
+
() => new InMemoryStore({ model: PasswordResetToken, primaryKey: 'token' }),
|
|
466
|
+
)
|
|
467
|
+
setupContext(injector)
|
|
468
|
+
|
|
469
|
+
usePasswordPolicy(injector)
|
|
505
470
|
useHttpAuthentication(injector)
|
|
506
471
|
|
|
507
472
|
await useRestService<ValidationApi>({
|
|
@@ -522,10 +487,10 @@ describe('Validation integration tests', () => {
|
|
|
522
487
|
JsonResult({ ...headers }),
|
|
523
488
|
),
|
|
524
489
|
'/mock': Validate({ schema, schemaName: 'GetMockCollectionEndpoint' })(
|
|
525
|
-
createGetCollectionEndpoint(
|
|
490
|
+
createGetCollectionEndpoint(MockDataSet),
|
|
526
491
|
),
|
|
527
492
|
'/mock/:id': Validate({ schema, schemaName: 'GetMockEntityEndpoint' })(
|
|
528
|
-
createGetEntityEndpoint(
|
|
493
|
+
createGetEntityEndpoint(MockDataSet),
|
|
529
494
|
),
|
|
530
495
|
},
|
|
531
496
|
POST: {
|
|
@@ -533,19 +498,13 @@ describe('Validation integration tests', () => {
|
|
|
533
498
|
const body = await getBody()
|
|
534
499
|
return JsonResult({ ...body })
|
|
535
500
|
}),
|
|
536
|
-
'/mock': Validate({ schema, schemaName: 'PostMockEndpoint' })(
|
|
537
|
-
createPostEndpoint({ model: MockClass, primaryKey: 'id' }),
|
|
538
|
-
),
|
|
501
|
+
'/mock': Validate({ schema, schemaName: 'PostMockEndpoint' })(createPostEndpoint(MockDataSet)),
|
|
539
502
|
},
|
|
540
503
|
PATCH: {
|
|
541
|
-
'/mock/:id': Validate({ schema, schemaName: 'PatchMockEndpoint' })(
|
|
542
|
-
createPatchEndpoint({ model: MockClass, primaryKey: 'id' }),
|
|
543
|
-
),
|
|
504
|
+
'/mock/:id': Validate({ schema, schemaName: 'PatchMockEndpoint' })(createPatchEndpoint(MockDataSet)),
|
|
544
505
|
},
|
|
545
506
|
DELETE: {
|
|
546
|
-
'/mock/:id': Validate({ schema, schemaName: 'DeleteMockEndpoint' })(
|
|
547
|
-
createDeleteEndpoint({ model: MockClass, primaryKey: 'id' }),
|
|
548
|
-
),
|
|
507
|
+
'/mock/:id': Validate({ schema, schemaName: 'DeleteMockEndpoint' })(createDeleteEndpoint(MockDataSet)),
|
|
549
508
|
},
|
|
550
509
|
},
|
|
551
510
|
port,
|
|
@@ -577,22 +536,5 @@ describe('Validation integration tests', () => {
|
|
|
577
536
|
})
|
|
578
537
|
})
|
|
579
538
|
})
|
|
580
|
-
|
|
581
|
-
it('Should include detected security schemes in the deprecated /swagger.json endpoint', async () => {
|
|
582
|
-
await usingAsync(await createApiWithAuth(), async ({ client }) => {
|
|
583
|
-
const result = await (client as ReturnType<typeof createClient<any>>)({
|
|
584
|
-
method: 'GET',
|
|
585
|
-
action: '/swagger.json',
|
|
586
|
-
})
|
|
587
|
-
|
|
588
|
-
const openApiDoc = result.result as OpenApiDocument
|
|
589
|
-
expect(openApiDoc.components?.securitySchemes?.basicAuth).toEqual({ type: 'http', scheme: 'basic' })
|
|
590
|
-
expect(openApiDoc.components?.securitySchemes?.cookieAuth).toEqual({
|
|
591
|
-
type: 'apiKey',
|
|
592
|
-
in: 'cookie',
|
|
593
|
-
name: 'session',
|
|
594
|
-
})
|
|
595
|
-
})
|
|
596
|
-
})
|
|
597
539
|
})
|
|
598
540
|
})
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"login-action.spec.d.ts","sourceRoot":"","sources":["../../src/actions/login-action.spec.ts"],"names":[],"mappings":""}
|
|
@@ -1,34 +0,0 @@
|
|
|
1
|
-
import { Injector } from '@furystack/inject';
|
|
2
|
-
import { usingAsync } from '@furystack/utils';
|
|
3
|
-
import { describe, expect, it, vi } from 'vitest';
|
|
4
|
-
import { HttpUserContext } from '../http-user-context.js';
|
|
5
|
-
import { LoginAction } from './login.js';
|
|
6
|
-
describe('LoginAction', () => {
|
|
7
|
-
const request = { url: 'https://google.com' };
|
|
8
|
-
const response = {};
|
|
9
|
-
it('Returns the provided user with 200 on success', async () => {
|
|
10
|
-
const testUser = { Name: 'Userke' };
|
|
11
|
-
await usingAsync(new Injector(), async (i) => {
|
|
12
|
-
i.setExplicitInstance({
|
|
13
|
-
authenticateUser: vi.fn(async () => testUser),
|
|
14
|
-
cookieLogin: vi.fn(async () => testUser),
|
|
15
|
-
authentication: {},
|
|
16
|
-
}, HttpUserContext);
|
|
17
|
-
const result = await LoginAction({
|
|
18
|
-
request,
|
|
19
|
-
response,
|
|
20
|
-
injector: i,
|
|
21
|
-
getBody: async () => ({ username: 'testuser', password: 'alma' }),
|
|
22
|
-
});
|
|
23
|
-
expect(result.chunk).toEqual(testUser);
|
|
24
|
-
expect(result.statusCode).toBe(200);
|
|
25
|
-
});
|
|
26
|
-
});
|
|
27
|
-
it('Returns throw error with 400 on fail', async () => {
|
|
28
|
-
await usingAsync(new Injector(), async (i) => {
|
|
29
|
-
i.setExplicitInstance({ cookieLogin: async () => Promise.reject(new Error(':(')) }, HttpUserContext);
|
|
30
|
-
await expect(LoginAction({ request, response, injector: i, getBody: async () => ({ username: '', password: '' }) })).rejects.toThrowError('Login Failed');
|
|
31
|
-
});
|
|
32
|
-
});
|
|
33
|
-
});
|
|
34
|
-
//# sourceMappingURL=login-action.spec.js.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"login-action.spec.js","sourceRoot":"","sources":["../../src/actions/login-action.spec.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAA;AAC5C,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAA;AAE7C,OAAO,EAAE,QAAQ,EAAE,MAAM,EAAE,EAAE,EAAE,EAAE,EAAE,MAAM,QAAQ,CAAA;AACjD,OAAO,EAAE,eAAe,EAAE,MAAM,yBAAyB,CAAA;AACzD,OAAO,EAAE,WAAW,EAAE,MAAM,YAAY,CAAA;AAExC,QAAQ,CAAC,aAAa,EAAE,GAAG,EAAE;IAC3B,MAAM,OAAO,GAAG,EAAE,GAAG,EAAE,oBAAoB,EAAqB,CAAA;IAChE,MAAM,QAAQ,GAAG,EAAoB,CAAA;IAErC,EAAE,CAAC,+CAA+C,EAAE,KAAK,IAAI,EAAE;QAC7D,MAAM,QAAQ,GAAG,EAAE,IAAI,EAAE,QAAQ,EAAE,CAAA;QACnC,MAAM,UAAU,CAAC,IAAI,QAAQ,EAAE,EAAE,KAAK,EAAE,CAAC,EAAE,EAAE;YAC3C,CAAC,CAAC,mBAAmB,CACnB;gBACE,gBAAgB,EAAE,EAAE,CAAC,EAAE,CAAC,KAAK,IAAI,EAAE,CAAC,QAAQ,CAAC;gBAC7C,WAAW,EAAE,EAAE,CAAC,EAAE,CAAC,KAAK,IAAI,EAAE,CAAC,QAAQ,CAAC;gBACxC,cAAc,EAAE,EAAE;aACnB,EACD,eAAe,CAChB,CAAA;YACD,MAAM,MAAM,GAAG,MAAM,WAAW,CAAC;gBAC/B,OAAO;gBACP,QAAQ;gBACR,QAAQ,EAAE,CAAC;gBACX,OAAO,EAAE,KAAK,IAAI,EAAE,CAAC,CAAC,EAAE,QAAQ,EAAE,UAAU,EAAE,QAAQ,EAAE,MAAM,EAAE,CAAC;aAClE,CAAC,CAAA;YACF,MAAM,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAA;YACtC,MAAM,CAAC,MAAM,CAAC,UAAU,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAA;QACrC,CAAC,CAAC,CAAA;IACJ,CAAC,CAAC,CAAA;IAEF,EAAE,CAAC,sCAAsC,EAAE,KAAK,IAAI,EAAE;QACpD,MAAM,UAAU,CAAC,IAAI,QAAQ,EAAE,EAAE,KAAK,EAAE,CAAC,EAAE,EAAE;YAC3C,CAAC,CAAC,mBAAmB,CAAC,EAAE,WAAW,EAAE,KAAK,IAAI,EAAE,CAAC,OAAO,CAAC,MAAM,CAAC,IAAI,KAAK,CAAC,IAAI,CAAC,CAAC,EAAE,EAAE,eAAe,CAAC,CAAA;YACpG,MAAM,MAAM,CACV,WAAW,CAAC,EAAE,OAAO,EAAE,QAAQ,EAAE,QAAQ,EAAE,CAAC,EAAE,OAAO,EAAE,KAAK,IAAI,EAAE,CAAC,CAAC,EAAE,QAAQ,EAAE,EAAE,EAAE,QAAQ,EAAE,EAAE,EAAE,CAAC,EAAE,CAAC,CACvG,CAAC,OAAO,CAAC,YAAY,CAAC,cAAc,CAAC,CAAA;QACxC,CAAC,CAAC,CAAA;IACJ,CAAC,CAAC,CAAA;AACJ,CAAC,CAAC,CAAA"}
|
package/esm/actions/login.d.ts
DELETED
|
@@ -1,19 +0,0 @@
|
|
|
1
|
-
import type { User } from '@furystack/core';
|
|
2
|
-
import type { RequestAction } from '../request-action-implementation.js';
|
|
3
|
-
/**
|
|
4
|
-
* Action that logs in the current user.
|
|
5
|
-
* Should be called with a JSON POST body with `username` and `password` fields.
|
|
6
|
-
* Returns the current user instance.
|
|
7
|
-
*
|
|
8
|
-
* @deprecated Use `createPasswordLoginAction(createCookieLoginStrategy(injector))` instead.
|
|
9
|
-
* This static action resolves services from the request-scoped injector on
|
|
10
|
-
* every call; the factory approach captures them once at setup time.
|
|
11
|
-
*/
|
|
12
|
-
export declare const LoginAction: RequestAction<{
|
|
13
|
-
result: User;
|
|
14
|
-
body: {
|
|
15
|
-
username: string;
|
|
16
|
-
password: string;
|
|
17
|
-
};
|
|
18
|
-
}>;
|
|
19
|
-
//# sourceMappingURL=login.d.ts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"login.d.ts","sourceRoot":"","sources":["../../src/actions/login.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,iBAAiB,CAAA;AAK3C,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,qCAAqC,CAAA;AAGxE;;;;;;;;GAQG;AACH,eAAO,MAAM,WAAW,EAAE,aAAa,CAAC;IACtC,MAAM,EAAE,IAAI,CAAA;IACZ,IAAI,EAAE;QAAE,QAAQ,EAAE,MAAM,CAAC;QAAC,QAAQ,EAAE,MAAM,CAAA;KAAE,CAAA;CAC7C,CAWA,CAAA"}
|
package/esm/actions/login.js
DELETED
|
@@ -1,27 +0,0 @@
|
|
|
1
|
-
import { RequestError } from '@furystack/rest';
|
|
2
|
-
import { sleepAsync } from '@furystack/utils';
|
|
3
|
-
import { HttpUserContext } from '../http-user-context.js';
|
|
4
|
-
import { JsonResult } from '../request-action-implementation.js';
|
|
5
|
-
/**
|
|
6
|
-
* Action that logs in the current user.
|
|
7
|
-
* Should be called with a JSON POST body with `username` and `password` fields.
|
|
8
|
-
* Returns the current user instance.
|
|
9
|
-
*
|
|
10
|
-
* @deprecated Use `createPasswordLoginAction(createCookieLoginStrategy(injector))` instead.
|
|
11
|
-
* This static action resolves services from the request-scoped injector on
|
|
12
|
-
* every call; the factory approach captures them once at setup time.
|
|
13
|
-
*/
|
|
14
|
-
export const LoginAction = async ({ injector, getBody, response }) => {
|
|
15
|
-
const userContext = injector.getInstance(HttpUserContext);
|
|
16
|
-
const body = await getBody();
|
|
17
|
-
try {
|
|
18
|
-
const user = await userContext.authenticateUser(body.username, body.password);
|
|
19
|
-
await userContext.cookieLogin(user, response);
|
|
20
|
-
return JsonResult(user, 200);
|
|
21
|
-
}
|
|
22
|
-
catch {
|
|
23
|
-
await sleepAsync(Math.random() * 1000);
|
|
24
|
-
throw new RequestError('Login Failed', 400);
|
|
25
|
-
}
|
|
26
|
-
};
|
|
27
|
-
//# sourceMappingURL=login.js.map
|
package/esm/actions/login.js.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"login.js","sourceRoot":"","sources":["../../src/actions/login.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,YAAY,EAAE,MAAM,iBAAiB,CAAA;AAC9C,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAA;AAE7C,OAAO,EAAE,eAAe,EAAE,MAAM,yBAAyB,CAAA;AAEzD,OAAO,EAAE,UAAU,EAAE,MAAM,qCAAqC,CAAA;AAEhE;;;;;;;;GAQG;AACH,MAAM,CAAC,MAAM,WAAW,GAGnB,KAAK,EAAE,EAAE,QAAQ,EAAE,OAAO,EAAE,QAAQ,EAAE,EAAE,EAAE;IAC7C,MAAM,WAAW,GAAG,QAAQ,CAAC,WAAW,CAAC,eAAe,CAAC,CAAA;IACzD,MAAM,IAAI,GAAG,MAAM,OAAO,EAAE,CAAA;IAC5B,IAAI,CAAC;QACH,MAAM,IAAI,GAAG,MAAM,WAAW,CAAC,gBAAgB,CAAC,IAAI,CAAC,QAAQ,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAA;QAC7E,MAAM,WAAW,CAAC,WAAW,CAAC,IAAI,EAAE,QAAQ,CAAC,CAAA;QAC7C,OAAO,UAAU,CAAC,IAAI,EAAE,GAAG,CAAC,CAAA;IAC9B,CAAC;IAAC,MAAM,CAAC;QACP,MAAM,UAAU,CAAC,IAAI,CAAC,MAAM,EAAE,GAAG,IAAI,CAAC,CAAA;QACtC,MAAM,IAAI,YAAY,CAAC,cAAc,EAAE,GAAG,CAAC,CAAA;IAC7C,CAAC;AACH,CAAC,CAAA"}
|
package/esm/api-manager.d.ts
DELETED
|
@@ -1,104 +0,0 @@
|
|
|
1
|
-
import type { Injector } from '@furystack/inject';
|
|
2
|
-
import type { Method, RestApi } from '@furystack/rest';
|
|
3
|
-
import type { MatchFunction } from 'path-to-regexp';
|
|
4
|
-
import type { CorsOptions } from './models/cors-options.js';
|
|
5
|
-
import type { RequestAction } from './request-action-implementation.js';
|
|
6
|
-
import type { OnRequest } from './server-manager.js';
|
|
7
|
-
import './server-response-extensions.js';
|
|
8
|
-
export type RestApiImplementation<T extends RestApi> = {
|
|
9
|
-
[TMethod in keyof T]: {
|
|
10
|
-
[TUrl in keyof T[TMethod]]: T[TMethod][TUrl] extends {
|
|
11
|
-
result: unknown;
|
|
12
|
-
} ? RequestAction<T[TMethod][TUrl]> : never;
|
|
13
|
-
};
|
|
14
|
-
};
|
|
15
|
-
export interface ImplementApiOptions<T extends RestApi> {
|
|
16
|
-
/**
|
|
17
|
-
* The structure of the implemented API.
|
|
18
|
-
*/
|
|
19
|
-
api: RestApiImplementation<T>;
|
|
20
|
-
/**
|
|
21
|
-
* The Injector instance to use for dependency injection in the API actions.
|
|
22
|
-
*/
|
|
23
|
-
injector: Injector;
|
|
24
|
-
/**
|
|
25
|
-
* The host name for the API Server. If not provided, the default host (ServerManager.DEFAULT_HOST) will be used.
|
|
26
|
-
*/
|
|
27
|
-
hostName?: string;
|
|
28
|
-
/**
|
|
29
|
-
* The root path for the API. This will be prepended to all API paths.
|
|
30
|
-
*/
|
|
31
|
-
root: string;
|
|
32
|
-
/**
|
|
33
|
-
* The port on which the API server will listen.
|
|
34
|
-
*/
|
|
35
|
-
port: number;
|
|
36
|
-
/**
|
|
37
|
-
* CORS options to configure Cross-Origin Resource Sharing for the API.
|
|
38
|
-
*/
|
|
39
|
-
cors?: CorsOptions;
|
|
40
|
-
/**
|
|
41
|
-
* An optional function to deserialize query parameters from the URL.
|
|
42
|
-
* This function should take a query string (e.g., "?key=value") and return an object with the parsed parameters.
|
|
43
|
-
* If not provided, the default deserialization will be used.
|
|
44
|
-
*/
|
|
45
|
-
deserializeQueryParams?: (param: string) => any;
|
|
46
|
-
/**
|
|
47
|
-
* Adds an additional 'GET /schema' endpoint that returns the schema definitions of the API.
|
|
48
|
-
* Also adds a 'GET /openapi.json' endpoint that returns the API schema in OpenAPI 3.1 format.
|
|
49
|
-
*/
|
|
50
|
-
enableGetSchema?: boolean;
|
|
51
|
-
/**
|
|
52
|
-
* Optional name for the API, used in the generated schema.
|
|
53
|
-
* This can be useful for documentation or identification purposes.
|
|
54
|
-
*/
|
|
55
|
-
name?: string;
|
|
56
|
-
/**
|
|
57
|
-
* Optional description for the API, used in the generated schema.
|
|
58
|
-
* This can provide additional context or information about the API's purpose.
|
|
59
|
-
*/
|
|
60
|
-
description?: string;
|
|
61
|
-
/**
|
|
62
|
-
* Optional version for the API, used in the generated schema.
|
|
63
|
-
* This can help in versioning the API and tracking changes over time.
|
|
64
|
-
*/
|
|
65
|
-
version?: string;
|
|
66
|
-
}
|
|
67
|
-
export type NewCompiledApiEntry = {
|
|
68
|
-
method: Method;
|
|
69
|
-
fullPath: string;
|
|
70
|
-
matcher: MatchFunction<Partial<Record<string, string | string[]>>>;
|
|
71
|
-
action: RequestAction<any>;
|
|
72
|
-
};
|
|
73
|
-
export type NewCompiledApi = {
|
|
74
|
-
[K in Method]?: NewCompiledApiEntry[];
|
|
75
|
-
};
|
|
76
|
-
export type OnRequestOptions = OnRequest & {
|
|
77
|
-
compiledApi: NewCompiledApi;
|
|
78
|
-
hostName?: string;
|
|
79
|
-
port: number;
|
|
80
|
-
rootApiPath: string;
|
|
81
|
-
injector: Injector;
|
|
82
|
-
cors?: CorsOptions;
|
|
83
|
-
supportedMethods: string[];
|
|
84
|
-
deserializeQueryParams?: (param: string) => Record<string, unknown>;
|
|
85
|
-
};
|
|
86
|
-
export declare class ApiManager {
|
|
87
|
-
private getSuportedMethods;
|
|
88
|
-
private compileApi;
|
|
89
|
-
addApi<T extends RestApi>({ api, hostName, port, root, cors, injector, deserializeQueryParams, enableGetSchema, name, description, version, }: ImplementApiOptions<T>): Promise<{
|
|
90
|
-
shouldExec: (msg: OnRequest) => boolean;
|
|
91
|
-
onRequest: (msg: OnRequest) => Promise<void>;
|
|
92
|
-
}>;
|
|
93
|
-
shouldExecRequest(options: {
|
|
94
|
-
method?: Method;
|
|
95
|
-
url?: string;
|
|
96
|
-
rootApiPath: string;
|
|
97
|
-
supportedMethods: Method[];
|
|
98
|
-
}): boolean;
|
|
99
|
-
private getActionFromEndpoint;
|
|
100
|
-
private executeAction;
|
|
101
|
-
private onMessage;
|
|
102
|
-
private readonly serverManager;
|
|
103
|
-
}
|
|
104
|
-
//# sourceMappingURL=api-manager.d.ts.map
|
package/esm/api-manager.d.ts.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"api-manager.d.ts","sourceRoot":"","sources":["../src/api-manager.ts"],"names":[],"mappings":"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"}
|
package/esm/api-manager.js
DELETED
|
@@ -1,180 +0,0 @@
|
|
|
1
|
-
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
|
|
2
|
-
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
3
|
-
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
4
|
-
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
5
|
-
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
6
|
-
};
|
|
7
|
-
var __metadata = (this && this.__metadata) || function (k, v) {
|
|
8
|
-
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
9
|
-
};
|
|
10
|
-
import { IdentityContext } from '@furystack/core';
|
|
11
|
-
import { Injectable, Injected } from '@furystack/inject';
|
|
12
|
-
import { RequestError, deserializeQueryString } from '@furystack/rest';
|
|
13
|
-
import { PathHelper, usingAsync } from '@furystack/utils';
|
|
14
|
-
import { match } from 'path-to-regexp';
|
|
15
|
-
import { ErrorAction } from './actions/error-action.js';
|
|
16
|
-
import { NotFoundAction } from './actions/not-found-action.js';
|
|
17
|
-
import { addCorsHeaders } from './add-cors-header.js';
|
|
18
|
-
import { CreateGetSchemaAction } from './endpoint-generators/create-get-schema-action.js';
|
|
19
|
-
import { CreateGetOpenApiDocumentAction, CreateDeprecatedSwaggerRedirect, } from './endpoint-generators/create-get-openapi-document-action.js';
|
|
20
|
-
import { HttpUserContext } from './http-user-context.js';
|
|
21
|
-
import { readPostBody } from './read-post-body.js';
|
|
22
|
-
import { ServerManager } from './server-manager.js';
|
|
23
|
-
import './server-response-extensions.js';
|
|
24
|
-
let ApiManager = class ApiManager {
|
|
25
|
-
getSuportedMethods(api) {
|
|
26
|
-
return Object.keys(api);
|
|
27
|
-
}
|
|
28
|
-
compileApi(api, root) {
|
|
29
|
-
const supportedMethods = this.getSuportedMethods(api);
|
|
30
|
-
const compiledApi = {};
|
|
31
|
-
supportedMethods.forEach((method) => {
|
|
32
|
-
compiledApi[method] = [
|
|
33
|
-
...Object.entries(api[method]).map(([path, action]) => {
|
|
34
|
-
const fullPath = `/${PathHelper.normalize(PathHelper.joinPaths(root, path))}`;
|
|
35
|
-
const matcher = match(fullPath, { decode: decodeURIComponent });
|
|
36
|
-
return { method, fullPath, matcher, action: action };
|
|
37
|
-
}),
|
|
38
|
-
];
|
|
39
|
-
});
|
|
40
|
-
return compiledApi;
|
|
41
|
-
}
|
|
42
|
-
async addApi({ api, hostName, port, root, cors, injector, deserializeQueryParams, enableGetSchema, name, description, version, }) {
|
|
43
|
-
const extendedApi = enableGetSchema
|
|
44
|
-
? {
|
|
45
|
-
...api,
|
|
46
|
-
GET: {
|
|
47
|
-
...api.GET,
|
|
48
|
-
'/schema': CreateGetSchemaAction(api, name, description, version),
|
|
49
|
-
'/openapi.json': CreateGetOpenApiDocumentAction(api, name, description, version),
|
|
50
|
-
'/swagger.json': CreateDeprecatedSwaggerRedirect(api, name, description, version),
|
|
51
|
-
},
|
|
52
|
-
}
|
|
53
|
-
: api;
|
|
54
|
-
const supportedMethods = this.getSuportedMethods(extendedApi);
|
|
55
|
-
const rootApiPath = PathHelper.normalize(root);
|
|
56
|
-
const server = await this.serverManager.getOrCreate({ hostName, port });
|
|
57
|
-
const compiledApi = this.compileApi(extendedApi, root);
|
|
58
|
-
const serverApi = {
|
|
59
|
-
shouldExec: (msg) => this.shouldExecRequest({
|
|
60
|
-
...msg,
|
|
61
|
-
method: msg.req.method?.toUpperCase(),
|
|
62
|
-
rootApiPath,
|
|
63
|
-
supportedMethods,
|
|
64
|
-
url: PathHelper.normalize(msg.req.url || ''),
|
|
65
|
-
}),
|
|
66
|
-
onRequest: (msg) => this.onMessage({
|
|
67
|
-
...msg,
|
|
68
|
-
compiledApi,
|
|
69
|
-
rootApiPath,
|
|
70
|
-
port,
|
|
71
|
-
supportedMethods,
|
|
72
|
-
cors,
|
|
73
|
-
injector,
|
|
74
|
-
hostName,
|
|
75
|
-
deserializeQueryParams,
|
|
76
|
-
}),
|
|
77
|
-
};
|
|
78
|
-
server.apis.push(serverApi);
|
|
79
|
-
return serverApi;
|
|
80
|
-
}
|
|
81
|
-
shouldExecRequest(options) {
|
|
82
|
-
return options.method &&
|
|
83
|
-
options.url &&
|
|
84
|
-
(options.supportedMethods.includes(options.method) || options.method === 'OPTIONS') &&
|
|
85
|
-
PathHelper.matchesBaseUrl(options.url, options.rootApiPath)
|
|
86
|
-
? true
|
|
87
|
-
: false;
|
|
88
|
-
}
|
|
89
|
-
getActionFromEndpoint(compiledEndpoint, fullUrl, method) {
|
|
90
|
-
let resolvedParams;
|
|
91
|
-
const action = compiledEndpoint[method]?.find((route) => {
|
|
92
|
-
const result = route.matcher(fullUrl.pathname);
|
|
93
|
-
if (result) {
|
|
94
|
-
resolvedParams = result.params;
|
|
95
|
-
}
|
|
96
|
-
return result;
|
|
97
|
-
});
|
|
98
|
-
return (action && {
|
|
99
|
-
...action,
|
|
100
|
-
params: resolvedParams,
|
|
101
|
-
});
|
|
102
|
-
}
|
|
103
|
-
async executeAction({ injector, req, res, fullUrl, action, deserializeQueryParams, params, }) {
|
|
104
|
-
await usingAsync(injector.createChild({ owner: action }), async (i) => {
|
|
105
|
-
const httpUserContext = i.getInstance(HttpUserContext);
|
|
106
|
-
i.setExplicitInstance({
|
|
107
|
-
getCurrentUser: () => httpUserContext.getCurrentUser(req),
|
|
108
|
-
isAuthorized: (...roles) => httpUserContext.isAuthorized(req, ...roles),
|
|
109
|
-
isAuthenticated: () => httpUserContext.isAuthenticated(req),
|
|
110
|
-
}, IdentityContext);
|
|
111
|
-
try {
|
|
112
|
-
const actionResult = await action({
|
|
113
|
-
request: req,
|
|
114
|
-
response: res,
|
|
115
|
-
injector: i,
|
|
116
|
-
getBody: () => readPostBody(req),
|
|
117
|
-
headers: req.headers,
|
|
118
|
-
getQuery: () => deserializeQueryParams ? deserializeQueryParams(fullUrl.search) : deserializeQueryString(fullUrl.search),
|
|
119
|
-
getUrlParams: () => {
|
|
120
|
-
return params;
|
|
121
|
-
},
|
|
122
|
-
});
|
|
123
|
-
res.sendActionResult(actionResult);
|
|
124
|
-
}
|
|
125
|
-
catch (error) {
|
|
126
|
-
const errorActionResult = await ErrorAction({
|
|
127
|
-
request: req,
|
|
128
|
-
response: res,
|
|
129
|
-
injector: i,
|
|
130
|
-
getBody: async () => error,
|
|
131
|
-
});
|
|
132
|
-
res.sendActionResult(errorActionResult);
|
|
133
|
-
}
|
|
134
|
-
return;
|
|
135
|
-
});
|
|
136
|
-
}
|
|
137
|
-
async onMessage(options) {
|
|
138
|
-
const protocol = 'http://';
|
|
139
|
-
const host = `${options.hostName || ServerManager.DEFAULT_HOST}:${options.port}`;
|
|
140
|
-
const fullUrl = new URL(PathHelper.joinUrl(`${protocol}${host}`, options.req.url));
|
|
141
|
-
if (options.cors) {
|
|
142
|
-
addCorsHeaders(options.cors, options.req, options.res);
|
|
143
|
-
}
|
|
144
|
-
if (options.req.method === 'OPTIONS') {
|
|
145
|
-
options.res.writeHead(200);
|
|
146
|
-
options.res.end();
|
|
147
|
-
return;
|
|
148
|
-
}
|
|
149
|
-
let action;
|
|
150
|
-
try {
|
|
151
|
-
action = this.getActionFromEndpoint(options.compiledApi, fullUrl, options.req.method?.toUpperCase());
|
|
152
|
-
}
|
|
153
|
-
catch (error) {
|
|
154
|
-
const responseError = error instanceof URIError ? new RequestError('Failed to decode URL path parameter', 400) : error;
|
|
155
|
-
const errorActionResult = await ErrorAction({
|
|
156
|
-
request: options.req,
|
|
157
|
-
response: options.res,
|
|
158
|
-
injector: options.injector,
|
|
159
|
-
getBody: async () => responseError,
|
|
160
|
-
});
|
|
161
|
-
options.res.sendActionResult(errorActionResult);
|
|
162
|
-
return;
|
|
163
|
-
}
|
|
164
|
-
if (action) {
|
|
165
|
-
await this.executeAction({ ...options, ...action, fullUrl });
|
|
166
|
-
}
|
|
167
|
-
else {
|
|
168
|
-
options.res.sendActionResult(await NotFoundAction({ injector: options.injector, request: options.req, response: options.res }));
|
|
169
|
-
}
|
|
170
|
-
}
|
|
171
|
-
};
|
|
172
|
-
__decorate([
|
|
173
|
-
Injected(ServerManager),
|
|
174
|
-
__metadata("design:type", ServerManager)
|
|
175
|
-
], ApiManager.prototype, "serverManager", void 0);
|
|
176
|
-
ApiManager = __decorate([
|
|
177
|
-
Injectable({ lifetime: 'singleton' })
|
|
178
|
-
], ApiManager);
|
|
179
|
-
export { ApiManager };
|
|
180
|
-
//# sourceMappingURL=api-manager.js.map
|
package/esm/api-manager.js.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"api-manager.js","sourceRoot":"","sources":["../src/api-manager.ts"],"names":[],"mappings":"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"}
|