axe-api 1.4.7 → 1.5.0-rc-1
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/build/dev-kit.d.ts +1 -0
- package/build/dev-kit.js +12 -0
- package/build/index.d.ts +2 -2
- package/build/index.js +2 -1
- package/build/src/Handlers/RequestHandler.js +6 -2
- package/build/src/Interfaces.d.ts +1 -0
- package/build/src/Middlewares/RateLimit/index.d.ts +1 -0
- package/build/src/Middlewares/RateLimit/index.js +29 -18
- package/build/src/Server.js +5 -5
- package/build/src/Services/AxeResponse.d.ts +0 -1
- package/build/src/Services/AxeResponse.js +4 -5
- package/build/src/constants.js +1 -0
- package/package.json +1 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
package/build/dev-kit.js
ADDED
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
const dotenv_1 = __importDefault(require("dotenv"));
|
|
7
|
+
const path_1 = __importDefault(require("path"));
|
|
8
|
+
const index_1 = require("./index");
|
|
9
|
+
console.log("Axe API dev-kit (1.0.1)");
|
|
10
|
+
dotenv_1.default.config();
|
|
11
|
+
const server = new index_1.Server();
|
|
12
|
+
server.start(path_1.default.join(__dirname, "dev-kit"));
|
package/build/index.d.ts
CHANGED
|
@@ -4,8 +4,8 @@ import ApiError from "./src/Exceptions/ApiError";
|
|
|
4
4
|
import RedisAdaptor from "./src/Middlewares/RateLimit/RedisAdaptor";
|
|
5
5
|
import { DEFAULT_HANDLERS, DEFAULT_VERSION_CONFIG } from "./src/constants";
|
|
6
6
|
import { IoCService, allow, deny, App, AxeRequest, AxeResponse } from "./src/Services";
|
|
7
|
-
import { rateLimit } from "./src/Middlewares/RateLimit";
|
|
7
|
+
import { rateLimit, createRateLimitMiddleware } from "./src/Middlewares/RateLimit";
|
|
8
8
|
export * from "./src/Enums";
|
|
9
9
|
export * from "./src/Interfaces";
|
|
10
10
|
export * from "./src/Types";
|
|
11
|
-
export { App, AxeRequest, AxeResponse, Server, Model, ApiError, RedisAdaptor, DEFAULT_HANDLERS, DEFAULT_VERSION_CONFIG, IoCService, allow, deny, rateLimit, };
|
|
11
|
+
export { App, AxeRequest, AxeResponse, Server, Model, ApiError, RedisAdaptor, DEFAULT_HANDLERS, DEFAULT_VERSION_CONFIG, IoCService, allow, deny, rateLimit, createRateLimitMiddleware, };
|
package/build/index.js
CHANGED
|
@@ -17,7 +17,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
17
17
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
18
18
|
};
|
|
19
19
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
20
|
-
exports.rateLimit = exports.deny = exports.allow = exports.IoCService = exports.DEFAULT_VERSION_CONFIG = exports.DEFAULT_HANDLERS = exports.RedisAdaptor = exports.ApiError = exports.Model = exports.Server = exports.AxeResponse = exports.AxeRequest = exports.App = void 0;
|
|
20
|
+
exports.createRateLimitMiddleware = exports.rateLimit = exports.deny = exports.allow = exports.IoCService = exports.DEFAULT_VERSION_CONFIG = exports.DEFAULT_HANDLERS = exports.RedisAdaptor = exports.ApiError = exports.Model = exports.Server = exports.AxeResponse = exports.AxeRequest = exports.App = void 0;
|
|
21
21
|
const Server_1 = __importDefault(require("./src/Server"));
|
|
22
22
|
exports.Server = Server_1.default;
|
|
23
23
|
const Model_1 = __importDefault(require("./src/Model"));
|
|
@@ -38,6 +38,7 @@ Object.defineProperty(exports, "AxeRequest", { enumerable: true, get: function (
|
|
|
38
38
|
Object.defineProperty(exports, "AxeResponse", { enumerable: true, get: function () { return Services_1.AxeResponse; } });
|
|
39
39
|
const RateLimit_1 = require("./src/Middlewares/RateLimit");
|
|
40
40
|
Object.defineProperty(exports, "rateLimit", { enumerable: true, get: function () { return RateLimit_1.rateLimit; } });
|
|
41
|
+
Object.defineProperty(exports, "createRateLimitMiddleware", { enumerable: true, get: function () { return RateLimit_1.createRateLimitMiddleware; } });
|
|
41
42
|
__exportStar(require("./src/Enums"), exports);
|
|
42
43
|
__exportStar(require("./src/Interfaces"), exports);
|
|
43
44
|
__exportStar(require("./src/Types"), exports);
|
|
@@ -53,8 +53,12 @@ exports.default = (request, response, next) => __awaiter(void 0, void 0, void 0,
|
|
|
53
53
|
}
|
|
54
54
|
const validator = yield Services_1.IoCService.use("Validator");
|
|
55
55
|
const context = Object.assign(Object.assign({}, match.data), { params: match.params, api, req: axeRequest, res: axeResponse, isTransactionOpen: match.hasTransaction, database: match.hasTransaction && trx ? trx : database, validator });
|
|
56
|
-
response.
|
|
57
|
-
|
|
56
|
+
if (!response.isResponded) {
|
|
57
|
+
response.setHeader("Content-Type", "application/json");
|
|
58
|
+
if (api.config.disableXPoweredByHeader === false) {
|
|
59
|
+
response.setHeader("x-powered-by", "Axe API");
|
|
60
|
+
}
|
|
61
|
+
}
|
|
58
62
|
for (const phase of match.phases) {
|
|
59
63
|
// If there is an non-async phase, it should be an Event function
|
|
60
64
|
if (phase.isAsync === false) {
|
|
@@ -85,6 +85,7 @@ export interface AxeConfig extends IConfig {
|
|
|
85
85
|
rateLimit: IRateLimitConfig;
|
|
86
86
|
errorHandler: ErrorHandleFunction;
|
|
87
87
|
docs: boolean;
|
|
88
|
+
disableXPoweredByHeader: boolean;
|
|
88
89
|
redis: RedisClientOptions | undefined;
|
|
89
90
|
cache: ICacheConfiguration;
|
|
90
91
|
elasticSearch: ClientOptions;
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { IncomingMessage, ServerResponse } from "http";
|
|
2
2
|
import { AxeConfig, IRateLimitOptions, IContext } from "../../Interfaces";
|
|
3
3
|
export declare const setupRateLimitAdaptors: (config: AxeConfig) => Promise<void>;
|
|
4
|
+
export declare const createRateLimitMiddleware: (req: IncomingMessage, res: ServerResponse, next: () => void, key: string, options: IRateLimitOptions) => Promise<void>;
|
|
4
5
|
/**
|
|
5
6
|
* Add a rate limit with the `IRateLimitOptions`
|
|
6
7
|
*
|
|
@@ -12,7 +12,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
12
12
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
13
13
|
};
|
|
14
14
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
15
|
-
exports.rateLimit = exports.setupRateLimitAdaptors = void 0;
|
|
15
|
+
exports.rateLimit = exports.createRateLimitMiddleware = exports.setupRateLimitAdaptors = void 0;
|
|
16
16
|
const AdaptorFactory_1 = __importDefault(require("./AdaptorFactory"));
|
|
17
17
|
const Services_1 = require("../../Services");
|
|
18
18
|
const nanoid_1 = require("nanoid");
|
|
@@ -70,6 +70,25 @@ const setupRateLimitAdaptors = (config) => __awaiter(void 0, void 0, void 0, fun
|
|
|
70
70
|
adaptor = yield (0, AdaptorFactory_1.default)(((_a = config.rateLimit) === null || _a === void 0 ? void 0 : _a.adaptor) || "memory");
|
|
71
71
|
});
|
|
72
72
|
exports.setupRateLimitAdaptors = setupRateLimitAdaptors;
|
|
73
|
+
const createRateLimitMiddleware = (req, res, next, key, options) => __awaiter(void 0, void 0, void 0, function* () {
|
|
74
|
+
// Checking the rate limit
|
|
75
|
+
const isAllowed = yield checkRateLimit(key, options);
|
|
76
|
+
// Setting the headers
|
|
77
|
+
res.setHeader("X-RateLimit-Limit", isAllowed.limit);
|
|
78
|
+
res.setHeader("X-RateLimit-Remaining", isAllowed.remaining);
|
|
79
|
+
// Sending an error message if there is an error
|
|
80
|
+
if (isAllowed.success === false) {
|
|
81
|
+
Services_1.LogService.warn(`Rate limit exceeded: ${req.url}`);
|
|
82
|
+
res.statusCode = Enums_1.StatusCodes.TOO_MANY_REQUESTS;
|
|
83
|
+
res.write(JSON.stringify({
|
|
84
|
+
error: "Rate limit exceeded.",
|
|
85
|
+
}));
|
|
86
|
+
res.isResponded = true;
|
|
87
|
+
res.end();
|
|
88
|
+
}
|
|
89
|
+
next();
|
|
90
|
+
});
|
|
91
|
+
exports.createRateLimitMiddleware = createRateLimitMiddleware;
|
|
73
92
|
/**
|
|
74
93
|
* Add a rate limit with the `IRateLimitOptions`
|
|
75
94
|
*
|
|
@@ -90,26 +109,18 @@ exports.setupRateLimitAdaptors = setupRateLimitAdaptors;
|
|
|
90
109
|
const rateLimit = (options) => {
|
|
91
110
|
// For each model middleware, we should use a different ID for the cache key
|
|
92
111
|
const id = (0, nanoid_1.nanoid)();
|
|
112
|
+
// API configuration fetching
|
|
113
|
+
const api = Services_1.APIService.getInstance();
|
|
114
|
+
// Developers are able to set different rate limit options
|
|
115
|
+
// in model files. That's why we should create a new option object.
|
|
116
|
+
const selectedOptions = Object.assign(Object.assign({}, api.config.rateLimit), options);
|
|
93
117
|
return (context) => __awaiter(void 0, void 0, void 0, function* () {
|
|
94
|
-
// API configuration fetching
|
|
95
|
-
const api = Services_1.APIService.getInstance();
|
|
96
118
|
// Creating a clientkey by the client key configurations
|
|
97
119
|
const clientKey = getClientKeyByConfigurations(context.req.original, api.config.rateLimit);
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
const isAllowed = yield checkRateLimit(`${clientKey}:${id}`, selectedOptions);
|
|
103
|
-
// Setting the headers
|
|
104
|
-
context.res.original.setHeader("X-RateLimit-Limit", isAllowed.limit);
|
|
105
|
-
context.res.original.setHeader("X-RateLimit-Remaining", isAllowed.remaining);
|
|
106
|
-
// Sending an error message if there is an error
|
|
107
|
-
if (isAllowed.success === false) {
|
|
108
|
-
Services_1.LogService.warn(`Rate limit exceeded: ${context.req.url}`);
|
|
109
|
-
context.res
|
|
110
|
-
.status(Enums_1.StatusCodes.TOO_MANY_REQUESTS)
|
|
111
|
-
.json({ error: "Rate limit exceeded." });
|
|
112
|
-
}
|
|
120
|
+
const key = `${clientKey}:${id}`;
|
|
121
|
+
return new Promise((resolve) => {
|
|
122
|
+
(0, exports.createRateLimitMiddleware)(context.req.original, context.res.original, resolve, key, selectedOptions);
|
|
123
|
+
});
|
|
113
124
|
});
|
|
114
125
|
};
|
|
115
126
|
exports.rateLimit = rateLimit;
|
package/build/src/Server.js
CHANGED
|
@@ -142,6 +142,11 @@ class Server {
|
|
|
142
142
|
var _a;
|
|
143
143
|
const app = yield Services_1.IoCService.use("App");
|
|
144
144
|
const api = Services_1.APIService.getInstance();
|
|
145
|
+
// Rate limitting should be added before init() functions
|
|
146
|
+
if ((_a = api.config.rateLimit) === null || _a === void 0 ? void 0 : _a.enabled) {
|
|
147
|
+
Services_1.LogService.debug("New middleware: rateLimit()");
|
|
148
|
+
app.use(RateLimit_1.default);
|
|
149
|
+
}
|
|
145
150
|
// Adding the default handler for auto-created routes
|
|
146
151
|
app.use(RequestHandler_1.default);
|
|
147
152
|
// Setting the error handler
|
|
@@ -155,11 +160,6 @@ class Server {
|
|
|
155
160
|
app.get("/docs", DocsHandler_1.default);
|
|
156
161
|
app.get("/routes", RoutesHandler_1.default);
|
|
157
162
|
}
|
|
158
|
-
// Rate limitting should be added after init() functions.
|
|
159
|
-
if ((_a = api.config.rateLimit) === null || _a === void 0 ? void 0 : _a.enabled) {
|
|
160
|
-
Services_1.LogService.debug("New middleware: rateLimit()");
|
|
161
|
-
app.use(RateLimit_1.default);
|
|
162
|
-
}
|
|
163
163
|
server.listen(api.config.port);
|
|
164
164
|
Services_1.LogService.axe(`Axe API listens requests on http://localhost:${api.config.port}`);
|
|
165
165
|
});
|
|
@@ -2,7 +2,6 @@
|
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
class AxeResponse {
|
|
4
4
|
constructor(response, language) {
|
|
5
|
-
this.responseStatus = false;
|
|
6
5
|
this.response = response;
|
|
7
6
|
this.response.statusCode = 200;
|
|
8
7
|
this.language = language;
|
|
@@ -36,7 +35,7 @@ class AxeResponse {
|
|
|
36
35
|
this.response.setHeader("Content-Language", this.language.language);
|
|
37
36
|
this.response.write(JSON.stringify(data));
|
|
38
37
|
this.response.end();
|
|
39
|
-
this.
|
|
38
|
+
this.response.isResponded = true;
|
|
40
39
|
}
|
|
41
40
|
/**
|
|
42
41
|
* Set the HTTP Response Data as string
|
|
@@ -46,7 +45,7 @@ class AxeResponse {
|
|
|
46
45
|
send(content) {
|
|
47
46
|
this.response.write(content);
|
|
48
47
|
this.response.end();
|
|
49
|
-
this.
|
|
48
|
+
this.response.isResponded = true;
|
|
50
49
|
}
|
|
51
50
|
/**
|
|
52
51
|
* Set the no-content to the HTTP Response with 204 status code.
|
|
@@ -54,10 +53,10 @@ class AxeResponse {
|
|
|
54
53
|
noContent() {
|
|
55
54
|
this.response.statusCode = 204;
|
|
56
55
|
this.response.end();
|
|
57
|
-
this.
|
|
56
|
+
this.response.isResponded = true;
|
|
58
57
|
}
|
|
59
58
|
isResponded() {
|
|
60
|
-
return this.
|
|
59
|
+
return !!this.response.isResponded;
|
|
61
60
|
}
|
|
62
61
|
statusCode() {
|
|
63
62
|
return this.response.statusCode;
|
package/build/src/constants.js
CHANGED