@feathersjs/express 5.0.0-pre.10 → 5.0.0-pre.16
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 +61 -0
- package/lib/authentication.d.ts +5 -6
- package/lib/authentication.js +26 -37
- package/lib/authentication.js.map +1 -1
- package/lib/declarations.d.ts +12 -10
- package/lib/index.d.ts +5 -5
- package/lib/index.js +42 -42
- package/lib/index.js.map +1 -1
- package/lib/rest.d.ts +9 -9
- package/lib/rest.js +58 -73
- package/lib/rest.js.map +1 -1
- package/package.json +17 -16
- package/src/authentication.ts +36 -46
- package/src/declarations.ts +24 -22
- package/src/handlers.ts +4 -4
- package/src/index.ts +35 -30
- package/src/rest.ts +78 -87
package/CHANGELOG.md
CHANGED
|
@@ -3,6 +3,67 @@
|
|
|
3
3
|
All notable changes to this project will be documented in this file.
|
|
4
4
|
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
|
5
5
|
|
|
6
|
+
# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12)
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
### Features
|
|
10
|
+
|
|
11
|
+
* **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159))
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27)
|
|
18
|
+
|
|
19
|
+
|
|
20
|
+
### Bug Fixes
|
|
21
|
+
|
|
22
|
+
* missing express types for Request, Response ([#2498](https://github.com/feathersjs/feathers/issues/2498)) ([ee67131](https://github.com/feathersjs/feathers/commit/ee67131bbaa24c54d3d781bdf8820015759ac488))
|
|
23
|
+
* **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110))
|
|
24
|
+
|
|
25
|
+
|
|
26
|
+
### Features
|
|
27
|
+
|
|
28
|
+
* **core:** add `context.http` and move `statusCode` there ([#2496](https://github.com/feathersjs/feathers/issues/2496)) ([b701bf7](https://github.com/feathersjs/feathers/commit/b701bf77fb83048aa1dffa492b3d77dd53f7b72b))
|
|
29
|
+
* **core:** Improve legacy hooks integration ([08c8b40](https://github.com/feathersjs/feathers/commit/08c8b40999bf3889c61a4d4fad97a2c4f78bafc9))
|
|
30
|
+
|
|
31
|
+
|
|
32
|
+
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13)
|
|
36
|
+
|
|
37
|
+
**Note:** Version bump only for package @feathersjs/express
|
|
38
|
+
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
|
|
42
|
+
|
|
43
|
+
# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13)
|
|
44
|
+
|
|
45
|
+
**Note:** Version bump only for package @feathersjs/express
|
|
46
|
+
|
|
47
|
+
|
|
48
|
+
|
|
49
|
+
|
|
50
|
+
|
|
51
|
+
# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12)
|
|
52
|
+
|
|
53
|
+
**Note:** Version bump only for package @feathersjs/express
|
|
54
|
+
|
|
55
|
+
|
|
56
|
+
|
|
57
|
+
|
|
58
|
+
|
|
59
|
+
# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06)
|
|
60
|
+
|
|
61
|
+
**Note:** Version bump only for package @feathersjs/express
|
|
62
|
+
|
|
63
|
+
|
|
64
|
+
|
|
65
|
+
|
|
66
|
+
|
|
6
67
|
# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19)
|
|
7
68
|
|
|
8
69
|
**Note:** Version bump only for package @feathersjs/express
|
package/lib/authentication.d.ts
CHANGED
|
@@ -1,8 +1,7 @@
|
|
|
1
|
-
import {
|
|
2
|
-
declare type
|
|
1
|
+
import { RequestHandler } from 'express';
|
|
2
|
+
export declare type AuthenticationSettings = {
|
|
3
3
|
service?: string;
|
|
4
|
-
strategies
|
|
4
|
+
strategies?: string[];
|
|
5
5
|
};
|
|
6
|
-
export declare function parseAuthentication(settings?:
|
|
7
|
-
export declare function authenticate(
|
|
8
|
-
export {};
|
|
6
|
+
export declare function parseAuthentication(settings?: AuthenticationSettings): RequestHandler;
|
|
7
|
+
export declare function authenticate(settings: string | AuthenticationSettings, ...strategies: string[]): RequestHandler;
|
package/lib/authentication.js
CHANGED
|
@@ -2,55 +2,44 @@
|
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.authenticate = exports.parseAuthentication = void 0;
|
|
4
4
|
const commons_1 = require("@feathersjs/commons");
|
|
5
|
-
const
|
|
5
|
+
const authentication_1 = require("@feathersjs/authentication");
|
|
6
6
|
const debug = (0, commons_1.createDebug)('@feathersjs/express/authentication');
|
|
7
|
-
const
|
|
8
|
-
|
|
9
|
-
|
|
7
|
+
const toHandler = (func) => {
|
|
8
|
+
return (req, res, next) => func(req, res, next).catch(error => next(error));
|
|
9
|
+
};
|
|
10
10
|
function parseAuthentication(settings = {}) {
|
|
11
|
-
return
|
|
11
|
+
return toHandler(async (req, res, next) => {
|
|
12
|
+
var _a;
|
|
12
13
|
const app = req.app;
|
|
13
|
-
const service = app.defaultAuthentication ?
|
|
14
|
-
if (service
|
|
14
|
+
const service = (_a = app.defaultAuthentication) === null || _a === void 0 ? void 0 : _a.call(app, settings.service);
|
|
15
|
+
if (!service) {
|
|
15
16
|
return next();
|
|
16
17
|
}
|
|
17
18
|
const config = service.configuration;
|
|
18
|
-
const authStrategies = config.parseStrategies || config.authStrategies || [];
|
|
19
|
+
const authStrategies = settings.strategies || config.parseStrategies || config.authStrategies || [];
|
|
19
20
|
if (authStrategies.length === 0) {
|
|
20
21
|
debug('No `authStrategies` or `parseStrategies` found in authentication configuration');
|
|
21
22
|
return next();
|
|
22
23
|
}
|
|
23
|
-
service.parse(req, res, ...authStrategies)
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
});
|
|
31
|
-
}
|
|
32
|
-
next();
|
|
33
|
-
}).catch(next);
|
|
34
|
-
};
|
|
24
|
+
const authentication = await service.parse(req, res, ...authStrategies);
|
|
25
|
+
if (authentication) {
|
|
26
|
+
debug('Parsed authentication from HTTP header', authentication);
|
|
27
|
+
req.feathers = { ...req.feathers, authentication };
|
|
28
|
+
}
|
|
29
|
+
return next();
|
|
30
|
+
});
|
|
35
31
|
}
|
|
36
32
|
exports.parseAuthentication = parseAuthentication;
|
|
37
|
-
function authenticate(
|
|
38
|
-
const
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
service.authenticate(authentication, req.feathers, ...settings.strategies)
|
|
48
|
-
.then((authResult) => {
|
|
49
|
-
debug('Merging request with', authResult);
|
|
50
|
-
(0, lodash_1.merge)(req, authResult);
|
|
51
|
-
next();
|
|
52
|
-
}).catch(next);
|
|
53
|
-
};
|
|
33
|
+
function authenticate(settings, ...strategies) {
|
|
34
|
+
const hook = (0, authentication_1.authenticate)(settings, ...strategies);
|
|
35
|
+
return toHandler(async (req, _res, next) => {
|
|
36
|
+
const app = req.app;
|
|
37
|
+
const params = req.feathers;
|
|
38
|
+
const context = { app, params };
|
|
39
|
+
await hook(context);
|
|
40
|
+
req.feathers = context.params;
|
|
41
|
+
return next();
|
|
42
|
+
});
|
|
54
43
|
}
|
|
55
44
|
exports.authenticate = authenticate;
|
|
56
45
|
//# sourceMappingURL=authentication.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"authentication.js","sourceRoot":"","sources":["../src/authentication.ts"],"names":[],"mappings":";;;
|
|
1
|
+
{"version":3,"file":"authentication.js","sourceRoot":"","sources":["../src/authentication.ts"],"names":[],"mappings":";;;AAEA,iDAAkD;AAClD,+DAA8E;AAI9E,MAAM,KAAK,GAAG,IAAA,qBAAW,EAAC,oCAAoC,CAAC,CAAC;AAEhE,MAAM,SAAS,GAAG,CAAC,IAAsE,EAAkB,EAAE;IAC3G,OAAO,CAAC,GAAG,EAAE,GAAG,EAAE,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,IAAI,CAAC,CAAC,KAAK,CAAC,KAAK,CAAC,EAAE,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC;AAC9E,CAAC,CAAC;AAOF,SAAgB,mBAAmB,CAAE,WAAmC,EAAE;IACxE,OAAO,SAAS,CAAC,KAAK,EAAE,GAAG,EAAE,GAAG,EAAE,IAAI,EAAE,EAAE;;QACxC,MAAM,GAAG,GAAG,GAAG,CAAC,GAAyB,CAAC;QAC1C,MAAM,OAAO,GAAG,MAAA,GAAG,CAAC,qBAAqB,+CAAzB,GAAG,EAAyB,QAAQ,CAAC,OAAO,CAAC,CAAC;QAE9D,IAAI,CAAC,OAAO,EAAE;YACZ,OAAO,IAAI,EAAE,CAAC;SACf;QAED,MAAM,MAAM,GAAG,OAAO,CAAC,aAAa,CAAC;QACrC,MAAM,cAAc,GAAG,QAAQ,CAAC,UAAU,IAAI,MAAM,CAAC,eAAe,IAAI,MAAM,CAAC,cAAc,IAAI,EAAE,CAAC;QAEpG,IAAI,cAAc,CAAC,MAAM,KAAK,CAAC,EAAE;YAC/B,KAAK,CAAC,gFAAgF,CAAC,CAAC;YACxF,OAAO,IAAI,EAAE,CAAC;SACf;QAED,MAAM,cAAc,GAAG,MAAM,OAAO,CAAC,KAAK,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,cAAc,CAAC,CAAA;QAEvE,IAAI,cAAc,EAAE;YAClB,KAAK,CAAC,wCAAwC,EAAE,cAAc,CAAC,CAAC;YAChE,GAAG,CAAC,QAAQ,GAAG,EAAE,GAAG,GAAG,CAAC,QAAQ,EAAE,cAAc,EAAE,CAAC;SACpD;QAED,OAAO,IAAI,EAAE,CAAC;IAChB,CAAC,CAAC,CAAC;AACL,CAAC;AA1BD,kDA0BC;AAED,SAAgB,YAAY,CAAE,QAAyC,EAAE,GAAG,UAAoB;IAC9F,MAAM,IAAI,GAAG,IAAA,6BAAgB,EAAC,QAAQ,EAAE,GAAG,UAAU,CAAC,CAAC;IAEvD,OAAO,SAAS,CAAC,KAAK,EAAE,GAAG,EAAE,IAAI,EAAE,IAAI,EAAE,EAAE;QACzC,MAAM,GAAG,GAAG,GAAG,CAAC,GAAyB,CAAC;QAC1C,MAAM,MAAM,GAAG,GAAG,CAAC,QAAQ,CAAC;QAC5B,MAAM,OAAO,GAAG,EAAE,GAAG,EAAE,MAAM,EAAwB,CAAC;QAEtD,MAAM,IAAI,CAAC,OAAO,CAAC,CAAC;QAEpB,GAAG,CAAC,QAAQ,GAAG,OAAO,CAAC,MAAM,CAAC;QAE9B,OAAO,IAAI,EAAE,CAAC;IAChB,CAAC,CAAC,CAAC;AACL,CAAC;AAdD,oCAcC"}
|
package/lib/declarations.d.ts
CHANGED
|
@@ -1,39 +1,41 @@
|
|
|
1
1
|
/// <reference types="node" />
|
|
2
2
|
import http from 'http';
|
|
3
3
|
import express, { Express } from 'express';
|
|
4
|
-
import { Application as FeathersApplication, Params as FeathersParams, HookContext, ServiceMethods, ServiceInterface } from '@feathersjs/feathers';
|
|
5
|
-
interface ExpressUseHandler<T,
|
|
6
|
-
<L extends keyof
|
|
4
|
+
import { Application as FeathersApplication, Params as FeathersParams, HookContext, ServiceMethods, ServiceInterface, RouteLookup } from '@feathersjs/feathers';
|
|
5
|
+
interface ExpressUseHandler<T, Services> {
|
|
6
|
+
<L extends keyof Services & string>(path: L, ...middlewareOrService: (Express | express.RequestHandler | (keyof any extends keyof Services ? ServiceInterface : Services[L]))[]): T;
|
|
7
7
|
(path: string | RegExp, ...expressHandlers: express.RequestHandler[]): T;
|
|
8
8
|
(...expressHandlers: express.RequestHandler[]): T;
|
|
9
9
|
(handler: Express | express.ErrorRequestHandler): T;
|
|
10
10
|
}
|
|
11
|
-
export interface ExpressOverrides<
|
|
11
|
+
export interface ExpressOverrides<Services> {
|
|
12
12
|
listen(port: number, hostname: string, backlog: number, callback?: () => void): Promise<http.Server>;
|
|
13
13
|
listen(port: number, hostname: string, callback?: () => void): Promise<http.Server>;
|
|
14
14
|
listen(port: number | string | any, callback?: () => void): Promise<http.Server>;
|
|
15
15
|
listen(callback?: () => void): Promise<http.Server>;
|
|
16
|
-
use: ExpressUseHandler<this,
|
|
16
|
+
use: ExpressUseHandler<this, Services>;
|
|
17
17
|
}
|
|
18
|
-
export declare type Application<
|
|
18
|
+
export declare type Application<Services = any, Settings = any> = Omit<Express, 'listen' | 'use'> & FeathersApplication<Services, Settings> & ExpressOverrides<Services>;
|
|
19
19
|
declare module '@feathersjs/feathers/lib/declarations' {
|
|
20
20
|
interface ServiceOptions {
|
|
21
|
-
|
|
22
|
-
before
|
|
23
|
-
after
|
|
21
|
+
express?: {
|
|
22
|
+
before?: express.RequestHandler[];
|
|
23
|
+
after?: express.RequestHandler[];
|
|
24
|
+
composed?: express.RequestHandler;
|
|
24
25
|
};
|
|
25
26
|
}
|
|
26
27
|
}
|
|
27
28
|
declare module 'express-serve-static-core' {
|
|
28
29
|
interface Request {
|
|
29
30
|
feathers?: Partial<FeathersParams>;
|
|
31
|
+
lookup?: RouteLookup;
|
|
30
32
|
}
|
|
31
33
|
interface Response {
|
|
32
34
|
data?: any;
|
|
33
35
|
hook?: HookContext;
|
|
34
36
|
}
|
|
35
37
|
interface IRouterMatcher<T> {
|
|
36
|
-
<P extends Params = ParamsDictionary, ResBody = any, ReqBody = any>(path: PathParams, ...handlers: (RequestHandler<P, ResBody, ReqBody> | Partial<ServiceMethods
|
|
38
|
+
<P extends Params = ParamsDictionary, ResBody = any, ReqBody = any>(path: PathParams, ...handlers: (RequestHandler<P, ResBody, ReqBody> | Partial<ServiceMethods> | Application)[]): T;
|
|
37
39
|
}
|
|
38
40
|
}
|
|
39
41
|
export {};
|
package/lib/index.d.ts
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
|
-
import
|
|
1
|
+
import { Express } from 'express';
|
|
2
2
|
import { Application as FeathersApplication } from '@feathersjs/feathers';
|
|
3
3
|
import { Application } from './declarations';
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
export { _static as static, json, raw, text, urlencoded, query, errorHandler, notFound, express as original, authenticate, parseAuthentication };
|
|
7
|
-
export * from './rest';
|
|
4
|
+
export { default as original, static, static as serveStatic, json, raw, text, urlencoded, query } from 'express';
|
|
5
|
+
export * from './authentication';
|
|
8
6
|
export * from './declarations';
|
|
7
|
+
export * from './handlers';
|
|
8
|
+
export * from './rest';
|
|
9
9
|
export default function feathersExpress<S = any, C = any>(feathersApp?: FeathersApplication<S, C>, expressApp?: Express): Application<S, C>;
|
package/lib/index.js
CHANGED
|
@@ -6,41 +6,31 @@ var __createBinding = (this && this.__createBinding) || (Object.create ? (functi
|
|
|
6
6
|
if (k2 === undefined) k2 = k;
|
|
7
7
|
o[k2] = m[k];
|
|
8
8
|
}));
|
|
9
|
-
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
10
|
-
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
11
|
-
}) : function(o, v) {
|
|
12
|
-
o["default"] = v;
|
|
13
|
-
});
|
|
14
|
-
var __importStar = (this && this.__importStar) || function (mod) {
|
|
15
|
-
if (mod && mod.__esModule) return mod;
|
|
16
|
-
var result = {};
|
|
17
|
-
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
|
|
18
|
-
__setModuleDefault(result, mod);
|
|
19
|
-
return result;
|
|
20
|
-
};
|
|
21
9
|
var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
22
10
|
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
23
11
|
};
|
|
12
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
13
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
14
|
+
};
|
|
24
15
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
25
|
-
exports.
|
|
26
|
-
const express_1 =
|
|
27
|
-
exports.original = express_1.default;
|
|
28
|
-
Object.defineProperty(exports, "static", { enumerable: true, get: function () { return express_1.static; } });
|
|
29
|
-
Object.defineProperty(exports, "json", { enumerable: true, get: function () { return express_1.json; } });
|
|
30
|
-
Object.defineProperty(exports, "raw", { enumerable: true, get: function () { return express_1.raw; } });
|
|
31
|
-
Object.defineProperty(exports, "text", { enumerable: true, get: function () { return express_1.text; } });
|
|
32
|
-
Object.defineProperty(exports, "urlencoded", { enumerable: true, get: function () { return express_1.urlencoded; } });
|
|
33
|
-
Object.defineProperty(exports, "query", { enumerable: true, get: function () { return express_1.query; } });
|
|
16
|
+
exports.query = exports.urlencoded = exports.text = exports.raw = exports.json = exports.serveStatic = exports.static = exports.original = void 0;
|
|
17
|
+
const express_1 = __importDefault(require("express"));
|
|
34
18
|
const feathers_1 = require("@feathersjs/feathers");
|
|
19
|
+
const transport_commons_1 = require("@feathersjs/transport-commons");
|
|
35
20
|
const commons_1 = require("@feathersjs/commons");
|
|
36
|
-
|
|
37
|
-
Object.defineProperty(exports, "
|
|
38
|
-
Object.defineProperty(exports, "
|
|
39
|
-
|
|
40
|
-
Object.defineProperty(exports, "
|
|
41
|
-
Object.defineProperty(exports, "
|
|
42
|
-
|
|
21
|
+
var express_2 = require("express");
|
|
22
|
+
Object.defineProperty(exports, "original", { enumerable: true, get: function () { return __importDefault(express_2).default; } });
|
|
23
|
+
Object.defineProperty(exports, "static", { enumerable: true, get: function () { return express_2.static; } });
|
|
24
|
+
Object.defineProperty(exports, "serveStatic", { enumerable: true, get: function () { return express_2.static; } });
|
|
25
|
+
Object.defineProperty(exports, "json", { enumerable: true, get: function () { return express_2.json; } });
|
|
26
|
+
Object.defineProperty(exports, "raw", { enumerable: true, get: function () { return express_2.raw; } });
|
|
27
|
+
Object.defineProperty(exports, "text", { enumerable: true, get: function () { return express_2.text; } });
|
|
28
|
+
Object.defineProperty(exports, "urlencoded", { enumerable: true, get: function () { return express_2.urlencoded; } });
|
|
29
|
+
Object.defineProperty(exports, "query", { enumerable: true, get: function () { return express_2.query; } });
|
|
30
|
+
__exportStar(require("./authentication"), exports);
|
|
43
31
|
__exportStar(require("./declarations"), exports);
|
|
32
|
+
__exportStar(require("./handlers"), exports);
|
|
33
|
+
__exportStar(require("./rest"), exports);
|
|
44
34
|
const debug = (0, commons_1.createDebug)('@feathersjs/express');
|
|
45
35
|
function feathersExpress(feathersApp, expressApp = (0, express_1.default)()) {
|
|
46
36
|
if (!feathersApp) {
|
|
@@ -49,9 +39,10 @@ function feathersExpress(feathersApp, expressApp = (0, express_1.default)()) {
|
|
|
49
39
|
if (typeof feathersApp.setup !== 'function') {
|
|
50
40
|
throw new Error('@feathersjs/express requires a valid Feathers application instance');
|
|
51
41
|
}
|
|
52
|
-
const
|
|
53
|
-
|
|
54
|
-
const
|
|
42
|
+
const app = expressApp;
|
|
43
|
+
const { use: expressUse, listen: expressListen } = expressApp;
|
|
44
|
+
const feathersUse = feathersApp.use;
|
|
45
|
+
Object.assign(app, {
|
|
55
46
|
use(location, ...rest) {
|
|
56
47
|
let service;
|
|
57
48
|
let options = {};
|
|
@@ -77,37 +68,46 @@ function feathersExpress(feathersApp, expressApp = (0, express_1.default)()) {
|
|
|
77
68
|
// Check for service (any object with at least one service method)
|
|
78
69
|
if (hasMethod(['handle', 'set']) || !hasMethod(feathers_1.defaultServiceMethods)) {
|
|
79
70
|
debug('Passing app.use call to Express app');
|
|
80
|
-
return
|
|
71
|
+
return expressUse.call(this, location, ...rest);
|
|
81
72
|
}
|
|
82
73
|
debug('Registering service with middleware', middleware);
|
|
83
74
|
// Since this is a service, call Feathers `.use`
|
|
84
|
-
|
|
75
|
+
feathersUse.call(this, location, service, {
|
|
85
76
|
...options,
|
|
86
|
-
middleware
|
|
77
|
+
express: middleware
|
|
87
78
|
});
|
|
88
79
|
return this;
|
|
89
80
|
},
|
|
90
81
|
async listen(...args) {
|
|
91
|
-
const server =
|
|
82
|
+
const server = expressListen.call(this, ...args);
|
|
92
83
|
await this.setup(server);
|
|
93
84
|
debug('Feathers application listening');
|
|
94
85
|
return server;
|
|
95
86
|
}
|
|
87
|
+
});
|
|
88
|
+
const appDescriptors = {
|
|
89
|
+
...Object.getOwnPropertyDescriptors(Object.getPrototypeOf(app)),
|
|
90
|
+
...Object.getOwnPropertyDescriptors(app)
|
|
96
91
|
};
|
|
97
|
-
const
|
|
92
|
+
const newDescriptors = {
|
|
98
93
|
...Object.getOwnPropertyDescriptors(Object.getPrototypeOf(feathersApp)),
|
|
99
94
|
...Object.getOwnPropertyDescriptors(feathersApp)
|
|
100
95
|
};
|
|
101
96
|
// Copy all non-existing properties (including non-enumerables)
|
|
102
97
|
// that don't already exist on the Express app
|
|
103
|
-
Object.keys(
|
|
104
|
-
const
|
|
105
|
-
const
|
|
106
|
-
if (
|
|
107
|
-
Object.defineProperty(expressApp, prop,
|
|
98
|
+
Object.keys(newDescriptors).forEach(prop => {
|
|
99
|
+
const appProp = appDescriptors[prop];
|
|
100
|
+
const newProp = newDescriptors[prop];
|
|
101
|
+
if (appProp === undefined && newProp !== undefined) {
|
|
102
|
+
Object.defineProperty(expressApp, prop, newProp);
|
|
108
103
|
}
|
|
109
104
|
});
|
|
110
|
-
|
|
105
|
+
app.configure((0, transport_commons_1.routing)());
|
|
106
|
+
app.use((req, _res, next) => {
|
|
107
|
+
req.feathers = { ...req.feathers, provider: 'rest' };
|
|
108
|
+
return next();
|
|
109
|
+
});
|
|
110
|
+
return app;
|
|
111
111
|
}
|
|
112
112
|
exports.default = feathersExpress;
|
|
113
113
|
if (typeof module !== 'undefined') {
|
package/lib/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
|
package/lib/rest.d.ts
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
4
|
-
export declare
|
|
5
|
-
export declare
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
export declare
|
|
1
|
+
import { RequestHandler } from 'express';
|
|
2
|
+
import { AuthenticationSettings } from './authentication';
|
|
3
|
+
import { Application } from './declarations';
|
|
4
|
+
export declare const formatter: RequestHandler;
|
|
5
|
+
export declare type RestOptions = {
|
|
6
|
+
formatter?: RequestHandler;
|
|
7
|
+
authentication?: AuthenticationSettings;
|
|
8
|
+
};
|
|
9
|
+
export declare const rest: (options?: RestOptions | RequestHandler) => (app: Application) => void;
|
package/lib/rest.js
CHANGED
|
@@ -1,22 +1,56 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.rest = exports.
|
|
3
|
+
exports.rest = exports.formatter = void 0;
|
|
4
|
+
const express_1 = require("express");
|
|
4
5
|
const errors_1 = require("@feathersjs/errors");
|
|
5
6
|
const commons_1 = require("@feathersjs/commons");
|
|
6
7
|
const transport_commons_1 = require("@feathersjs/transport-commons");
|
|
7
8
|
const feathers_1 = require("@feathersjs/feathers");
|
|
8
|
-
const express_1 = require("express");
|
|
9
9
|
const authentication_1 = require("./authentication");
|
|
10
10
|
const debug = (0, commons_1.createDebug)('@feathersjs/express/rest');
|
|
11
|
-
const
|
|
12
|
-
req.
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
11
|
+
const toHandler = (func) => {
|
|
12
|
+
return (req, res, next) => func(req, res, next).catch(error => next(error));
|
|
13
|
+
};
|
|
14
|
+
const serviceMiddleware = () => {
|
|
15
|
+
return toHandler(async (req, res, next) => {
|
|
16
|
+
const { query, headers, path, body: data, method: httpMethod } = req;
|
|
17
|
+
const methodOverride = req.headers[transport_commons_1.http.METHOD_HEADER];
|
|
18
|
+
const { service, params: { __id: id = null, ...route } = {} } = req.lookup;
|
|
19
|
+
const method = transport_commons_1.http.getServiceMethod(httpMethod, id, methodOverride);
|
|
20
|
+
const { methods } = (0, feathers_1.getServiceOptions)(service);
|
|
21
|
+
debug(`Found service for path ${path}, attempting to run '${method}' service method`);
|
|
22
|
+
if (!methods.includes(method) || feathers_1.defaultServiceMethods.includes(methodOverride)) {
|
|
23
|
+
const error = new errors_1.MethodNotAllowed(`Method \`${method}\` is not supported by this endpoint.`);
|
|
24
|
+
res.statusCode = error.code;
|
|
25
|
+
throw error;
|
|
26
|
+
}
|
|
27
|
+
const createArguments = transport_commons_1.http.argumentsFor[method] || transport_commons_1.http.argumentsFor.default;
|
|
28
|
+
const params = { query, headers, route, ...req.feathers };
|
|
29
|
+
const args = createArguments({ id, data, params });
|
|
30
|
+
const contextBase = (0, feathers_1.createContext)(service, method, { http: {} });
|
|
31
|
+
res.hook = contextBase;
|
|
32
|
+
const context = await service[method](...args, contextBase);
|
|
33
|
+
res.hook = context;
|
|
34
|
+
const result = transport_commons_1.http.getData(context);
|
|
35
|
+
const statusCode = transport_commons_1.http.getStatusCode(context, result);
|
|
36
|
+
res.data = result;
|
|
37
|
+
res.statusCode = statusCode;
|
|
38
|
+
return next();
|
|
39
|
+
});
|
|
40
|
+
};
|
|
41
|
+
const servicesMiddleware = () => {
|
|
42
|
+
return toHandler(async (req, res, next) => {
|
|
43
|
+
const app = req.app;
|
|
44
|
+
const lookup = app.lookup(req.path);
|
|
45
|
+
if (!lookup) {
|
|
46
|
+
return next();
|
|
47
|
+
}
|
|
48
|
+
req.lookup = lookup;
|
|
49
|
+
const options = (0, feathers_1.getServiceOptions)(lookup.service);
|
|
50
|
+
const middleware = options.express.composed;
|
|
51
|
+
return middleware(req, res, next);
|
|
52
|
+
});
|
|
18
53
|
};
|
|
19
|
-
exports.feathersParams = feathersParams;
|
|
20
54
|
const formatter = (_req, res, next) => {
|
|
21
55
|
if (res.data === undefined) {
|
|
22
56
|
return next();
|
|
@@ -28,73 +62,24 @@ const formatter = (_req, res, next) => {
|
|
|
28
62
|
});
|
|
29
63
|
};
|
|
30
64
|
exports.formatter = formatter;
|
|
31
|
-
const
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
const params = { query, route, ...req.feathers };
|
|
37
|
-
const context = await callback(req, res, { id, data, params });
|
|
38
|
-
const result = transport_commons_1.http.getData(context);
|
|
39
|
-
res.data = result;
|
|
40
|
-
res.status(transport_commons_1.http.getStatusCode(context, result));
|
|
41
|
-
next();
|
|
42
|
-
}
|
|
43
|
-
catch (error) {
|
|
44
|
-
next(error);
|
|
45
|
-
}
|
|
46
|
-
};
|
|
47
|
-
exports.serviceMiddleware = serviceMiddleware;
|
|
48
|
-
const serviceMethodHandler = (service, methodName, getArgs, headerOverride) => (0, exports.serviceMiddleware)(async (req, res, options) => {
|
|
49
|
-
const methodOverride = typeof headerOverride === 'string' && req.headers[headerOverride];
|
|
50
|
-
const method = methodOverride ? methodOverride : methodName;
|
|
51
|
-
const { methods } = (0, feathers_1.getServiceOptions)(service);
|
|
52
|
-
if (!methods.includes(method) || feathers_1.defaultServiceMethods.includes(methodOverride)) {
|
|
53
|
-
res.status(transport_commons_1.http.statusCodes.methodNotAllowed);
|
|
54
|
-
throw new errors_1.MethodNotAllowed(`Method \`${method}\` is not supported by this endpoint.`);
|
|
55
|
-
}
|
|
56
|
-
const args = getArgs(options);
|
|
57
|
-
const context = (0, feathers_1.createContext)(service, method);
|
|
58
|
-
res.hook = context;
|
|
59
|
-
return service[method](...args, context);
|
|
60
|
-
});
|
|
61
|
-
exports.serviceMethodHandler = serviceMethodHandler;
|
|
62
|
-
function rest(handler = exports.formatter) {
|
|
63
|
-
return function (app) {
|
|
65
|
+
const rest = (options) => {
|
|
66
|
+
options = typeof options === 'function' ? { formatter: options } : options || {};
|
|
67
|
+
const formatterMiddleware = options.formatter || exports.formatter;
|
|
68
|
+
const authenticationOptions = options.authentication;
|
|
69
|
+
return (app) => {
|
|
64
70
|
if (typeof app.route !== 'function') {
|
|
65
71
|
throw new Error('@feathersjs/express/rest needs an Express compatible app.');
|
|
66
72
|
}
|
|
67
|
-
app.use(
|
|
68
|
-
app.use((
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
const
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
}
|
|
76
|
-
const baseUri = `/${path}`;
|
|
77
|
-
const find = (0, exports.serviceMethodHandler)(service, 'find', transport_commons_1.http.argumentsFor.find);
|
|
78
|
-
const get = (0, exports.serviceMethodHandler)(service, 'get', transport_commons_1.http.argumentsFor.get);
|
|
79
|
-
const create = (0, exports.serviceMethodHandler)(service, 'create', transport_commons_1.http.argumentsFor.create, transport_commons_1.http.METHOD_HEADER);
|
|
80
|
-
const update = (0, exports.serviceMethodHandler)(service, 'update', transport_commons_1.http.argumentsFor.update);
|
|
81
|
-
const patch = (0, exports.serviceMethodHandler)(service, 'patch', transport_commons_1.http.argumentsFor.patch);
|
|
82
|
-
const remove = (0, exports.serviceMethodHandler)(service, 'remove', transport_commons_1.http.argumentsFor.remove);
|
|
83
|
-
debug(`Adding REST provider for service \`${path}\` at base route \`${baseUri}\``);
|
|
84
|
-
const idRoute = '/:__feathersId';
|
|
85
|
-
const serviceRouter = (0, express_1.Router)({ mergeParams: true })
|
|
86
|
-
.get('/', find)
|
|
87
|
-
.post('/', create)
|
|
88
|
-
.get(idRoute, get)
|
|
89
|
-
.put('/', update)
|
|
90
|
-
.put(idRoute, update)
|
|
91
|
-
.patch('/', patch)
|
|
92
|
-
.patch(idRoute, patch)
|
|
93
|
-
.delete('/', remove)
|
|
94
|
-
.delete(idRoute, remove);
|
|
95
|
-
app.use(baseUri, ...before, serviceRouter, ...after);
|
|
73
|
+
app.use((0, authentication_1.parseAuthentication)(authenticationOptions));
|
|
74
|
+
app.use(servicesMiddleware());
|
|
75
|
+
app.mixins.push((_service, _path, options) => {
|
|
76
|
+
const { express: { before = [], after = [] } = {} } = options;
|
|
77
|
+
const middlewares = [].concat(before, serviceMiddleware(), after, formatterMiddleware);
|
|
78
|
+
const middleware = (0, express_1.Router)().use(middlewares);
|
|
79
|
+
options.express || (options.express = {});
|
|
80
|
+
options.express.composed = middleware;
|
|
96
81
|
});
|
|
97
82
|
};
|
|
98
|
-
}
|
|
83
|
+
};
|
|
99
84
|
exports.rest = rest;
|
|
100
85
|
//# sourceMappingURL=rest.js.map
|
package/lib/rest.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"rest.js","sourceRoot":"","sources":["../src/rest.ts"],"names":[],"mappings":";;;AAAA,+CAAsD;
|
|
1
|
+
{"version":3,"file":"rest.js","sourceRoot":"","sources":["../src/rest.ts"],"names":[],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@feathersjs/express",
|
|
3
3
|
"description": "Feathers Express framework bindings and REST provider",
|
|
4
|
-
"version": "5.0.0-pre.
|
|
4
|
+
"version": "5.0.0-pre.16",
|
|
5
5
|
"homepage": "https://feathersjs.com",
|
|
6
6
|
"main": "lib/",
|
|
7
7
|
"keywords": [
|
|
@@ -49,26 +49,27 @@
|
|
|
49
49
|
"access": "public"
|
|
50
50
|
},
|
|
51
51
|
"dependencies": {
|
|
52
|
-
"@feathersjs/
|
|
53
|
-
"@feathersjs/
|
|
54
|
-
"@feathersjs/
|
|
52
|
+
"@feathersjs/authentication": "^5.0.0-pre.16",
|
|
53
|
+
"@feathersjs/commons": "^5.0.0-pre.16",
|
|
54
|
+
"@feathersjs/errors": "^5.0.0-pre.16",
|
|
55
|
+
"@feathersjs/feathers": "^5.0.0-pre.16",
|
|
56
|
+
"@feathersjs/transport-commons": "^5.0.0-pre.16",
|
|
55
57
|
"@types/express": "^4.17.13",
|
|
56
|
-
"express": "^4.17.
|
|
57
|
-
"
|
|
58
|
+
"@types/express-serve-static-core": "^4.17.27",
|
|
59
|
+
"express": "^4.17.2"
|
|
58
60
|
},
|
|
59
61
|
"devDependencies": {
|
|
60
|
-
"@feathersjs/authentication": "^5.0.0-pre.
|
|
61
|
-
"@feathersjs/
|
|
62
|
-
"@
|
|
63
|
-
"@feathersjs/tests": "^5.0.0-pre.10",
|
|
62
|
+
"@feathersjs/authentication-local": "^5.0.0-pre.16",
|
|
63
|
+
"@feathersjs/tests": "^5.0.0-pre.16",
|
|
64
|
+
"@types/lodash": "^4.14.178",
|
|
64
65
|
"@types/mocha": "^9.0.0",
|
|
65
|
-
"@types/node": "^
|
|
66
|
-
"axios": "^0.
|
|
66
|
+
"@types/node": "^17.0.5",
|
|
67
|
+
"axios": "^0.24.0",
|
|
67
68
|
"lodash": "^4.17.21",
|
|
68
|
-
"mocha": "^9.1.
|
|
69
|
+
"mocha": "^9.1.3",
|
|
69
70
|
"shx": "^0.3.3",
|
|
70
|
-
"ts-node": "^10.
|
|
71
|
-
"typescript": "^4.4
|
|
71
|
+
"ts-node": "^10.4.0",
|
|
72
|
+
"typescript": "^4.5.4"
|
|
72
73
|
},
|
|
73
|
-
"gitHead": "
|
|
74
|
+
"gitHead": "f0cd227a82d159b528193bd33747c97684a48773"
|
|
74
75
|
}
|
package/src/authentication.ts
CHANGED
|
@@ -1,71 +1,61 @@
|
|
|
1
|
+
import { RequestHandler, Request, Response } from 'express';
|
|
2
|
+
import { HookContext } from '@feathersjs/feathers';
|
|
1
3
|
import { createDebug } from '@feathersjs/commons';
|
|
2
|
-
import {
|
|
3
|
-
|
|
4
|
+
import { authenticate as AuthenticateHook } from '@feathersjs/authentication';
|
|
5
|
+
|
|
6
|
+
import { Application } from './declarations';
|
|
4
7
|
|
|
5
8
|
const debug = createDebug('@feathersjs/express/authentication');
|
|
6
9
|
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
strategies: string[]
|
|
10
|
+
const toHandler = (func: (req: Request, res: Response, next: () => void) => Promise<void>): RequestHandler => {
|
|
11
|
+
return (req, res, next) => func(req, res, next).catch(error => next(error));
|
|
10
12
|
};
|
|
11
13
|
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
14
|
+
export type AuthenticationSettings = {
|
|
15
|
+
service?: string;
|
|
16
|
+
strategies?: string[];
|
|
17
|
+
};
|
|
16
18
|
|
|
17
|
-
export function parseAuthentication (settings:
|
|
18
|
-
return
|
|
19
|
-
const app = req.app as any;
|
|
20
|
-
const service = app.defaultAuthentication
|
|
19
|
+
export function parseAuthentication (settings: AuthenticationSettings = {}): RequestHandler {
|
|
20
|
+
return toHandler(async (req, res, next) => {
|
|
21
|
+
const app = req.app as any as Application;
|
|
22
|
+
const service = app.defaultAuthentication?.(settings.service);
|
|
21
23
|
|
|
22
|
-
if (service
|
|
24
|
+
if (!service) {
|
|
23
25
|
return next();
|
|
24
26
|
}
|
|
25
27
|
|
|
26
28
|
const config = service.configuration;
|
|
27
|
-
const authStrategies = config.parseStrategies || config.authStrategies || [];
|
|
29
|
+
const authStrategies = settings.strategies || config.parseStrategies || config.authStrategies || [];
|
|
28
30
|
|
|
29
31
|
if (authStrategies.length === 0) {
|
|
30
32
|
debug('No `authStrategies` or `parseStrategies` found in authentication configuration');
|
|
31
33
|
return next();
|
|
32
34
|
}
|
|
33
35
|
|
|
34
|
-
service.parse(req, res, ...authStrategies)
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
feathers: { authentication }
|
|
41
|
-
});
|
|
42
|
-
}
|
|
43
|
-
|
|
44
|
-
next();
|
|
45
|
-
}).catch(next);
|
|
46
|
-
};
|
|
47
|
-
}
|
|
36
|
+
const authentication = await service.parse(req, res, ...authStrategies)
|
|
37
|
+
|
|
38
|
+
if (authentication) {
|
|
39
|
+
debug('Parsed authentication from HTTP header', authentication);
|
|
40
|
+
req.feathers = { ...req.feathers, authentication };
|
|
41
|
+
}
|
|
48
42
|
|
|
49
|
-
|
|
50
|
-
|
|
43
|
+
return next();
|
|
44
|
+
});
|
|
45
|
+
}
|
|
51
46
|
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
}
|
|
47
|
+
export function authenticate (settings: string | AuthenticationSettings, ...strategies: string[]): RequestHandler {
|
|
48
|
+
const hook = AuthenticateHook(settings, ...strategies);
|
|
55
49
|
|
|
56
|
-
return (
|
|
57
|
-
const
|
|
58
|
-
const
|
|
59
|
-
const
|
|
50
|
+
return toHandler(async (req, _res, next) => {
|
|
51
|
+
const app = req.app as any as Application;
|
|
52
|
+
const params = req.feathers;
|
|
53
|
+
const context = { app, params } as any as HookContext;
|
|
60
54
|
|
|
61
|
-
|
|
55
|
+
await hook(context);
|
|
62
56
|
|
|
63
|
-
|
|
64
|
-
.then((authResult: any) => {
|
|
65
|
-
debug('Merging request with', authResult);
|
|
66
|
-
merge(req, authResult);
|
|
57
|
+
req.feathers = context.params;
|
|
67
58
|
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
};
|
|
59
|
+
return next();
|
|
60
|
+
});
|
|
71
61
|
}
|
package/src/declarations.ts
CHANGED
|
@@ -2,15 +2,15 @@ import http from 'http';
|
|
|
2
2
|
import express, { Express } from 'express';
|
|
3
3
|
import {
|
|
4
4
|
Application as FeathersApplication, Params as FeathersParams,
|
|
5
|
-
HookContext, ServiceMethods, ServiceInterface
|
|
5
|
+
HookContext, ServiceMethods, ServiceInterface, RouteLookup
|
|
6
6
|
} from '@feathersjs/feathers';
|
|
7
7
|
|
|
8
|
-
interface ExpressUseHandler<T,
|
|
9
|
-
<L extends keyof
|
|
8
|
+
interface ExpressUseHandler<T, Services> {
|
|
9
|
+
<L extends keyof Services & string> (
|
|
10
10
|
path: L,
|
|
11
11
|
...middlewareOrService: (
|
|
12
12
|
Express|express.RequestHandler|
|
|
13
|
-
(keyof any extends keyof
|
|
13
|
+
(keyof any extends keyof Services ? ServiceInterface : Services[L])
|
|
14
14
|
)[]
|
|
15
15
|
): T;
|
|
16
16
|
(path: string|RegExp, ...expressHandlers: express.RequestHandler[]): T;
|
|
@@ -18,43 +18,45 @@ interface ExpressUseHandler<T, ServiceTypes> {
|
|
|
18
18
|
(handler: Express|express.ErrorRequestHandler): T;
|
|
19
19
|
}
|
|
20
20
|
|
|
21
|
-
export interface ExpressOverrides<
|
|
21
|
+
export interface ExpressOverrides<Services> {
|
|
22
22
|
listen(port: number, hostname: string, backlog: number, callback?: () => void): Promise<http.Server>;
|
|
23
23
|
listen(port: number, hostname: string, callback?: () => void): Promise<http.Server>;
|
|
24
24
|
listen(port: number|string|any, callback?: () => void): Promise<http.Server>;
|
|
25
25
|
listen(callback?: () => void): Promise<http.Server>;
|
|
26
|
-
use: ExpressUseHandler<this,
|
|
26
|
+
use: ExpressUseHandler<this, Services>;
|
|
27
27
|
}
|
|
28
28
|
|
|
29
|
-
export type Application<
|
|
29
|
+
export type Application<Services = any, Settings = any> =
|
|
30
30
|
Omit<Express, 'listen'|'use'> &
|
|
31
|
-
FeathersApplication<
|
|
32
|
-
ExpressOverrides<
|
|
31
|
+
FeathersApplication<Services, Settings> &
|
|
32
|
+
ExpressOverrides<Services>;
|
|
33
33
|
|
|
34
34
|
declare module '@feathersjs/feathers/lib/declarations' {
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
before
|
|
38
|
-
after
|
|
39
|
-
|
|
35
|
+
interface ServiceOptions {
|
|
36
|
+
express?: {
|
|
37
|
+
before?: express.RequestHandler[];
|
|
38
|
+
after?: express.RequestHandler[];
|
|
39
|
+
composed?: express.RequestHandler;
|
|
40
|
+
};
|
|
40
41
|
}
|
|
41
42
|
}
|
|
42
43
|
|
|
43
44
|
declare module 'express-serve-static-core' {
|
|
44
45
|
interface Request {
|
|
45
|
-
|
|
46
|
+
feathers?: Partial<FeathersParams>;
|
|
47
|
+
lookup?: RouteLookup;
|
|
46
48
|
}
|
|
47
49
|
|
|
48
50
|
interface Response {
|
|
49
|
-
|
|
50
|
-
|
|
51
|
+
data?: any;
|
|
52
|
+
hook?: HookContext;
|
|
51
53
|
}
|
|
52
54
|
|
|
53
55
|
interface IRouterMatcher<T> {
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
56
|
+
// eslint-disable-next-line
|
|
57
|
+
<P extends Params = ParamsDictionary, ResBody = any, ReqBody = any>(
|
|
58
|
+
path: PathParams,
|
|
59
|
+
...handlers: (RequestHandler<P, ResBody, ReqBody> | Partial<ServiceMethods> | Application)[]
|
|
60
|
+
): T;
|
|
59
61
|
}
|
|
60
62
|
}
|
package/src/handlers.ts
CHANGED
|
@@ -18,10 +18,10 @@ export function notFound ({ verbose = false } = {}): RequestHandler {
|
|
|
18
18
|
}
|
|
19
19
|
|
|
20
20
|
export type ErrorHandlerOptions = {
|
|
21
|
-
public?: string
|
|
22
|
-
logger?: boolean|{ error?: (msg: any) => void, info?: (msg: any) => void }
|
|
23
|
-
html?: any
|
|
24
|
-
json?: any
|
|
21
|
+
public?: string;
|
|
22
|
+
logger?: boolean|{ error?: (msg: any) => void, info?: (msg: any) => void };
|
|
23
|
+
html?: any;
|
|
24
|
+
json?: any;
|
|
25
25
|
};
|
|
26
26
|
|
|
27
27
|
export function errorHandler (_options: ErrorHandlerOptions = {}): ErrorRequestHandler {
|
package/src/index.ts
CHANGED
|
@@ -1,23 +1,16 @@
|
|
|
1
|
-
import express, {
|
|
2
|
-
|
|
3
|
-
} from '
|
|
4
|
-
import {
|
|
5
|
-
Application as FeathersApplication, defaultServiceMethods
|
|
6
|
-
} from '@feathersjs/feathers';
|
|
1
|
+
import express, { Express } from 'express';
|
|
2
|
+
import { Application as FeathersApplication, defaultServiceMethods } from '@feathersjs/feathers';
|
|
3
|
+
import { routing } from '@feathersjs/transport-commons';
|
|
7
4
|
import { createDebug } from '@feathersjs/commons';
|
|
8
5
|
|
|
9
6
|
import { Application } from './declarations';
|
|
10
|
-
import { errorHandler, notFound } from './handlers';
|
|
11
|
-
import { parseAuthentication, authenticate } from './authentication';
|
|
12
7
|
|
|
13
|
-
export {
|
|
14
|
-
_static as static, json, raw, text, urlencoded, query,
|
|
15
|
-
errorHandler, notFound, express as original,
|
|
16
|
-
authenticate, parseAuthentication
|
|
17
|
-
};
|
|
8
|
+
export { default as original, static, static as serveStatic, json, raw, text, urlencoded, query } from 'express';
|
|
18
9
|
|
|
19
|
-
export * from './
|
|
10
|
+
export * from './authentication';
|
|
20
11
|
export * from './declarations';
|
|
12
|
+
export * from './handlers';
|
|
13
|
+
export * from './rest';
|
|
21
14
|
|
|
22
15
|
const debug = createDebug('@feathersjs/express');
|
|
23
16
|
|
|
@@ -30,10 +23,12 @@ export default function feathersExpress<S = any, C = any> (feathersApp?: Feather
|
|
|
30
23
|
throw new Error('@feathersjs/express requires a valid Feathers application instance');
|
|
31
24
|
}
|
|
32
25
|
|
|
33
|
-
const
|
|
34
|
-
|
|
35
|
-
const
|
|
36
|
-
|
|
26
|
+
const app = expressApp as any as Application<S, C>;
|
|
27
|
+
const { use: expressUse, listen: expressListen } = expressApp as any;
|
|
28
|
+
const feathersUse = feathersApp.use;
|
|
29
|
+
|
|
30
|
+
Object.assign(app, {
|
|
31
|
+
use (location: string & keyof S, ...rest: any[]) {
|
|
37
32
|
let service: any;
|
|
38
33
|
let options = {};
|
|
39
34
|
|
|
@@ -60,46 +55,56 @@ export default function feathersExpress<S = any, C = any> (feathersApp?: Feather
|
|
|
60
55
|
// Check for service (any object with at least one service method)
|
|
61
56
|
if (hasMethod(['handle', 'set']) || !hasMethod(defaultServiceMethods)) {
|
|
62
57
|
debug('Passing app.use call to Express app');
|
|
63
|
-
return
|
|
58
|
+
return expressUse.call(this, location, ...rest);
|
|
64
59
|
}
|
|
65
60
|
|
|
66
61
|
debug('Registering service with middleware', middleware);
|
|
67
62
|
// Since this is a service, call Feathers `.use`
|
|
68
|
-
|
|
63
|
+
feathersUse.call(this, location, service, {
|
|
69
64
|
...options,
|
|
70
|
-
middleware
|
|
65
|
+
express: middleware
|
|
71
66
|
});
|
|
72
67
|
|
|
73
68
|
return this;
|
|
74
69
|
},
|
|
75
70
|
|
|
76
71
|
async listen (...args: any[]) {
|
|
77
|
-
const server =
|
|
72
|
+
const server = expressListen.call(this, ...args);
|
|
78
73
|
|
|
79
74
|
await this.setup(server);
|
|
80
75
|
debug('Feathers application listening');
|
|
81
76
|
|
|
82
77
|
return server;
|
|
83
78
|
}
|
|
84
|
-
};
|
|
79
|
+
} as Application<S, C>);
|
|
85
80
|
|
|
86
|
-
const
|
|
81
|
+
const appDescriptors = {
|
|
82
|
+
...Object.getOwnPropertyDescriptors(Object.getPrototypeOf(app)),
|
|
83
|
+
...Object.getOwnPropertyDescriptors(app)
|
|
84
|
+
};
|
|
85
|
+
const newDescriptors = {
|
|
87
86
|
...Object.getOwnPropertyDescriptors(Object.getPrototypeOf(feathersApp)),
|
|
88
87
|
...Object.getOwnPropertyDescriptors(feathersApp)
|
|
89
88
|
};
|
|
90
89
|
|
|
91
90
|
// Copy all non-existing properties (including non-enumerables)
|
|
92
91
|
// that don't already exist on the Express app
|
|
93
|
-
Object.keys(
|
|
94
|
-
const
|
|
95
|
-
const
|
|
92
|
+
Object.keys(newDescriptors).forEach(prop => {
|
|
93
|
+
const appProp = appDescriptors[prop];
|
|
94
|
+
const newProp = newDescriptors[prop];
|
|
96
95
|
|
|
97
|
-
if (
|
|
98
|
-
Object.defineProperty(expressApp, prop,
|
|
96
|
+
if (appProp === undefined && newProp !== undefined) {
|
|
97
|
+
Object.defineProperty(expressApp, prop, newProp);
|
|
99
98
|
}
|
|
100
99
|
});
|
|
101
100
|
|
|
102
|
-
|
|
101
|
+
app.configure(routing() as any);
|
|
102
|
+
app.use((req, _res, next) => {
|
|
103
|
+
req.feathers = { ...req.feathers, provider: 'rest' };
|
|
104
|
+
return next();
|
|
105
|
+
});
|
|
106
|
+
|
|
107
|
+
return app;
|
|
103
108
|
}
|
|
104
109
|
|
|
105
110
|
if (typeof module !== 'undefined') {
|
package/src/rest.ts
CHANGED
|
@@ -1,120 +1,111 @@
|
|
|
1
|
+
import { Request, Response, RequestHandler, Router } from 'express';
|
|
1
2
|
import { MethodNotAllowed } from '@feathersjs/errors';
|
|
2
|
-
import { HookContext } from '@feathersjs/hooks';
|
|
3
3
|
import { createDebug } from '@feathersjs/commons';
|
|
4
4
|
import { http } from '@feathersjs/transport-commons';
|
|
5
5
|
import { createContext, defaultServiceMethods, getServiceOptions } from '@feathersjs/feathers';
|
|
6
|
-
import { Request, Response, NextFunction, RequestHandler, Router } from 'express';
|
|
7
6
|
|
|
8
|
-
import { parseAuthentication } from './authentication';
|
|
7
|
+
import { AuthenticationSettings, parseAuthentication } from './authentication';
|
|
8
|
+
import { Application } from './declarations';
|
|
9
9
|
|
|
10
10
|
const debug = createDebug('@feathersjs/express/rest');
|
|
11
11
|
|
|
12
|
-
|
|
12
|
+
const toHandler = (func: (req: Request, res: Response, next: () => void) => Promise<void>): RequestHandler => {
|
|
13
|
+
return (req, res, next) => func(req, res, next).catch(error => next(error));
|
|
14
|
+
};
|
|
13
15
|
|
|
14
|
-
|
|
15
|
-
req
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
headers: req.headers
|
|
19
|
-
};
|
|
20
|
-
next();
|
|
21
|
-
}
|
|
16
|
+
const serviceMiddleware = (): RequestHandler => {
|
|
17
|
+
return toHandler(async (req, res, next) => {
|
|
18
|
+
const { query, headers, path, body: data, method: httpMethod } = req;
|
|
19
|
+
const methodOverride = req.headers[http.METHOD_HEADER] as string | undefined;
|
|
22
20
|
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
}
|
|
21
|
+
const { service, params: { __id: id = null, ...route } = {} } = req.lookup!;
|
|
22
|
+
const method = http.getServiceMethod(httpMethod, id, methodOverride);
|
|
23
|
+
const { methods } = getServiceOptions(service);
|
|
27
24
|
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
25
|
+
debug(`Found service for path ${path}, attempting to run '${method}' service method`);
|
|
26
|
+
|
|
27
|
+
if (!methods.includes(method) || defaultServiceMethods.includes(methodOverride)) {
|
|
28
|
+
const error = new MethodNotAllowed(`Method \`${method}\` is not supported by this endpoint.`);
|
|
29
|
+
res.statusCode = error.code;
|
|
30
|
+
throw error;
|
|
31
31
|
}
|
|
32
|
-
});
|
|
33
|
-
}
|
|
34
32
|
|
|
33
|
+
const createArguments = http.argumentsFor[method as 'get'] || http.argumentsFor.default;
|
|
34
|
+
const params = { query, headers, route, ...req.feathers };
|
|
35
|
+
const args = createArguments({ id, data, params });
|
|
36
|
+
const contextBase = createContext(service, method, { http: {} });
|
|
37
|
+
res.hook = contextBase;
|
|
38
|
+
|
|
39
|
+
const context = await (service as any)[method](...args, contextBase);
|
|
40
|
+
res.hook = context;
|
|
35
41
|
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
debug(`Running service middleware for '${req.url}'`);
|
|
42
|
+
const result = http.getData(context);
|
|
43
|
+
const statusCode = http.getStatusCode(context, result);
|
|
39
44
|
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
45
|
+
res.data = result;
|
|
46
|
+
res.statusCode = statusCode;
|
|
47
|
+
|
|
48
|
+
return next();
|
|
49
|
+
});
|
|
50
|
+
};
|
|
46
51
|
|
|
47
|
-
|
|
48
|
-
|
|
52
|
+
const servicesMiddleware = (): RequestHandler => {
|
|
53
|
+
return toHandler(async (req, res, next) => {
|
|
54
|
+
const app = req.app as any as Application;
|
|
55
|
+
const lookup = app.lookup(req.path);
|
|
49
56
|
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
next(error);
|
|
57
|
+
if (!lookup) {
|
|
58
|
+
return next();
|
|
53
59
|
}
|
|
54
|
-
}
|
|
55
60
|
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
const method = methodOverride ? methodOverride : methodName
|
|
61
|
-
const { methods } = getServiceOptions(service);
|
|
61
|
+
req.lookup = lookup;
|
|
62
|
+
|
|
63
|
+
const options = getServiceOptions(lookup.service);
|
|
64
|
+
const middleware = options.express!.composed!;
|
|
62
65
|
|
|
63
|
-
|
|
64
|
-
|
|
66
|
+
return middleware(req, res, next);
|
|
67
|
+
});
|
|
68
|
+
};
|
|
65
69
|
|
|
66
|
-
|
|
70
|
+
export const formatter: RequestHandler = (_req, res, next) => {
|
|
71
|
+
if (res.data === undefined) {
|
|
72
|
+
return next();
|
|
67
73
|
}
|
|
68
74
|
|
|
69
|
-
|
|
70
|
-
|
|
75
|
+
res.format({
|
|
76
|
+
'application/json' () {
|
|
77
|
+
res.json(res.data);
|
|
78
|
+
}
|
|
79
|
+
});
|
|
80
|
+
};
|
|
81
|
+
|
|
82
|
+
export type RestOptions = {
|
|
83
|
+
formatter?: RequestHandler;
|
|
84
|
+
authentication?: AuthenticationSettings;
|
|
85
|
+
};
|
|
71
86
|
|
|
72
|
-
|
|
87
|
+
export const rest = (options?: RestOptions | RequestHandler) => {
|
|
88
|
+
options = typeof options === 'function' ? { formatter: options } : options || {};
|
|
73
89
|
|
|
74
|
-
|
|
75
|
-
|
|
90
|
+
const formatterMiddleware = options.formatter || formatter;
|
|
91
|
+
const authenticationOptions = options.authentication;
|
|
76
92
|
|
|
77
|
-
|
|
78
|
-
return function (this: any, app: any) {
|
|
93
|
+
return (app: Application) => {
|
|
79
94
|
if (typeof app.route !== 'function') {
|
|
80
95
|
throw new Error('@feathersjs/express/rest needs an Express compatible app.');
|
|
81
96
|
}
|
|
82
97
|
|
|
83
|
-
app.use(
|
|
84
|
-
app.use(
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
const baseUri = `/${path}`;
|
|
96
|
-
const find = serviceMethodHandler(service, 'find', http.argumentsFor.find);
|
|
97
|
-
const get = serviceMethodHandler(service, 'get', http.argumentsFor.get);
|
|
98
|
-
const create = serviceMethodHandler(service, 'create', http.argumentsFor.create, http.METHOD_HEADER);
|
|
99
|
-
const update = serviceMethodHandler(service, 'update', http.argumentsFor.update);
|
|
100
|
-
const patch = serviceMethodHandler(service, 'patch', http.argumentsFor.patch);
|
|
101
|
-
const remove = serviceMethodHandler(service, 'remove', http.argumentsFor.remove);
|
|
102
|
-
|
|
103
|
-
debug(`Adding REST provider for service \`${path}\` at base route \`${baseUri}\``);
|
|
104
|
-
|
|
105
|
-
const idRoute = '/:__feathersId';
|
|
106
|
-
const serviceRouter = Router({ mergeParams: true })
|
|
107
|
-
.get('/', find)
|
|
108
|
-
.post('/', create)
|
|
109
|
-
.get(idRoute, get)
|
|
110
|
-
.put('/', update)
|
|
111
|
-
.put(idRoute, update)
|
|
112
|
-
.patch('/', patch)
|
|
113
|
-
.patch(idRoute, patch)
|
|
114
|
-
.delete('/', remove)
|
|
115
|
-
.delete(idRoute, remove);
|
|
116
|
-
|
|
117
|
-
app.use(baseUri, ...before, serviceRouter, ...after);
|
|
98
|
+
app.use(parseAuthentication(authenticationOptions));
|
|
99
|
+
app.use(servicesMiddleware());
|
|
100
|
+
|
|
101
|
+
app.mixins.push((_service, _path, options) => {
|
|
102
|
+
const { express: { before = [], after = [] } = {} } = options;
|
|
103
|
+
|
|
104
|
+
const middlewares = [].concat(before, serviceMiddleware(), after, formatterMiddleware);
|
|
105
|
+
const middleware = Router().use(middlewares);
|
|
106
|
+
|
|
107
|
+
options.express ||= {};
|
|
108
|
+
options.express.composed = middleware;
|
|
118
109
|
});
|
|
119
110
|
};
|
|
120
111
|
}
|