remult 0.14.20 → 0.14.23
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/esm/index.d.ts +1 -1
- package/esm/index.js +1 -1
- package/esm/postgres/schema-builder.js +1 -1
- package/esm/remult-express.d.ts +7 -1
- package/esm/remult-express.js +7 -2
- package/esm/remult-fastify.d.ts +3 -0
- package/esm/remult-fastify.js +57 -0
- package/esm/remult-knex/index.js +1 -1
- package/esm/remult-middleware.d.ts +7 -1
- package/esm/remult-middleware.js +6 -4
- package/esm/server/expressBridge.d.ts +22 -17
- package/esm/server/expressBridge.js +13 -16
- package/esm/src/backend-tests/test-http-server.backend-spec.js +32 -8
- package/esm/src/remult3/RepositoryImplementation.js +1 -1
- package/esm/src/server-action.js +2 -1
- package/esm/src/valueConverters.d.ts +12 -0
- package/esm/src/valueConverters.js +169 -0
- package/index.d.ts +1 -1
- package/index.js +1 -1
- package/package.json +21 -1
- package/postgres/schema-builder.js +1 -1
- package/remult-express.d.ts +7 -1
- package/remult-express.js +6 -1
- package/remult-fastify.d.ts +3 -0
- package/remult-fastify.js +66 -0
- package/remult-knex/index.js +1 -1
- package/remult-middleware.d.ts +7 -1
- package/remult-middleware.js +5 -3
- package/server/expressBridge.d.ts +22 -17
- package/server/expressBridge.js +15 -18
- package/src/backend-tests/test-http-server.backend-spec.js +69 -12
- package/src/remult3/RepositoryImplementation.js +1 -1
- package/src/server-action.js +4 -2
- package/src/valueConverters.d.ts +12 -0
- package/src/valueConverters.js +168 -0
package/esm/index.d.ts
CHANGED
|
@@ -19,4 +19,4 @@ export { Filter } from './src/filter/filter-interfaces';
|
|
|
19
19
|
export { FilterConsumerBridgeToSqlRequest } from './src/filter/filter-consumer-bridge-to-sql-request';
|
|
20
20
|
export { UrlBuilder } from './urlBuilder';
|
|
21
21
|
export { Validators } from './src/validators';
|
|
22
|
-
export { ValueConverters } from './valueConverters';
|
|
22
|
+
export { ValueConverters } from './src/valueConverters';
|
package/esm/index.js
CHANGED
|
@@ -18,4 +18,4 @@ export { Filter } from './src/filter/filter-interfaces';
|
|
|
18
18
|
export { FilterConsumerBridgeToSqlRequest } from './src/filter/filter-consumer-bridge-to-sql-request';
|
|
19
19
|
export { UrlBuilder } from './urlBuilder';
|
|
20
20
|
export { Validators } from './src/validators';
|
|
21
|
-
export { ValueConverters } from './valueConverters';
|
|
21
|
+
export { ValueConverters } from './src/valueConverters';
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { allEntities } from '../src/context';
|
|
2
2
|
import { getDbNameProvider } from '../src/filter/filter-consumer-bridge-to-sql-request';
|
|
3
3
|
import { isAutoIncrement } from '../src/remult3';
|
|
4
|
-
import { ValueConverters } from '../valueConverters';
|
|
4
|
+
import { ValueConverters } from '../src/valueConverters';
|
|
5
5
|
export function postgresColumnSyntax(x, dbName) {
|
|
6
6
|
let result = dbName;
|
|
7
7
|
if (x.valueType == Number) {
|
package/esm/remult-express.d.ts
CHANGED
|
@@ -2,4 +2,10 @@ import { RemultMiddlewareOptions } from './server/expressBridge';
|
|
|
2
2
|
export declare function remultExpress(options?: RemultMiddlewareOptions & {
|
|
3
3
|
bodyParser?: boolean;
|
|
4
4
|
bodySizeLimit?: string;
|
|
5
|
-
}): import("
|
|
5
|
+
}): import("express-serve-static-core").Router & {
|
|
6
|
+
getRemult: (req: any) => Promise<import(".").Remult>;
|
|
7
|
+
openApiDoc: (options: {
|
|
8
|
+
title: string;
|
|
9
|
+
}) => any;
|
|
10
|
+
addArea: (x: any) => any;
|
|
11
|
+
};
|
package/esm/remult-express.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import * as express from 'express';
|
|
2
|
-
import {
|
|
2
|
+
import { buildRemultServer } from './server/expressBridge';
|
|
3
3
|
export function remultExpress(options) {
|
|
4
4
|
let app = express.Router();
|
|
5
5
|
if (!options) {
|
|
@@ -12,5 +12,10 @@ export function remultExpress(options) {
|
|
|
12
12
|
app.use(express.json({ limit: options.bodySizeLimit }));
|
|
13
13
|
app.use(express.urlencoded({ extended: true, limit: options.bodySizeLimit }));
|
|
14
14
|
}
|
|
15
|
-
|
|
15
|
+
const server = buildRemultServer(app, options);
|
|
16
|
+
return Object.assign(app, {
|
|
17
|
+
getRemult: (req) => server.getRemult(req),
|
|
18
|
+
openApiDoc: (options) => server.openApiDoc(options),
|
|
19
|
+
addArea: x => server.addArea(x)
|
|
20
|
+
});
|
|
16
21
|
}
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
import { buildRemultServer } from './server/expressBridge';
|
|
2
|
+
export function remultFastify(options) {
|
|
3
|
+
function fastifyHandler(handler) {
|
|
4
|
+
const response = (req, res) => {
|
|
5
|
+
const myRes = {
|
|
6
|
+
status(statusCode) {
|
|
7
|
+
res.status(statusCode);
|
|
8
|
+
return myRes;
|
|
9
|
+
},
|
|
10
|
+
end() {
|
|
11
|
+
res.send();
|
|
12
|
+
},
|
|
13
|
+
json(data) {
|
|
14
|
+
res.send(data);
|
|
15
|
+
}
|
|
16
|
+
};
|
|
17
|
+
handler(req, myRes, () => { });
|
|
18
|
+
};
|
|
19
|
+
return response;
|
|
20
|
+
}
|
|
21
|
+
let api;
|
|
22
|
+
const pluginFunction = async (instance, options) => {
|
|
23
|
+
//@ts-ignore
|
|
24
|
+
let fastifyRouter = {
|
|
25
|
+
route(path) {
|
|
26
|
+
let r = {
|
|
27
|
+
delete(handler) {
|
|
28
|
+
instance.delete(path, fastifyHandler(handler));
|
|
29
|
+
return r;
|
|
30
|
+
},
|
|
31
|
+
get(handler) {
|
|
32
|
+
instance.get(path, fastifyHandler(handler));
|
|
33
|
+
return r;
|
|
34
|
+
}, post(handler) {
|
|
35
|
+
instance.post(path, fastifyHandler(handler));
|
|
36
|
+
return r;
|
|
37
|
+
}, put(handler) {
|
|
38
|
+
instance.put(path, fastifyHandler(handler));
|
|
39
|
+
return r;
|
|
40
|
+
},
|
|
41
|
+
};
|
|
42
|
+
return r;
|
|
43
|
+
},
|
|
44
|
+
};
|
|
45
|
+
api = buildRemultServer(fastifyRouter, options);
|
|
46
|
+
};
|
|
47
|
+
const getApi = () => {
|
|
48
|
+
if (!api)
|
|
49
|
+
throw "Please call fastify's register before using this method";
|
|
50
|
+
return api;
|
|
51
|
+
};
|
|
52
|
+
return Object.assign(pluginFunction, {
|
|
53
|
+
addArea: x => getApi().addArea(x),
|
|
54
|
+
getRemult: x => getApi().getRemult(x),
|
|
55
|
+
openApiDoc: x => getApi().openApiDoc(x)
|
|
56
|
+
});
|
|
57
|
+
}
|
package/esm/remult-knex/index.js
CHANGED
|
@@ -3,7 +3,7 @@ import { customDatabaseFilterToken, Filter } from "../src/filter/filter-interfac
|
|
|
3
3
|
import { getDbNameProvider } from "../src/filter/filter-consumer-bridge-to-sql-request";
|
|
4
4
|
import { allEntities, Remult } from "../src/context";
|
|
5
5
|
import { isAutoIncrement } from "../src/remult3";
|
|
6
|
-
import { ValueConverters } from "../valueConverters";
|
|
6
|
+
import { ValueConverters } from "../src/valueConverters";
|
|
7
7
|
import { CompoundIdField } from '../src/column';
|
|
8
8
|
export class KnexDataProvider {
|
|
9
9
|
constructor(knex) {
|
|
@@ -1,2 +1,8 @@
|
|
|
1
1
|
import { RemultMiddlewareOptions } from './server/expressBridge';
|
|
2
|
-
export declare function remultMiddleware(options?: RemultMiddlewareOptions):
|
|
2
|
+
export declare function remultMiddleware(options?: RemultMiddlewareOptions): ((req: any, res: any, next: any) => void) & {
|
|
3
|
+
getRemult: (req: any) => Promise<import(".").Remult>;
|
|
4
|
+
openApiDoc: (options: {
|
|
5
|
+
title: string;
|
|
6
|
+
}) => any;
|
|
7
|
+
addArea: (x: any) => any;
|
|
8
|
+
};
|
package/esm/remult-middleware.js
CHANGED
|
@@ -1,10 +1,12 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { buildRemultServer } from './server/expressBridge';
|
|
2
2
|
export function remultMiddleware(options) {
|
|
3
3
|
const m = new middleware();
|
|
4
|
-
|
|
5
|
-
|
|
4
|
+
const server = buildRemultServer(m, options);
|
|
5
|
+
return Object.assign((req, res, next) => m.handleRequest(req, res, next), {
|
|
6
|
+
getRemult: (req) => server.getRemult(req),
|
|
7
|
+
openApiDoc: (options) => server.openApiDoc(options),
|
|
8
|
+
addArea: x => server.addArea(x)
|
|
6
9
|
});
|
|
7
|
-
return remultMiddlewareBase(app, options);
|
|
8
10
|
}
|
|
9
11
|
class middleware {
|
|
10
12
|
constructor() {
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { queuedJobInfoResponse } from '../src/server-action';
|
|
2
2
|
import { DataProvider } from '../src/data-interfaces';
|
|
3
3
|
import { DataApi, DataApiRequest, DataApiResponse } from '../src/data-api';
|
|
4
|
-
import { AllowedForInstance, Remult } from '../src/context';
|
|
4
|
+
import { AllowedForInstance, Remult, UserInfo } from '../src/context';
|
|
5
5
|
import { ClassType } from '../classType';
|
|
6
6
|
import { Repository } from '../src/remult3';
|
|
7
7
|
import { IdEntity } from '../src/id-entity';
|
|
@@ -22,27 +22,18 @@ export declare type RemultMiddlewareOptions = {
|
|
|
22
22
|
bodyParser?: boolean;
|
|
23
23
|
rootPath?: string;
|
|
24
24
|
};
|
|
25
|
-
export declare function
|
|
26
|
-
export
|
|
25
|
+
export declare function buildRemultServer(app: GenericRouter, options: RemultMiddlewareOptions): RemultServer;
|
|
26
|
+
export declare type GenericRequestHandler = (req: GenericRequest, res: GenericResponse, next: VoidFunction) => void;
|
|
27
|
+
export interface RemultExpressBridge extends GenericRequestHandler, RemultServer {
|
|
28
|
+
}
|
|
29
|
+
export interface RemultServer {
|
|
27
30
|
getRemult(req: GenericRequest): Promise<Remult>;
|
|
28
31
|
openApiDoc(options: {
|
|
29
32
|
title: string;
|
|
30
33
|
}): any;
|
|
31
34
|
addArea(rootUrl: string): any;
|
|
32
35
|
}
|
|
33
|
-
export
|
|
34
|
-
method: any;
|
|
35
|
-
url: any;
|
|
36
|
-
query?: any;
|
|
37
|
-
body: any;
|
|
38
|
-
params?: any;
|
|
39
|
-
}
|
|
40
|
-
export interface GenericResponse {
|
|
41
|
-
json(data: any): any;
|
|
42
|
-
statusCode: number;
|
|
43
|
-
end(): any;
|
|
44
|
-
}
|
|
45
|
-
export declare type GenericRouter = GenericRequestHandler & {
|
|
36
|
+
export declare type GenericRouter = {
|
|
46
37
|
route(path: string): SpecificRoute;
|
|
47
38
|
};
|
|
48
39
|
export declare type SpecificRoute = {
|
|
@@ -51,7 +42,21 @@ export declare type SpecificRoute = {
|
|
|
51
42
|
post(handler: GenericRequestHandler): SpecificRoute;
|
|
52
43
|
delete(handler: GenericRequestHandler): SpecificRoute;
|
|
53
44
|
};
|
|
54
|
-
export
|
|
45
|
+
export interface GenericRequest {
|
|
46
|
+
url: string;
|
|
47
|
+
method?: any;
|
|
48
|
+
body?: any;
|
|
49
|
+
query?: any;
|
|
50
|
+
params?: any;
|
|
51
|
+
user?: UserInfo;
|
|
52
|
+
auth?: UserInfo;
|
|
53
|
+
}
|
|
54
|
+
export interface GenericResponse {
|
|
55
|
+
json(data: any): any;
|
|
56
|
+
status?(statusCode: number): GenericResponse;
|
|
57
|
+
setStatus?(statusCode: number): GenericResponse;
|
|
58
|
+
end(): any;
|
|
59
|
+
}
|
|
55
60
|
declare class ExpressBridge {
|
|
56
61
|
private app;
|
|
57
62
|
queue: inProcessQueueHandler;
|
|
@@ -8,7 +8,7 @@ import { allEntities, Remult } from '../src/context';
|
|
|
8
8
|
import { Entity, Fields, getEntityKey } from '../src/remult3';
|
|
9
9
|
import { JsonDataProvider } from '../src/data-providers/json-data-provider';
|
|
10
10
|
import { IdEntity } from '../src/id-entity';
|
|
11
|
-
export function
|
|
11
|
+
export function buildRemultServer(app, options) {
|
|
12
12
|
if (!options) {
|
|
13
13
|
options = {};
|
|
14
14
|
}
|
|
@@ -52,12 +52,9 @@ export function remultMiddlewareBase(app, options) {
|
|
|
52
52
|
registerActionsOnServer(apiArea, actions);
|
|
53
53
|
registerEntitiesOnServer(apiArea, options.entities);
|
|
54
54
|
}
|
|
55
|
-
return
|
|
56
|
-
getRemult: (req) => bridge.getRemult(req),
|
|
57
|
-
openApiDoc: (options) => bridge.openApiDoc(options),
|
|
58
|
-
addArea: x => bridge.addArea(x)
|
|
59
|
-
});
|
|
55
|
+
return bridge;
|
|
60
56
|
}
|
|
57
|
+
;
|
|
61
58
|
class ExpressBridge {
|
|
62
59
|
constructor(app, queue, initRequest, dataProvider) {
|
|
63
60
|
this.app = app;
|
|
@@ -479,11 +476,12 @@ class ExpressResponseBridgeToDataApiResponse {
|
|
|
479
476
|
this.req = req;
|
|
480
477
|
}
|
|
481
478
|
forbidden() {
|
|
482
|
-
this.
|
|
479
|
+
this.setStatus(403).end();
|
|
483
480
|
}
|
|
484
|
-
|
|
485
|
-
this.r.
|
|
486
|
-
|
|
481
|
+
setStatus(status) {
|
|
482
|
+
if (this.r.setStatus)
|
|
483
|
+
return this.r.setStatus(status);
|
|
484
|
+
return this.r.status(status);
|
|
487
485
|
}
|
|
488
486
|
progress(progress) {
|
|
489
487
|
}
|
|
@@ -491,14 +489,13 @@ class ExpressResponseBridgeToDataApiResponse {
|
|
|
491
489
|
this.r.json(data);
|
|
492
490
|
}
|
|
493
491
|
created(data) {
|
|
494
|
-
this.
|
|
495
|
-
this.r.json(data);
|
|
492
|
+
this.setStatus(201).json(data);
|
|
496
493
|
}
|
|
497
494
|
deleted() {
|
|
498
|
-
this.
|
|
495
|
+
this.setStatus(204).end();
|
|
499
496
|
}
|
|
500
497
|
notFound() {
|
|
501
|
-
this.
|
|
498
|
+
this.setStatus(404).end();
|
|
502
499
|
}
|
|
503
500
|
error(data) {
|
|
504
501
|
data = serializeError(data);
|
|
@@ -508,8 +505,8 @@ class ExpressResponseBridgeToDataApiResponse {
|
|
|
508
505
|
url: this.req.url,
|
|
509
506
|
method: this.req.method
|
|
510
507
|
});
|
|
511
|
-
this.
|
|
512
|
-
|
|
508
|
+
this.setStatus(400).json(data);
|
|
509
|
+
;
|
|
513
510
|
}
|
|
514
511
|
}
|
|
515
512
|
function throwError() {
|
|
@@ -3,22 +3,41 @@ import axios from 'axios';
|
|
|
3
3
|
import { HttpProviderBridgeToRestDataProviderHttpProvider, Remult } from '../context';
|
|
4
4
|
import { Entity, Fields } from '../remult3';
|
|
5
5
|
import { Action, BackendMethod } from '../server-action';
|
|
6
|
-
Remult.apiBaseUrl = 'http://localhost:
|
|
7
|
-
|
|
8
|
-
|
|
6
|
+
Remult.apiBaseUrl = 'http://localhost:3003/api';
|
|
7
|
+
let path = Remult.apiBaseUrl + '/tasks';
|
|
8
|
+
const environments = [
|
|
9
|
+
// ["next", 3000],
|
|
10
|
+
["nest", 3001],
|
|
11
|
+
["koa", 3002],
|
|
12
|
+
["fastify", 3003],
|
|
13
|
+
["express", 3004],
|
|
14
|
+
["middleware", 3005],
|
|
15
|
+
];
|
|
16
|
+
function test(name, test) {
|
|
17
|
+
for (const [env, port] of environments) {
|
|
18
|
+
const theTest = async () => {
|
|
19
|
+
Remult.apiBaseUrl = `http://localhost:${port}/api`;
|
|
20
|
+
path = Remult.apiBaseUrl + '/tasks';
|
|
21
|
+
await test();
|
|
22
|
+
};
|
|
23
|
+
const testName = env + ` ${port}: ${name}`;
|
|
24
|
+
fit(testName, theTest);
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
test("works", async () => {
|
|
9
28
|
const repo = await create3Tasks();
|
|
10
29
|
const tasks = await repo.find({ where: { completed: true } });
|
|
11
30
|
expect(tasks.length).toBe(1);
|
|
12
31
|
await repo.save({ ...tasks[0], completed: false });
|
|
13
32
|
expect(await repo.count({ completed: true })).toBe(0);
|
|
14
33
|
});
|
|
15
|
-
|
|
34
|
+
test("test multiple items", async () => {
|
|
16
35
|
const repo = await create3Tasks();
|
|
17
36
|
expect(await repo.count({
|
|
18
37
|
title: { "!=": ["a", "c"] }
|
|
19
38
|
})).toBe(1);
|
|
20
39
|
});
|
|
21
|
-
|
|
40
|
+
test("validation", async () => {
|
|
22
41
|
const r = await create3Tasks();
|
|
23
42
|
let err = undefined;
|
|
24
43
|
try {
|
|
@@ -35,7 +54,7 @@ fit("validation", async () => {
|
|
|
35
54
|
}
|
|
36
55
|
});
|
|
37
56
|
});
|
|
38
|
-
|
|
57
|
+
test("forbidden", async () => {
|
|
39
58
|
let err = undefined;
|
|
40
59
|
try {
|
|
41
60
|
await Task.testForbidden();
|
|
@@ -45,7 +64,7 @@ fit("forbidden", async () => {
|
|
|
45
64
|
}
|
|
46
65
|
expect(err.httpStatusCode).toEqual(403);
|
|
47
66
|
});
|
|
48
|
-
|
|
67
|
+
test("test http 404", async () => {
|
|
49
68
|
const repo = create3Tasks();
|
|
50
69
|
const task = await (await repo).findFirst();
|
|
51
70
|
let result = await axios.get(path + "/" + task.id);
|
|
@@ -60,13 +79,18 @@ fit("test http 404", async () => {
|
|
|
60
79
|
}
|
|
61
80
|
expect(error.response.status).toBe(404);
|
|
62
81
|
});
|
|
63
|
-
|
|
82
|
+
test("test http 201", async () => {
|
|
64
83
|
let result = await axios.post(path, { title: "z", id: "" });
|
|
65
84
|
expect(result.data.title).toBe("z");
|
|
66
85
|
expect(result.status).toBe(201);
|
|
67
86
|
result = await axios.delete(path + "/" + result.data.id);
|
|
68
87
|
expect(result.status).toBe(204);
|
|
69
88
|
});
|
|
89
|
+
test("test regular api call", async () => {
|
|
90
|
+
await create3Tasks();
|
|
91
|
+
let result = await axios.get(Remult.apiBaseUrl + "/test");
|
|
92
|
+
expect(result.data.result).toBe(3);
|
|
93
|
+
});
|
|
70
94
|
let Task = class Task {
|
|
71
95
|
constructor() {
|
|
72
96
|
this.title = '';
|
|
@@ -3,7 +3,7 @@ import { allEntities, Remult, isBackend, queryConfig as queryConfig, setControll
|
|
|
3
3
|
import { entityFilterToJson, Filter } from "../filter/filter-interfaces";
|
|
4
4
|
import { Sort } from "../sort";
|
|
5
5
|
import { v4 as uuid } from 'uuid';
|
|
6
|
-
import { ValueConverters } from "
|
|
6
|
+
import { ValueConverters } from "../valueConverters";
|
|
7
7
|
import { filterHelper } from "../filter/filter-interfaces";
|
|
8
8
|
import { assign } from "../../assign";
|
|
9
9
|
let classValidatorValidate = undefined;
|
package/esm/src/server-action.js
CHANGED
|
@@ -46,7 +46,7 @@ export class Action {
|
|
|
46
46
|
res.success(r);
|
|
47
47
|
}
|
|
48
48
|
catch (err) {
|
|
49
|
-
if (err
|
|
49
|
+
if (err.isForbiddenError) // got a problem in next with instance of ForbiddenError - so replaced it with this bool
|
|
50
50
|
res.forbidden();
|
|
51
51
|
else
|
|
52
52
|
res.error(err);
|
|
@@ -58,6 +58,7 @@ Action.apiUrlForJobStatus = 'jobStatusInQueue';
|
|
|
58
58
|
class ForbiddenError extends Error {
|
|
59
59
|
constructor() {
|
|
60
60
|
super("Forbidden");
|
|
61
|
+
this.isForbiddenError = true;
|
|
61
62
|
}
|
|
62
63
|
}
|
|
63
64
|
export class myServerAction extends Action {
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { ValueConverter } from "./column-interfaces";
|
|
2
|
+
export declare class ValueConverters {
|
|
3
|
+
static readonly Date: ValueConverter<Date>;
|
|
4
|
+
static readonly DateOnly: ValueConverter<Date>;
|
|
5
|
+
static readonly DateOnlyString: ValueConverter<Date>;
|
|
6
|
+
static readonly Boolean: ValueConverter<Boolean>;
|
|
7
|
+
static readonly Number: ValueConverter<number>;
|
|
8
|
+
static readonly Integer: ValueConverter<number>;
|
|
9
|
+
static readonly Default: ValueConverter<any>;
|
|
10
|
+
static readonly JsonString: ValueConverter<any>;
|
|
11
|
+
static readonly JsonValue: ValueConverter<any>;
|
|
12
|
+
}
|
|
@@ -0,0 +1,169 @@
|
|
|
1
|
+
import { InputTypes } from "../inputTypes";
|
|
2
|
+
export class ValueConverters {
|
|
3
|
+
}
|
|
4
|
+
ValueConverters.Date = {
|
|
5
|
+
toJson: (val) => {
|
|
6
|
+
if (!val)
|
|
7
|
+
return '';
|
|
8
|
+
if (typeof (val) === "string")
|
|
9
|
+
val = new Date(val);
|
|
10
|
+
if (val instanceof Date) {
|
|
11
|
+
return val.toISOString();
|
|
12
|
+
}
|
|
13
|
+
else {
|
|
14
|
+
console.log("ToJsonError", val);
|
|
15
|
+
throw new Error("Expected date but got val");
|
|
16
|
+
}
|
|
17
|
+
},
|
|
18
|
+
fromJson: (val) => {
|
|
19
|
+
if (val == undefined)
|
|
20
|
+
return undefined;
|
|
21
|
+
if (val == '')
|
|
22
|
+
return undefined;
|
|
23
|
+
if (val.startsWith('0000-00-00'))
|
|
24
|
+
return undefined;
|
|
25
|
+
return new Date(Date.parse(val));
|
|
26
|
+
},
|
|
27
|
+
toDb: x => x,
|
|
28
|
+
fromDb: x => x,
|
|
29
|
+
fromInput: x => ValueConverters.Date.fromJson(x),
|
|
30
|
+
toInput: x => ValueConverters.Date.toJson(x),
|
|
31
|
+
displayValue: (val) => {
|
|
32
|
+
if (!val)
|
|
33
|
+
return '';
|
|
34
|
+
return val.toLocaleString();
|
|
35
|
+
}
|
|
36
|
+
};
|
|
37
|
+
ValueConverters.DateOnly = {
|
|
38
|
+
fromInput: x => ValueConverters.DateOnly.fromJson(x),
|
|
39
|
+
toInput: x => ValueConverters.DateOnly.toJson(x),
|
|
40
|
+
toJson: (val) => {
|
|
41
|
+
var d = val;
|
|
42
|
+
if (typeof d === "string" || typeof (d) === "number")
|
|
43
|
+
d = new Date(d);
|
|
44
|
+
if (!d || d == null)
|
|
45
|
+
return null;
|
|
46
|
+
if (d.getHours() == 0)
|
|
47
|
+
return new Date(d.valueOf() - d.getTimezoneOffset() * 60000).toISOString().substring(0, 10);
|
|
48
|
+
else
|
|
49
|
+
return d.toISOString().substring(0, 10);
|
|
50
|
+
},
|
|
51
|
+
fromJson: (value) => {
|
|
52
|
+
if (!value || value == '' || value == '0000-00-00')
|
|
53
|
+
return null;
|
|
54
|
+
let d = new Date(Date.parse(value));
|
|
55
|
+
d.setMinutes(d.getMinutes() + d.getTimezoneOffset());
|
|
56
|
+
return d;
|
|
57
|
+
},
|
|
58
|
+
inputType: InputTypes.date,
|
|
59
|
+
toDb: (val) => {
|
|
60
|
+
if (!val)
|
|
61
|
+
return null;
|
|
62
|
+
return ValueConverters.DateOnly.fromJson(ValueConverters.DateOnly.toJson(val));
|
|
63
|
+
} //when using date storage, the database expects and returns a date local and every where else we reflect on date iso
|
|
64
|
+
,
|
|
65
|
+
fromDb: (val) => {
|
|
66
|
+
var d = val;
|
|
67
|
+
if (!d)
|
|
68
|
+
return null;
|
|
69
|
+
return val;
|
|
70
|
+
},
|
|
71
|
+
fieldTypeInDb: 'date',
|
|
72
|
+
displayValue: (value) => {
|
|
73
|
+
if (!value)
|
|
74
|
+
return '';
|
|
75
|
+
return value.toLocaleDateString(undefined);
|
|
76
|
+
}
|
|
77
|
+
};
|
|
78
|
+
ValueConverters.DateOnlyString = {
|
|
79
|
+
...ValueConverters.DateOnly,
|
|
80
|
+
toDb: (d) => {
|
|
81
|
+
let val = ValueConverters.DateOnly.toJson(d);
|
|
82
|
+
if (!val)
|
|
83
|
+
return undefined;
|
|
84
|
+
return val.replace(/-/g, '');
|
|
85
|
+
},
|
|
86
|
+
fromDb: (val) => {
|
|
87
|
+
if (val === null)
|
|
88
|
+
return null;
|
|
89
|
+
if (!val)
|
|
90
|
+
return undefined;
|
|
91
|
+
return new Date(val.substring(0, 4) + '-' + val.substring(4, 6) + '-' + val.substring(6, 8));
|
|
92
|
+
}
|
|
93
|
+
};
|
|
94
|
+
ValueConverters.Boolean = {
|
|
95
|
+
toDb: (val) => val,
|
|
96
|
+
inputType: InputTypes.checkbox,
|
|
97
|
+
fromDb: (value) => {
|
|
98
|
+
return ValueConverters.Boolean.fromJson(value);
|
|
99
|
+
},
|
|
100
|
+
fromJson: value => {
|
|
101
|
+
if (typeof value === "boolean")
|
|
102
|
+
return value;
|
|
103
|
+
if (value !== undefined && value !== null) {
|
|
104
|
+
return value.toString().trim().toLowerCase() == 'true';
|
|
105
|
+
}
|
|
106
|
+
return value;
|
|
107
|
+
},
|
|
108
|
+
toJson: x => x,
|
|
109
|
+
fromInput: x => ValueConverters.Boolean.fromJson(x),
|
|
110
|
+
toInput: x => ValueConverters.Boolean.toJson(x)
|
|
111
|
+
};
|
|
112
|
+
ValueConverters.Number = {
|
|
113
|
+
fromDb: value => {
|
|
114
|
+
if (value === null)
|
|
115
|
+
return null;
|
|
116
|
+
if (value !== undefined)
|
|
117
|
+
return +value;
|
|
118
|
+
return undefined;
|
|
119
|
+
},
|
|
120
|
+
toDb: value => value,
|
|
121
|
+
fromJson: value => ValueConverters.Number.fromDb(value),
|
|
122
|
+
toJson: value => ValueConverters.Number.toDb(value),
|
|
123
|
+
fromInput: (x, type) => {
|
|
124
|
+
let r = +x;
|
|
125
|
+
if (!x)
|
|
126
|
+
return undefined;
|
|
127
|
+
return r;
|
|
128
|
+
},
|
|
129
|
+
toInput: (x, type) => {
|
|
130
|
+
return x?.toString();
|
|
131
|
+
},
|
|
132
|
+
inputType: InputTypes.number
|
|
133
|
+
};
|
|
134
|
+
ValueConverters.Integer = {
|
|
135
|
+
...ValueConverters.Number,
|
|
136
|
+
toJson: value => {
|
|
137
|
+
let val = ValueConverters.Number.toDb(value);
|
|
138
|
+
if (!val)
|
|
139
|
+
return val;
|
|
140
|
+
return +(+val).toFixed(0);
|
|
141
|
+
},
|
|
142
|
+
toDb: value => ValueConverters.Integer.toJson(value),
|
|
143
|
+
fieldTypeInDb: 'integer'
|
|
144
|
+
};
|
|
145
|
+
ValueConverters.Default = {
|
|
146
|
+
fromJson: x => x,
|
|
147
|
+
toJson: x => x,
|
|
148
|
+
fromDb: x => ValueConverters.JsonString.fromDb(x),
|
|
149
|
+
toDb: x => ValueConverters.JsonString.toDb(x),
|
|
150
|
+
fromInput: x => ValueConverters.Default.fromJson(x),
|
|
151
|
+
toInput: x => ValueConverters.Default.toJson(x)
|
|
152
|
+
};
|
|
153
|
+
ValueConverters.JsonString = {
|
|
154
|
+
fromJson: x => x,
|
|
155
|
+
toJson: x => x,
|
|
156
|
+
fromDb: x => x == null ? null : x ? JSON.parse(ValueConverters.JsonString.fromJson(x)) : undefined,
|
|
157
|
+
toDb: x => x !== undefined ? x === null ? null : JSON.stringify(ValueConverters.JsonString.toJson(x)) : undefined,
|
|
158
|
+
fromInput: x => ValueConverters.JsonString.fromJson(x),
|
|
159
|
+
toInput: x => ValueConverters.JsonString.toJson(x)
|
|
160
|
+
};
|
|
161
|
+
ValueConverters.JsonValue = {
|
|
162
|
+
fromJson: x => x,
|
|
163
|
+
toJson: x => x,
|
|
164
|
+
fromDb: x => x,
|
|
165
|
+
toDb: x => x,
|
|
166
|
+
fromInput: x => ValueConverters.JsonString.fromJson(x),
|
|
167
|
+
toInput: x => ValueConverters.JsonString.toJson(x),
|
|
168
|
+
fieldTypeInDb: 'json'
|
|
169
|
+
};
|
package/index.d.ts
CHANGED
|
@@ -19,4 +19,4 @@ export { Filter } from './src/filter/filter-interfaces';
|
|
|
19
19
|
export { FilterConsumerBridgeToSqlRequest } from './src/filter/filter-consumer-bridge-to-sql-request';
|
|
20
20
|
export { UrlBuilder } from './urlBuilder';
|
|
21
21
|
export { Validators } from './src/validators';
|
|
22
|
-
export { ValueConverters } from './valueConverters';
|
|
22
|
+
export { ValueConverters } from './src/valueConverters';
|
package/index.js
CHANGED
|
@@ -55,5 +55,5 @@ var urlBuilder_1 = require("./urlBuilder");
|
|
|
55
55
|
Object.defineProperty(exports, "UrlBuilder", { enumerable: true, get: function () { return urlBuilder_1.UrlBuilder; } });
|
|
56
56
|
var validators_1 = require("./src/validators");
|
|
57
57
|
Object.defineProperty(exports, "Validators", { enumerable: true, get: function () { return validators_1.Validators; } });
|
|
58
|
-
var valueConverters_1 = require("./valueConverters");
|
|
58
|
+
var valueConverters_1 = require("./src/valueConverters");
|
|
59
59
|
Object.defineProperty(exports, "ValueConverters", { enumerable: true, get: function () { return valueConverters_1.ValueConverters; } });
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "remult",
|
|
3
|
-
"version": "0.14.
|
|
3
|
+
"version": "0.14.23",
|
|
4
4
|
"description": "A CRUD framework for full-stack TypeScript",
|
|
5
5
|
"main": "index.js",
|
|
6
6
|
"types": "index.d.ts",
|
|
@@ -32,9 +32,29 @@
|
|
|
32
32
|
"require": "./remult-middleware.js",
|
|
33
33
|
"import": "./esm/remult-middleware.js"
|
|
34
34
|
},
|
|
35
|
+
"./remult-fastify": {
|
|
36
|
+
"require": "./remult-fastify.js",
|
|
37
|
+
"import": "./esm/remult-fastify.js"
|
|
38
|
+
},
|
|
39
|
+
"./postgres": {
|
|
40
|
+
"require": "./postgres/index.js",
|
|
41
|
+
"import": "./esm/postgres/index.js"
|
|
42
|
+
},
|
|
35
43
|
"./postgres/schema-builder": {
|
|
36
44
|
"require": "./postgres/schema-builder.js",
|
|
37
45
|
"import": "./esm/postgres/schema-builder.js"
|
|
46
|
+
},
|
|
47
|
+
"./remult-knex": {
|
|
48
|
+
"require": "./remult-knex.js",
|
|
49
|
+
"import": "./esm/remult-knex.js"
|
|
50
|
+
},
|
|
51
|
+
"./remult-mongo": {
|
|
52
|
+
"require": "./remult-mongo.js",
|
|
53
|
+
"import": "./esm/remult-mongo.js"
|
|
54
|
+
},
|
|
55
|
+
"./graphql": {
|
|
56
|
+
"require": "./graphql.js",
|
|
57
|
+
"import": "./esm/graphql.js"
|
|
38
58
|
}
|
|
39
59
|
}
|
|
40
60
|
}
|
|
@@ -5,7 +5,7 @@ var tslib_1 = require("tslib");
|
|
|
5
5
|
var context_1 = require("../src/context");
|
|
6
6
|
var filter_consumer_bridge_to_sql_request_1 = require("../src/filter/filter-consumer-bridge-to-sql-request");
|
|
7
7
|
var remult3_1 = require("../src/remult3");
|
|
8
|
-
var valueConverters_1 = require("../valueConverters");
|
|
8
|
+
var valueConverters_1 = require("../src/valueConverters");
|
|
9
9
|
function postgresColumnSyntax(x, dbName) {
|
|
10
10
|
var result = dbName;
|
|
11
11
|
if (x.valueType == Number) {
|
package/remult-express.d.ts
CHANGED
|
@@ -2,4 +2,10 @@ import { RemultMiddlewareOptions } from './server/expressBridge';
|
|
|
2
2
|
export declare function remultExpress(options?: RemultMiddlewareOptions & {
|
|
3
3
|
bodyParser?: boolean;
|
|
4
4
|
bodySizeLimit?: string;
|
|
5
|
-
}): import("
|
|
5
|
+
}): import("express-serve-static-core").Router & {
|
|
6
|
+
getRemult: (req: any) => Promise<import(".").Remult>;
|
|
7
|
+
openApiDoc: (options: {
|
|
8
|
+
title: string;
|
|
9
|
+
}) => any;
|
|
10
|
+
addArea: (x: any) => any;
|
|
11
|
+
};
|