@livequery/rest 1.0.22 → 1.0.86
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/RestTransporter.d.ts +6 -0
- package/build/RestTransporter.js +69 -78
- package/build/Socket.js +46 -66
- package/build/index.d.ts +2 -2
- package/build/index.js +2 -7
- package/package.json +3 -2
|
@@ -6,6 +6,12 @@ export type RestTransporterConfig = {
|
|
|
6
6
|
headers?: () => Promise<{
|
|
7
7
|
[key: string]: string;
|
|
8
8
|
}>;
|
|
9
|
+
onResponse?: (data: {
|
|
10
|
+
url: string;
|
|
11
|
+
headers: Headers;
|
|
12
|
+
body: any;
|
|
13
|
+
status: number;
|
|
14
|
+
}) => void;
|
|
9
15
|
};
|
|
10
16
|
export declare class RestTransporter implements Transporter {
|
|
11
17
|
#private;
|
package/build/RestTransporter.js
CHANGED
|
@@ -1,48 +1,29 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
});
|
|
10
|
-
};
|
|
11
|
-
var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
|
|
12
|
-
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
|
|
13
|
-
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
|
|
14
|
-
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
|
|
15
|
-
};
|
|
16
|
-
var _RestTransporter_instances, _RestTransporter_encode_query;
|
|
17
|
-
Object.defineProperty(exports, "__esModule", { value: true });
|
|
18
|
-
exports.RestTransporter = void 0;
|
|
19
|
-
const rxjs_1 = require("rxjs");
|
|
20
|
-
const operators_1 = require("rxjs/operators");
|
|
21
|
-
const rxjs_2 = require("rxjs");
|
|
22
|
-
const Socket_1 = require("./Socket");
|
|
23
|
-
const query_string_1 = require("query-string");
|
|
24
|
-
class RestTransporter {
|
|
1
|
+
import { of } from 'rxjs';
|
|
2
|
+
import { catchError, map, mergeMap } from 'rxjs/operators';
|
|
3
|
+
import { merge, Subject } from 'rxjs';
|
|
4
|
+
import { Socket } from './Socket.js';
|
|
5
|
+
import { stringify } from 'query-string';
|
|
6
|
+
export class RestTransporter {
|
|
7
|
+
config;
|
|
8
|
+
socket;
|
|
25
9
|
constructor(config) {
|
|
26
10
|
this.config = config;
|
|
27
|
-
|
|
28
|
-
config.websocket_url && (this.socket = new Socket_1.Socket(config.websocket_url));
|
|
11
|
+
config.websocket_url && (this.socket = new Socket(config.websocket_url));
|
|
29
12
|
}
|
|
30
13
|
query(ref, options) {
|
|
31
|
-
|
|
32
|
-
const
|
|
33
|
-
|
|
34
|
-
.pipe((0, operators_1.mergeMap)(() => this.call(ref, 'GET', options)), (0, operators_1.map)(({ data, error }) => {
|
|
35
|
-
var _a;
|
|
14
|
+
const $on_reload = new Subject();
|
|
15
|
+
const http_request = merge(of(1), this.socket?.$reconnect || of(), $on_reload)
|
|
16
|
+
.pipe(mergeMap(() => this.call(ref, 'GET', options)), map(({ data, error }) => {
|
|
36
17
|
if (error)
|
|
37
18
|
throw error;
|
|
38
|
-
data.realtime_token &&
|
|
19
|
+
data.realtime_token && this.socket?.subscribe(data.realtime_token);
|
|
39
20
|
// If collection
|
|
40
21
|
const collection = data;
|
|
41
22
|
if (collection.items) {
|
|
42
23
|
return {
|
|
43
24
|
data: {
|
|
44
25
|
changes: collection.items.map(data => ({ data, type: 'added', ref })),
|
|
45
|
-
paging:
|
|
26
|
+
paging: { ...collection.paging, n: 0 }
|
|
46
27
|
}
|
|
47
28
|
};
|
|
48
29
|
}
|
|
@@ -54,62 +35,72 @@ class RestTransporter {
|
|
|
54
35
|
paging: { n: 0 }
|
|
55
36
|
}
|
|
56
37
|
};
|
|
57
|
-
}),
|
|
58
|
-
const websocket_sync = (!this.socket || options._cursor) ?
|
|
59
|
-
return Object.assign(
|
|
38
|
+
}), catchError(error => of({ error })));
|
|
39
|
+
const websocket_sync = (!this.socket || options._cursor) ? of() : (this.socket.listen(ref).pipe(map((change) => ({ data: { changes: [change] } }))));
|
|
40
|
+
return Object.assign(merge(http_request, websocket_sync), {
|
|
60
41
|
reload: () => $on_reload.next()
|
|
61
42
|
});
|
|
62
43
|
}
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
44
|
+
#encode_query(query) {
|
|
45
|
+
if (!query || Object.keys(query || {}).length == 0)
|
|
46
|
+
return '';
|
|
47
|
+
const encoded_query = Object.keys(query).reduce((o, key) => ({
|
|
48
|
+
...o,
|
|
49
|
+
[key]: typeof query[key] == 'object' ? JSON.stringify(query[key]) : query[key]
|
|
50
|
+
}), {});
|
|
51
|
+
return `?${stringify(encoded_query)}`;
|
|
52
|
+
}
|
|
53
|
+
async call(url, method, query = {}, payload) {
|
|
54
|
+
const headers = {
|
|
55
|
+
...await this.config.headers?.() || {},
|
|
56
|
+
...payload ? {
|
|
67
57
|
'Content-Type': 'application/json'
|
|
68
|
-
} : {}
|
|
58
|
+
} : {},
|
|
59
|
+
...this.socket ? { socket_id: this.socket.socket_session } : {}
|
|
60
|
+
};
|
|
61
|
+
try {
|
|
62
|
+
const response = await fetch(`${this.config.base_url()}/${url}${this.#encode_query(query)}`, {
|
|
63
|
+
method,
|
|
64
|
+
headers: headers,
|
|
65
|
+
...payload ? { body: JSON.stringify(payload) } : {},
|
|
66
|
+
});
|
|
69
67
|
try {
|
|
70
|
-
const
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
}
|
|
68
|
+
const body = await response.json();
|
|
69
|
+
this.config.onResponse?.({
|
|
70
|
+
body,
|
|
71
|
+
headers: response.headers,
|
|
72
|
+
status: response.status,
|
|
73
|
+
url
|
|
74
|
+
});
|
|
75
|
+
return body;
|
|
77
76
|
}
|
|
78
|
-
catch (
|
|
79
|
-
|
|
77
|
+
catch (e) {
|
|
78
|
+
this.config.onResponse?.({
|
|
79
|
+
body: null,
|
|
80
|
+
headers: response.headers,
|
|
81
|
+
status: response.status,
|
|
82
|
+
url
|
|
83
|
+
});
|
|
84
|
+
return null;
|
|
80
85
|
}
|
|
81
|
-
}
|
|
86
|
+
}
|
|
87
|
+
catch (error) {
|
|
88
|
+
throw error;
|
|
89
|
+
}
|
|
82
90
|
}
|
|
83
|
-
get(ref, query = {}) {
|
|
84
|
-
return
|
|
85
|
-
return yield this.call(ref, 'GET', query, null);
|
|
86
|
-
});
|
|
91
|
+
async get(ref, query = {}) {
|
|
92
|
+
return await this.call(ref, 'GET', query, null);
|
|
87
93
|
}
|
|
88
|
-
add(ref, data) {
|
|
89
|
-
return
|
|
90
|
-
return yield this.call(ref, 'POST', {}, data);
|
|
91
|
-
});
|
|
94
|
+
async add(ref, data) {
|
|
95
|
+
return await this.call(ref, 'POST', {}, data);
|
|
92
96
|
}
|
|
93
|
-
update(ref, data, method = 'PATCH') {
|
|
94
|
-
return
|
|
95
|
-
return yield this.call(ref, method, {}, data);
|
|
96
|
-
});
|
|
97
|
+
async update(ref, data, method = 'PATCH') {
|
|
98
|
+
return await this.call(ref, method, {}, data);
|
|
97
99
|
}
|
|
98
|
-
remove(ref) {
|
|
99
|
-
return
|
|
100
|
-
return yield this.call(ref, 'DELETE');
|
|
101
|
-
});
|
|
100
|
+
async remove(ref) {
|
|
101
|
+
return await this.call(ref, 'DELETE');
|
|
102
102
|
}
|
|
103
|
-
trigger(ref, name, query, payload) {
|
|
104
|
-
return
|
|
105
|
-
return yield this.call(`${ref}/~${name}`, 'POST', query, payload);
|
|
106
|
-
});
|
|
103
|
+
async trigger(ref, name, query, payload) {
|
|
104
|
+
return await this.call(`${ref}/~${name}`, 'POST', query, payload);
|
|
107
105
|
}
|
|
108
106
|
}
|
|
109
|
-
exports.RestTransporter = RestTransporter;
|
|
110
|
-
_RestTransporter_instances = new WeakSet(), _RestTransporter_encode_query = function _RestTransporter_encode_query(query) {
|
|
111
|
-
if (!query || Object.keys(query || {}).length == 0)
|
|
112
|
-
return '';
|
|
113
|
-
const encoded_query = Object.keys(query).reduce((o, key) => (Object.assign(Object.assign({}, o), { [key]: typeof query[key] == 'object' ? JSON.stringify(query[key]) : query[key] })), {});
|
|
114
|
-
return `?${(0, query_string_1.stringify)(encoded_query)}`;
|
|
115
|
-
};
|
package/build/Socket.js
CHANGED
|
@@ -1,42 +1,55 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
const
|
|
21
|
-
|
|
22
|
-
|
|
1
|
+
import { firstValueFrom, fromEvent, Subject, merge, ReplaySubject } from "rxjs";
|
|
2
|
+
import { finalize } from "rxjs/operators";
|
|
3
|
+
import { v4 } from 'uuid';
|
|
4
|
+
export class Socket {
|
|
5
|
+
ws_url_fatory;
|
|
6
|
+
topics = new Map();
|
|
7
|
+
$input = new ReplaySubject(1000);
|
|
8
|
+
$reconnect = new Subject();
|
|
9
|
+
socket_session = v4();
|
|
10
|
+
async #init() {
|
|
11
|
+
if (typeof WebSocket == 'undefined')
|
|
12
|
+
return;
|
|
13
|
+
for (let n = 0; true; n++) {
|
|
14
|
+
console.log('Connecting websocket .... ');
|
|
15
|
+
const ws = new WebSocket(await this.ws_url_fatory());
|
|
16
|
+
const messages_handler = fromEvent(ws, 'message').subscribe((evt) => {
|
|
17
|
+
const { data, event } = JSON.parse(evt.data);
|
|
18
|
+
this[`$${event}`]?.(data);
|
|
19
|
+
});
|
|
20
|
+
const data_sender = fromEvent(ws, 'open').subscribe(() => {
|
|
21
|
+
console.log(n == 0 ? 'Websocket connected' : 'Websocket re-connected');
|
|
22
|
+
ws.send(JSON.stringify({ event: 'start', data: { id: this.socket_session } }));
|
|
23
|
+
const subscription = this.$input.subscribe(data => ws.send(JSON.stringify(data)));
|
|
24
|
+
n > 0 && this.$reconnect.next();
|
|
25
|
+
return () => {
|
|
26
|
+
subscription.unsubscribe();
|
|
27
|
+
this.$input.complete();
|
|
28
|
+
};
|
|
29
|
+
});
|
|
30
|
+
await firstValueFrom(merge(fromEvent(ws, 'error'), fromEvent(ws, 'close'), fromEvent(ws, 'closed')));
|
|
31
|
+
this.$input = new ReplaySubject(1000);
|
|
32
|
+
data_sender.unsubscribe();
|
|
33
|
+
messages_handler.unsubscribe();
|
|
34
|
+
ws.close();
|
|
35
|
+
console.log(`Websocket connection dropped, reconnect in 1s ...`);
|
|
36
|
+
await new Promise(s => setTimeout(s, 1000));
|
|
37
|
+
}
|
|
38
|
+
}
|
|
23
39
|
constructor(ws_url_fatory) {
|
|
24
40
|
this.ws_url_fatory = ws_url_fatory;
|
|
25
|
-
|
|
26
|
-
this.topics = new Map();
|
|
27
|
-
this.$input = new rxjs_1.ReplaySubject(1000);
|
|
28
|
-
this.$reconnect = new rxjs_1.Subject();
|
|
29
|
-
this.socket_session = (0, uuid_1.v4)();
|
|
30
|
-
__classPrivateFieldGet(this, _Socket_instances, "m", _Socket_init).call(this);
|
|
41
|
+
this.#init();
|
|
31
42
|
}
|
|
32
43
|
$sync(data) {
|
|
33
|
-
var _a, _b;
|
|
34
44
|
for (const change of data.changes) {
|
|
35
45
|
// Collection ref broadcast
|
|
36
|
-
|
|
46
|
+
this.topics.get(change.ref)?.stream.next(change);
|
|
37
47
|
// Document ref broadcast
|
|
38
48
|
const ref = `${change.ref}/${change.data.id}`;
|
|
39
|
-
|
|
49
|
+
this.topics.get(ref)?.stream.next({
|
|
50
|
+
...change,
|
|
51
|
+
ref
|
|
52
|
+
});
|
|
40
53
|
}
|
|
41
54
|
}
|
|
42
55
|
subscribe(realtime_token) {
|
|
@@ -44,11 +57,11 @@ class Socket {
|
|
|
44
57
|
}
|
|
45
58
|
listen(ref) {
|
|
46
59
|
if (!this.topics.has(ref)) {
|
|
47
|
-
const stream = new
|
|
60
|
+
const stream = new Subject();
|
|
48
61
|
this.topics.set(ref, { stream, listen_count: 0 });
|
|
49
62
|
}
|
|
50
63
|
this.topics.get(ref).listen_count++;
|
|
51
|
-
return this.topics.get(ref).stream.pipe(
|
|
64
|
+
return this.topics.get(ref).stream.pipe(finalize(() => {
|
|
52
65
|
this.topics.get(ref).listen_count--;
|
|
53
66
|
setTimeout(() => {
|
|
54
67
|
if (this.topics.get(ref).listen_count == 0) {
|
|
@@ -58,36 +71,3 @@ class Socket {
|
|
|
58
71
|
}));
|
|
59
72
|
}
|
|
60
73
|
}
|
|
61
|
-
exports.Socket = Socket;
|
|
62
|
-
_Socket_instances = new WeakSet(), _Socket_init = function _Socket_init() {
|
|
63
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
64
|
-
if (typeof WebSocket == 'undefined')
|
|
65
|
-
return;
|
|
66
|
-
for (let n = 0; true; n++) {
|
|
67
|
-
console.log('Connecting websocket .... ');
|
|
68
|
-
const ws = new WebSocket(yield this.ws_url_fatory());
|
|
69
|
-
const messages_handler = (0, rxjs_1.fromEvent)(ws, 'message').subscribe((evt) => {
|
|
70
|
-
var _a;
|
|
71
|
-
const { data, event } = JSON.parse(evt.data);
|
|
72
|
-
(_a = this[`$${event}`]) === null || _a === void 0 ? void 0 : _a.call(this, data);
|
|
73
|
-
});
|
|
74
|
-
const data_sender = (0, rxjs_1.fromEvent)(ws, 'open').subscribe(() => {
|
|
75
|
-
console.log(n == 0 ? 'Websocket connected' : 'Websocket re-connected');
|
|
76
|
-
ws.send(JSON.stringify({ event: 'start', data: { id: this.socket_session } }));
|
|
77
|
-
const subscription = this.$input.subscribe(data => ws.send(JSON.stringify(data)));
|
|
78
|
-
n > 0 && this.$reconnect.next();
|
|
79
|
-
return () => {
|
|
80
|
-
subscription.unsubscribe();
|
|
81
|
-
this.$input.complete();
|
|
82
|
-
};
|
|
83
|
-
});
|
|
84
|
-
yield (0, rxjs_1.firstValueFrom)((0, rxjs_1.merge)((0, rxjs_1.fromEvent)(ws, 'error'), (0, rxjs_1.fromEvent)(ws, 'close'), (0, rxjs_1.fromEvent)(ws, 'closed')));
|
|
85
|
-
this.$input = new rxjs_1.ReplaySubject(1000);
|
|
86
|
-
data_sender.unsubscribe();
|
|
87
|
-
messages_handler.unsubscribe();
|
|
88
|
-
ws.close();
|
|
89
|
-
console.log(`Websocket connection dropped, reconnect in 1s ...`);
|
|
90
|
-
yield new Promise(s => setTimeout(s, 1000));
|
|
91
|
-
}
|
|
92
|
-
});
|
|
93
|
-
};
|
package/build/index.d.ts
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
export { RestTransporter } from './RestTransporter';
|
|
2
|
-
export { Socket } from './Socket';
|
|
1
|
+
export { RestTransporter } from './RestTransporter.js';
|
|
2
|
+
export { Socket } from './Socket.js';
|
package/build/index.js
CHANGED
|
@@ -1,7 +1,2 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
exports.Socket = exports.RestTransporter = void 0;
|
|
4
|
-
var RestTransporter_1 = require("./RestTransporter");
|
|
5
|
-
Object.defineProperty(exports, "RestTransporter", { enumerable: true, get: function () { return RestTransporter_1.RestTransporter; } });
|
|
6
|
-
var Socket_1 = require("./Socket");
|
|
7
|
-
Object.defineProperty(exports, "Socket", { enumerable: true, get: function () { return Socket_1.Socket; } });
|
|
1
|
+
export { RestTransporter } from './RestTransporter.js';
|
|
2
|
+
export { Socket } from './Socket.js';
|
package/package.json
CHANGED
|
@@ -3,7 +3,8 @@
|
|
|
3
3
|
"repository": {
|
|
4
4
|
"url": "https://github.com/livequery/rest"
|
|
5
5
|
},
|
|
6
|
-
"version": "1.0.
|
|
6
|
+
"version": "1.0.86",
|
|
7
|
+
"type": "module",
|
|
7
8
|
"description": "",
|
|
8
9
|
"main": "build/index.js",
|
|
9
10
|
"types": "build/index.d.ts",
|
|
@@ -18,7 +19,7 @@
|
|
|
18
19
|
"uuid": "^8.3.2"
|
|
19
20
|
},
|
|
20
21
|
"devDependencies": {
|
|
21
|
-
"@livequery/types": "1.0.
|
|
22
|
+
"@livequery/types": "1.0.82"
|
|
22
23
|
},
|
|
23
24
|
"peerDependencies": {},
|
|
24
25
|
"scripts": {
|