express-ext 0.1.7 → 0.1.12
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/lib/GenericController.js +16 -8
- package/lib/GenericSearchController.js +0 -1
- package/lib/HealthController.js +7 -49
- package/lib/LoadController.js +0 -1
- package/lib/LoadSearchController.js +0 -1
- package/lib/LogController.js +51 -0
- package/lib/LowCodeController.js +0 -1
- package/lib/SearchController.js +0 -1
- package/lib/edit.js +12 -13
- package/lib/health.js +5 -8
- package/lib/http.js +33 -7
- package/lib/index.js +2 -41
- package/lib/resources.js +2 -9
- package/lib/search.js +70 -58
- package/lib/search_func.js +0 -1
- package/lib/view.js +9 -7
- package/package.json +1 -1
- package/src/GenericController.ts +21 -13
- package/src/GenericSearchController.ts +3 -3
- package/src/HealthController.ts +1 -1
- package/src/LoadController.ts +6 -6
- package/src/LoadSearchController.ts +3 -3
- package/src/LogController.ts +70 -0
- package/src/LowCodeController.ts +4 -4
- package/src/SearchController.ts +3 -3
- package/src/edit.ts +18 -18
- package/src/health.ts +3 -4
- package/src/http.ts +46 -23
- package/src/index.ts +10 -0
- package/src/metadata.ts +2 -1
- package/src/search.ts +74 -62
- package/src/search_func.ts +1 -1
- package/src/view.ts +12 -9
- package/tsconfig.json +1 -0
package/src/LowCodeController.ts
CHANGED
|
@@ -3,22 +3,22 @@ import {ResultInfo, StatusConfig} from './edit';
|
|
|
3
3
|
import {GenericController, GenericService} from './GenericController';
|
|
4
4
|
import {handleError} from './http';
|
|
5
5
|
import {ErrorMessage} from './metadata';
|
|
6
|
-
import {format, fromRequest, getParameters, initializeConfig, jsonResult, SearchConfig,
|
|
6
|
+
import {Filter, format, fromRequest, getParameters, initializeConfig, jsonResult, SearchConfig, SearchResult} from './search';
|
|
7
7
|
import {getMetadataFunc} from './search_func';
|
|
8
8
|
|
|
9
9
|
export interface LowCodeConfig extends StatusConfig, SearchConfig {
|
|
10
10
|
}
|
|
11
|
-
export interface
|
|
11
|
+
export interface Service<T, ID, R, S extends Filter> extends GenericService<T, ID, R> {
|
|
12
12
|
search: (s: S, limit?: number, skip?: number|string, fields?: string[]) => Promise<SearchResult<T>>;
|
|
13
13
|
}
|
|
14
|
-
export class LowCodeController<T, ID, S extends
|
|
14
|
+
export class LowCodeController<T, ID, S extends Filter> extends GenericController<T, ID> {
|
|
15
15
|
config?: SearchConfig;
|
|
16
16
|
csv?: boolean;
|
|
17
17
|
dates?: string[];
|
|
18
18
|
numbers?: string[];
|
|
19
19
|
fields?: string;
|
|
20
20
|
excluding?: string;
|
|
21
|
-
constructor(log: (msg: string
|
|
21
|
+
constructor(log: (msg: string) => void, public lowCodeService: Service<T, ID, number|ResultInfo<T>, S>, config?: LowCodeConfig, validate?: (obj: T, patch?: boolean) => Promise<ErrorMessage[]>, dates?: string[], numbers?: string[]) {
|
|
22
22
|
super(log, lowCodeService, config, validate);
|
|
23
23
|
this.search = this.search.bind(this);
|
|
24
24
|
this.config = initializeConfig(config);
|
package/src/SearchController.ts
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
import {Request, Response} from 'express';
|
|
2
2
|
import {handleError} from './http';
|
|
3
|
-
import {format, fromRequest, getParameters, initializeConfig, jsonResult, SearchConfig,
|
|
3
|
+
import {Filter, format, fromRequest, getParameters, initializeConfig, jsonResult, SearchConfig, SearchResult} from './search';
|
|
4
4
|
|
|
5
|
-
export class SearchController<T, S extends
|
|
5
|
+
export class SearchController<T, S extends Filter> {
|
|
6
6
|
config?: SearchConfig;
|
|
7
7
|
csv?: boolean;
|
|
8
8
|
fields?: string;
|
|
9
9
|
excluding?: string;
|
|
10
|
-
constructor(protected log: (msg:
|
|
10
|
+
constructor(protected log: (msg: string) => void, public find: (s: S, limit?: number, skip?: number|string, fields?: string[]) => Promise<SearchResult<T>>, config?: SearchConfig|boolean, public dates?: string[], public numbers?: string[]) {
|
|
11
11
|
this.search = this.search.bind(this);
|
|
12
12
|
if (config) {
|
|
13
13
|
if (typeof config === 'boolean') {
|
package/src/edit.ts
CHANGED
|
@@ -3,11 +3,11 @@ import {handleError} from './http';
|
|
|
3
3
|
import {Attribute, ErrorMessage} from './metadata';
|
|
4
4
|
|
|
5
5
|
export interface StatusConfig {
|
|
6
|
-
duplicate_key
|
|
7
|
-
not_found
|
|
8
|
-
success
|
|
6
|
+
duplicate_key: number|string;
|
|
7
|
+
not_found: number|string;
|
|
8
|
+
success: number|string;
|
|
9
9
|
version_error?: number|string;
|
|
10
|
-
validation_error
|
|
10
|
+
validation_error: number|string;
|
|
11
11
|
error?: number|string;
|
|
12
12
|
}
|
|
13
13
|
export interface ResultInfo<T> {
|
|
@@ -16,7 +16,7 @@ export interface ResultInfo<T> {
|
|
|
16
16
|
value?: T;
|
|
17
17
|
message?: string;
|
|
18
18
|
}
|
|
19
|
-
export function initializeStatus(s
|
|
19
|
+
export function initializeStatus(s?: StatusConfig): StatusConfig {
|
|
20
20
|
if (s) {
|
|
21
21
|
return s;
|
|
22
22
|
}
|
|
@@ -25,39 +25,39 @@ export function initializeStatus(s: StatusConfig): StatusConfig {
|
|
|
25
25
|
not_found: 0,
|
|
26
26
|
success: 1,
|
|
27
27
|
version_error: 2,
|
|
28
|
+
validation_error: 4,
|
|
28
29
|
error: 4
|
|
29
30
|
};
|
|
30
31
|
return s1;
|
|
31
32
|
}
|
|
32
|
-
export function checkId<T, ID>(obj: T, id: ID, keys
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
}
|
|
33
|
+
export function checkId<T, ID>(obj: T, id: ID, keys?: Attribute[]): boolean {
|
|
34
|
+
const n: string = (keys && keys.length === 1 && keys[0].name ? keys[0].name : 'id');
|
|
35
|
+
const o: any = obj;
|
|
36
|
+
const i: any = id;
|
|
37
37
|
if (!keys || keys.length === 1) {
|
|
38
|
-
const v =
|
|
38
|
+
const v = o[n];
|
|
39
39
|
if (!v) {
|
|
40
|
-
|
|
40
|
+
o[n] = i;
|
|
41
41
|
return true;
|
|
42
42
|
}
|
|
43
43
|
// tslint:disable-next-line:triple-equals
|
|
44
|
-
if (v !=
|
|
44
|
+
if (v != i) {
|
|
45
45
|
return false;
|
|
46
46
|
}
|
|
47
47
|
return true;
|
|
48
48
|
}
|
|
49
|
-
const ks = Object.keys(
|
|
49
|
+
const ks = Object.keys(i);
|
|
50
50
|
for (const k of ks) {
|
|
51
|
-
const v =
|
|
51
|
+
const v = o[k];
|
|
52
52
|
if (!v) {
|
|
53
|
-
|
|
53
|
+
o[k] = i[k];
|
|
54
54
|
} else {
|
|
55
55
|
// tslint:disable-next-line:triple-equals
|
|
56
|
-
if (v !=
|
|
56
|
+
if (v != i[k]) {
|
|
57
57
|
return false;
|
|
58
58
|
}
|
|
59
59
|
}
|
|
60
|
-
|
|
60
|
+
o[k] = i[k];
|
|
61
61
|
}
|
|
62
62
|
return true;
|
|
63
63
|
}
|
package/src/health.ts
CHANGED
|
@@ -17,12 +17,10 @@ export interface HealthChecker {
|
|
|
17
17
|
}
|
|
18
18
|
|
|
19
19
|
export async function check(checkers: HealthChecker[]): Promise<Health> {
|
|
20
|
-
const p: Health = {
|
|
21
|
-
status: 'UP',
|
|
22
|
-
details: {} as HealthMap,
|
|
23
|
-
};
|
|
20
|
+
const p: Health = { status: 'UP' };
|
|
24
21
|
const total = checkers.length - 1;
|
|
25
22
|
let count = 0;
|
|
23
|
+
p.details = {} as HealthMap;
|
|
26
24
|
for (const checker of checkers) {
|
|
27
25
|
const sub: Health = {status: 'UP'};
|
|
28
26
|
try {
|
|
@@ -48,4 +46,5 @@ export async function check(checkers: HealthChecker[]): Promise<Health> {
|
|
|
48
46
|
}
|
|
49
47
|
}
|
|
50
48
|
}
|
|
49
|
+
return p;
|
|
51
50
|
}
|
package/src/http.ts
CHANGED
|
@@ -1,12 +1,19 @@
|
|
|
1
1
|
import {Request, Response} from 'express';
|
|
2
2
|
import {Attribute} from './metadata';
|
|
3
3
|
|
|
4
|
-
export function handleError(err: any, res: Response, log?: (msg: string
|
|
4
|
+
export function handleError(err: any, res: Response, log?: (msg: string) => void) {
|
|
5
5
|
if (log) {
|
|
6
|
-
log(
|
|
6
|
+
log(toString(err));
|
|
7
7
|
res.status(500).end('Internal Server Error');
|
|
8
8
|
} else {
|
|
9
|
-
res.status(500).end(
|
|
9
|
+
res.status(500).end(toString(err));
|
|
10
|
+
}
|
|
11
|
+
}
|
|
12
|
+
export function toString(v: any): string {
|
|
13
|
+
if (typeof v === 'string') {
|
|
14
|
+
return v;
|
|
15
|
+
} else {
|
|
16
|
+
return JSON.stringify(v);
|
|
10
17
|
}
|
|
11
18
|
}
|
|
12
19
|
export function attr(name: string): Attribute {
|
|
@@ -27,7 +34,7 @@ export function respondModel<T>(obj: T, res: Response): void {
|
|
|
27
34
|
res.status(404).json(null).end();
|
|
28
35
|
}
|
|
29
36
|
}
|
|
30
|
-
export function queryRequiredParams(req: Request, res: Response, name: string, split?: string): string[] {
|
|
37
|
+
export function queryRequiredParams(req: Request, res: Response, name: string, split?: string): string[]|undefined {
|
|
31
38
|
const v = req.query[name];
|
|
32
39
|
if (!v) {
|
|
33
40
|
res.status(400).end(`'${name}' cannot be empty`);
|
|
@@ -43,9 +50,12 @@ export function queryRequiredParams(req: Request, res: Response, name: string, s
|
|
|
43
50
|
}
|
|
44
51
|
return v2.split(split);
|
|
45
52
|
}
|
|
46
|
-
export function queryParams(req: Request, name: string, d?: string[], split?: string): string[] {
|
|
53
|
+
export function queryParams(req: Request, name: string, d?: string[], split?: string): string[]|undefined {
|
|
47
54
|
const q = req.query[name];
|
|
48
|
-
|
|
55
|
+
if (!q) {
|
|
56
|
+
return d;
|
|
57
|
+
}
|
|
58
|
+
const v = q.toString();
|
|
49
59
|
if (!v || v.length === 0) {
|
|
50
60
|
return d;
|
|
51
61
|
}
|
|
@@ -54,23 +64,33 @@ export function queryParams(req: Request, name: string, d?: string[], split?: st
|
|
|
54
64
|
}
|
|
55
65
|
return v.split(split);
|
|
56
66
|
}
|
|
57
|
-
export function queryParam(req: Request, res: Response, name: string): string {
|
|
58
|
-
const v = req.query[name]
|
|
59
|
-
if (!v
|
|
67
|
+
export function queryParam(req: Request, res: Response, name: string): string|undefined {
|
|
68
|
+
const v = req.query[name];
|
|
69
|
+
if (!v) {
|
|
60
70
|
res.status(400).end(`'${name}' cannot be empty`);
|
|
61
71
|
return undefined;
|
|
72
|
+
} else {
|
|
73
|
+
const v1 = v.toString();
|
|
74
|
+
if (v1.length === 0) {
|
|
75
|
+
res.status(400).end(`'${name}' cannot be empty`);
|
|
76
|
+
return undefined;
|
|
77
|
+
} else {
|
|
78
|
+
return v1;
|
|
79
|
+
}
|
|
62
80
|
}
|
|
63
|
-
return v;
|
|
64
81
|
}
|
|
65
|
-
export function query(req: Request, name: string, d?: string): string {
|
|
82
|
+
export function query(req: Request, name: string, d?: string): string|undefined {
|
|
66
83
|
const p = req.query[name];
|
|
67
84
|
if (!p || p.toString().length === 0) {
|
|
68
85
|
return d;
|
|
69
86
|
}
|
|
70
87
|
return p.toString();
|
|
71
88
|
}
|
|
72
|
-
export function queryRequiredNumber(req: Request, res: Response, name: string): number {
|
|
89
|
+
export function queryRequiredNumber(req: Request, res: Response, name: string): number|undefined {
|
|
73
90
|
const field = req.query[name];
|
|
91
|
+
if (!field) {
|
|
92
|
+
return undefined;
|
|
93
|
+
}
|
|
74
94
|
const v = field.toString();
|
|
75
95
|
if (!v || v.length === 0) {
|
|
76
96
|
res.status(400).end(`'${name}' cannot be empty`);
|
|
@@ -83,7 +103,7 @@ export function queryRequiredNumber(req: Request, res: Response, name: string):
|
|
|
83
103
|
const n = parseFloat(v);
|
|
84
104
|
return n;
|
|
85
105
|
}
|
|
86
|
-
export function queryNumber(req: Request, name: string, d?: number): number {
|
|
106
|
+
export function queryNumber(req: Request, name: string, d?: number): number|undefined {
|
|
87
107
|
const field = req.query[name];
|
|
88
108
|
const v = field ? field.toString() : undefined;
|
|
89
109
|
if (!v || v.length === 0) {
|
|
@@ -95,8 +115,11 @@ export function queryNumber(req: Request, name: string, d?: number): number {
|
|
|
95
115
|
const n = parseFloat(v);
|
|
96
116
|
return n;
|
|
97
117
|
}
|
|
98
|
-
export function queryRequiredDate(req: Request, res: Response, name: string): Date {
|
|
118
|
+
export function queryRequiredDate(req: Request, res: Response, name: string): Date|undefined {
|
|
99
119
|
const field = req.query[name];
|
|
120
|
+
if (!field) {
|
|
121
|
+
return undefined;
|
|
122
|
+
}
|
|
100
123
|
const v = field.toString();
|
|
101
124
|
if (!v || v.length === 0) {
|
|
102
125
|
res.status(400).end(`'${name}' cannot be empty`);
|
|
@@ -109,7 +132,7 @@ export function queryRequiredDate(req: Request, res: Response, name: string): Da
|
|
|
109
132
|
}
|
|
110
133
|
return date;
|
|
111
134
|
}
|
|
112
|
-
export function queryDate(req: Request, name: string, d?: Date): Date {
|
|
135
|
+
export function queryDate(req: Request, name: string, d?: Date): Date|undefined {
|
|
113
136
|
const field = req.query[name];
|
|
114
137
|
if (field) {
|
|
115
138
|
const v = field.toString();
|
|
@@ -125,7 +148,7 @@ export function queryDate(req: Request, name: string, d?: Date): Date {
|
|
|
125
148
|
return undefined;
|
|
126
149
|
}
|
|
127
150
|
|
|
128
|
-
export function param(req: Request, res: Response, name: string): string {
|
|
151
|
+
export function param(req: Request, res: Response, name: string): string|undefined {
|
|
129
152
|
const v = req.params[name];
|
|
130
153
|
if (!v || v.length === 0) {
|
|
131
154
|
res.status(400).end(`'${name}' cannot be empty`);
|
|
@@ -133,7 +156,7 @@ export function param(req: Request, res: Response, name: string): string {
|
|
|
133
156
|
}
|
|
134
157
|
return v;
|
|
135
158
|
}
|
|
136
|
-
export function params(req: Request, name: string, d?: string[], split?: string): string[] {
|
|
159
|
+
export function params(req: Request, name: string, d?: string[], split?: string): string[]|undefined {
|
|
137
160
|
const v = req.params[name];
|
|
138
161
|
if (!v || v.length === 0) {
|
|
139
162
|
return d;
|
|
@@ -143,7 +166,7 @@ export function params(req: Request, name: string, d?: string[], split?: string)
|
|
|
143
166
|
}
|
|
144
167
|
return v.split(split);
|
|
145
168
|
}
|
|
146
|
-
export function getRequiredParameters(req: Request, res: Response, name: string, split?: string): string[] {
|
|
169
|
+
export function getRequiredParameters(req: Request, res: Response, name: string, split?: string): string[]|undefined {
|
|
147
170
|
const v = req.params[name];
|
|
148
171
|
if (!v || v.length === 0) {
|
|
149
172
|
res.status(400).end(`'${name}' cannot be empty`);
|
|
@@ -154,7 +177,7 @@ export function getRequiredParameters(req: Request, res: Response, name: string,
|
|
|
154
177
|
}
|
|
155
178
|
return v.split(split);
|
|
156
179
|
}
|
|
157
|
-
export function getRequiredNumber(req: Request, res: Response, name: string): number {
|
|
180
|
+
export function getRequiredNumber(req: Request, res: Response, name: string): number|undefined {
|
|
158
181
|
const v = req.params[name];
|
|
159
182
|
if (!v || v.length === 0) {
|
|
160
183
|
res.status(400).end(`'${name}' cannot be empty`);
|
|
@@ -167,7 +190,7 @@ export function getRequiredNumber(req: Request, res: Response, name: string): nu
|
|
|
167
190
|
const n = parseFloat(v);
|
|
168
191
|
return n;
|
|
169
192
|
}
|
|
170
|
-
export function getNumber(req: Request, name: string, d?: number): number {
|
|
193
|
+
export function getNumber(req: Request, name: string, d?: number): number|undefined {
|
|
171
194
|
const v = req.params[name];
|
|
172
195
|
if (!v || v.length === 0) {
|
|
173
196
|
return d;
|
|
@@ -178,7 +201,7 @@ export function getNumber(req: Request, name: string, d?: number): number {
|
|
|
178
201
|
const n = parseFloat(v);
|
|
179
202
|
return n;
|
|
180
203
|
}
|
|
181
|
-
export function getInteger(req: Request, name: string, d?: number): number {
|
|
204
|
+
export function getInteger(req: Request, name: string, d?: number): number|undefined {
|
|
182
205
|
const v = req.params[name];
|
|
183
206
|
if (!v || v.length === 0) {
|
|
184
207
|
return d;
|
|
@@ -190,7 +213,7 @@ export function getInteger(req: Request, name: string, d?: number): number {
|
|
|
190
213
|
const s = n.toFixed(0);
|
|
191
214
|
return parseFloat(s);
|
|
192
215
|
}
|
|
193
|
-
export function getRequiredDate(req: Request, res: Response, name: string): Date {
|
|
216
|
+
export function getRequiredDate(req: Request, res: Response, name: string): Date|undefined {
|
|
194
217
|
const v = req.params[name];
|
|
195
218
|
if (!v || v.length === 0) {
|
|
196
219
|
res.status(400).end(`'${name}' cannot be empty`);
|
|
@@ -203,7 +226,7 @@ export function getRequiredDate(req: Request, res: Response, name: string): Date
|
|
|
203
226
|
}
|
|
204
227
|
return date;
|
|
205
228
|
}
|
|
206
|
-
export function getDate(req: Request, name: string, d?: Date): Date {
|
|
229
|
+
export function getDate(req: Request, name: string, d?: Date): Date|undefined {
|
|
207
230
|
const v = req.params[name];
|
|
208
231
|
if (!v || v.length === 0) {
|
|
209
232
|
return d;
|
package/src/index.ts
CHANGED
|
@@ -3,19 +3,29 @@ import {GenericSearchController} from './GenericSearchController';
|
|
|
3
3
|
import {HealthController} from './HealthController';
|
|
4
4
|
import {LoadController} from './LoadController';
|
|
5
5
|
import {LoadSearchController} from './LoadSearchController';
|
|
6
|
+
import {LogController} from './LogController';
|
|
6
7
|
import {LowCodeController} from './LowCodeController';
|
|
8
|
+
import {Service} from './LowCodeController';
|
|
7
9
|
import {SearchController} from './SearchController';
|
|
8
10
|
|
|
9
11
|
export {HealthController as HealthHandler};
|
|
12
|
+
export {LogController as LogHandler};
|
|
10
13
|
export {LoadController as LoadHandler};
|
|
14
|
+
export {LoadController as ViewHandler};
|
|
15
|
+
export {LoadController as ViewController};
|
|
16
|
+
|
|
11
17
|
export {GenericController as GenericHandler};
|
|
12
18
|
export {SearchController as SearchHandler};
|
|
13
19
|
export {LoadSearchController as LoadSearchHandler};
|
|
14
20
|
export {GenericSearchController as GenericSearchHandler};
|
|
15
21
|
export {LowCodeController as LowCodeHandler};
|
|
22
|
+
export {LowCodeController as Handler};
|
|
23
|
+
export {LowCodeController as Controller};
|
|
24
|
+
export {Service as LowCodeService};
|
|
16
25
|
|
|
17
26
|
export * from './health';
|
|
18
27
|
export * from './HealthController';
|
|
28
|
+
export * from './LogController';
|
|
19
29
|
export * from './http';
|
|
20
30
|
export * from './metadata';
|
|
21
31
|
export * from './view';
|
package/src/metadata.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
export type DataType = 'ObjectId' | 'date' | 'datetime' | 'time'
|
|
2
2
|
| 'boolean' | 'number' | 'integer' | 'string' | 'text'
|
|
3
|
-
| 'object' | 'array' | '
|
|
3
|
+
| 'object' | 'array' | 'binary'
|
|
4
|
+
| 'primitives' | 'booleans' | 'numbers' | 'integers' | 'strings' | 'dates' | 'datetimes' | 'times';
|
|
4
5
|
export type FormatType = 'currency' | 'percentage' | 'email' | 'url' | 'phone' | 'fax' | 'ipv4' | 'ipv6';
|
|
5
6
|
|
|
6
7
|
export interface ErrorMessage {
|