@auxilium/datalynk-client 0.4.5 → 0.4.7
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/README.md +276 -33
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -4,13 +4,21 @@
|
|
|
4
4
|
|
|
5
5
|
---
|
|
6
6
|
|
|
7
|
-
Datalynk client library to integrate JavaScript clients with the Datalynk API
|
|
7
|
+
Datalynk client library to integrate JavaScript clients with the Datalynk API.
|
|
8
8
|
|
|
9
9
|
## Table of Contents
|
|
10
10
|
- [Datalynk Client Library](#datalynk-client-library)
|
|
11
11
|
- [Table of Contents](#Table-of-Contents)
|
|
12
12
|
- [Quick Start](#quick-start)
|
|
13
|
-
- [
|
|
13
|
+
- [Documentation](#documentation)
|
|
14
|
+
- [Integration](#integration)
|
|
15
|
+
- [Angular](#integration)
|
|
16
|
+
- [Node / Vue](#integration)
|
|
17
|
+
- [Vanalia JS](#integration)
|
|
18
|
+
- [Build Models](#build-models)
|
|
19
|
+
- [Authentication](#authentication)
|
|
20
|
+
- [Slice Engine](#slice-engine)
|
|
21
|
+
- [Sockets](#sockets)
|
|
14
22
|
|
|
15
23
|
## Quick Start
|
|
16
24
|
1. Install the client library
|
|
@@ -29,45 +37,280 @@ Password: ********
|
|
|
29
37
|
|
|
30
38
|
3. Create an API object & start making requests
|
|
31
39
|
```js
|
|
32
|
-
import {API} from '@auxilium/datalynk-client'
|
|
33
|
-
import {User} from './models/User.model'; // Created automatically in Step 2
|
|
34
|
-
import {Slices} from './models/slices'; // Created automatically in Step 2
|
|
40
|
+
import {API} from '@auxilium/datalynk-client';
|
|
35
41
|
|
|
36
42
|
const api = new API('https://spoke.auxiliumgroup.com');
|
|
37
|
-
const resp = await api.
|
|
43
|
+
const resp = await api.request({'$/auth/current':{}});
|
|
38
44
|
```
|
|
39
45
|
|
|
40
|
-
##
|
|
41
|
-
```typescript
|
|
42
|
-
// Login
|
|
43
|
-
const user = await api.auth.login('spoke', 'username', 'password');
|
|
46
|
+
## Documentation
|
|
44
47
|
|
|
45
|
-
|
|
46
|
-
|
|
48
|
+
<details>
|
|
49
|
+
<summary>
|
|
50
|
+
<h3 id="integration" style="display: inline">Integration</h3>
|
|
51
|
+
</summary>
|
|
47
52
|
|
|
48
|
-
|
|
49
|
-
const rows = await api.slice<T>(12345).select().exec().rows();
|
|
50
|
-
const row = await api.slice<T>(12345).select(12345).exec().row();
|
|
53
|
+
This library is written with vanilia JS & has no framework dependencies allowing easy integration with any front-end website. Here is some boilerplate to get you going:
|
|
51
54
|
|
|
52
|
-
|
|
53
|
-
const key = await api.slice<Contact>(12345).insert({first: 'Bilbo', last: 'Baggins'}).exec().key();
|
|
54
|
-
const keys = await api.slice<Contacts>(12345).insert([
|
|
55
|
-
{first: 'Darth', last: 'Vader'},
|
|
56
|
-
{first: 'John', last: 'Snow'}
|
|
57
|
-
]).exec().keys();
|
|
55
|
+
#### Angular
|
|
58
56
|
|
|
59
|
-
|
|
60
|
-
const success = await api.slice(12345).update(
|
|
61
|
-
{id: 1, first: 'Adam', last: 'Baxter'}
|
|
62
|
-
).exec().key();
|
|
57
|
+
**File:** `/src/services/datalynk.service.ts`
|
|
63
58
|
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
59
|
+
```ts
|
|
60
|
+
import {Injectable} from '@angular/core';
|
|
61
|
+
import {Api, Slice} from '@auxilium/datalynk-client';
|
|
62
|
+
import {environment} from '../environment/environment';
|
|
63
|
+
import {Contact} from '../models/contact';
|
|
64
|
+
import {Slices} from '../models/slices';
|
|
65
|
+
|
|
66
|
+
declare global {
|
|
67
|
+
interface Window {
|
|
68
|
+
api: Api;
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
@Injectable({providedIn: 'root'})
|
|
73
|
+
export class DatalynkApi extends Api {
|
|
74
|
+
contacts!: Slice<Contact>;
|
|
75
|
+
|
|
76
|
+
constructor() {
|
|
77
|
+
super(environment.api, {/* options */});
|
|
78
|
+
window.api = this;
|
|
79
|
+
|
|
80
|
+
this.handleLogin('spoke', {/* login UI options */});
|
|
81
|
+
|
|
82
|
+
// Create store to cache slice data
|
|
83
|
+
this.contacts = this.slice<Contact>(Slices.Contact);
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
```
|
|
87
|
+
|
|
88
|
+
#### Node / Vue
|
|
89
|
+
|
|
90
|
+
**File:** `/src/services/datalynk.service.ts`
|
|
91
|
+
|
|
92
|
+
```ts
|
|
93
|
+
import {Api} from '@auxilium/datalynk-client';
|
|
94
|
+
import {environment} from '../environment/environment';
|
|
95
|
+
import {Contact} from '../models/contact';
|
|
96
|
+
import {Slices} from '../models/slices';
|
|
97
|
+
|
|
98
|
+
export const api = new Api(environment.api, {/* options */});
|
|
99
|
+
// Create store to cache slice data
|
|
100
|
+
export const contacts = api.slice<Contact>(Slices.Contact);
|
|
101
|
+
```
|
|
102
|
+
|
|
103
|
+
#### Vanilia JS
|
|
104
|
+
|
|
105
|
+
**File:** `/index.html`
|
|
106
|
+
|
|
107
|
+
```html
|
|
108
|
+
<script type="module">
|
|
109
|
+
import {Api} from '@auxilium/datlaynk-client/dist/index.mjs';
|
|
110
|
+
|
|
111
|
+
var api = new Api('https://spoke.auxiliumgroup.com', /* options */);
|
|
112
|
+
// Create store to cache slice data
|
|
113
|
+
var contacts = api.slice(12345);
|
|
114
|
+
</script>
|
|
68
115
|
|
|
69
|
-
// Advanced example - Add flag to underage users
|
|
70
|
-
const users = await api.slice(12345).select().exec().rows();
|
|
71
|
-
users = users.map(user => ({...user, underage: user.age < 18}));
|
|
72
|
-
api.slice(1245).update(users).exec();
|
|
73
116
|
```
|
|
117
|
+
|
|
118
|
+
</details>
|
|
119
|
+
|
|
120
|
+
<details>
|
|
121
|
+
<summary>
|
|
122
|
+
<h3 id="build-models" style="display: inline">Build Models</h3>
|
|
123
|
+
</summary>
|
|
124
|
+
|
|
125
|
+
This library comes with a command line tool for developers to automatically create Typescript models from the Datalynk metadata.
|
|
126
|
+
|
|
127
|
+
This takes most of the manual labour out of manually mapping the data & provides type safety.
|
|
128
|
+
|
|
129
|
+
1. Simply run the tool:
|
|
130
|
+
```bash
|
|
131
|
+
$ npx build-models
|
|
132
|
+
Output (src/models):
|
|
133
|
+
Spoke: spoke
|
|
134
|
+
Login: username
|
|
135
|
+
Password: ********
|
|
136
|
+
```
|
|
137
|
+
|
|
138
|
+
2. Import models:
|
|
139
|
+
```ts
|
|
140
|
+
import {Slices} from 'models/slices'; // Import slices map
|
|
141
|
+
import {Contact} from 'models/contact'; // Import model for slice we will be using
|
|
142
|
+
|
|
143
|
+
const contacts: Contact[] = await api.slice<Contact>(Slices.Contact)
|
|
144
|
+
.select()
|
|
145
|
+
.exec().rows();
|
|
146
|
+
```
|
|
147
|
+
|
|
148
|
+
</details>
|
|
149
|
+
|
|
150
|
+
<details>
|
|
151
|
+
<summary>
|
|
152
|
+
<h3 id="authentication" style="display: inline">Authentication</h3>
|
|
153
|
+
</summary>
|
|
154
|
+
|
|
155
|
+
#### Login flow
|
|
156
|
+
|
|
157
|
+
This library comes with some logic to automatically handle the login flow & should be called at the startup of your application:
|
|
158
|
+
|
|
159
|
+
1. It will check the URL for a token param: `?datalynkToken=...`
|
|
160
|
+
2. It will check the localStorage for a saved token
|
|
161
|
+
3. It will prompt the user to login via UI
|
|
162
|
+
4. Reload page if token changed
|
|
163
|
+
```js
|
|
164
|
+
await api.auth.handleLogin('spoke', {
|
|
165
|
+
background: 'url("...")', // CSS URL or hex color
|
|
166
|
+
color: '#ff0000', // hex color
|
|
167
|
+
title: '<img alt="logo" src="..." />', // text or HTML
|
|
168
|
+
titleColor: '#ffffff' // Color of title text
|
|
169
|
+
});
|
|
170
|
+
```
|
|
171
|
+
|
|
172
|
+
#### Login UI
|
|
173
|
+
|
|
174
|
+
Alternatively you can manage the login prompt manually:
|
|
175
|
+
|
|
176
|
+
```js
|
|
177
|
+
const prompt = api.auth.loginPrompt('spoke', options);
|
|
178
|
+
await prompt.wait; // Wait for the user to login/close the prompt
|
|
179
|
+
prompt.close(); // Close prompt manually
|
|
180
|
+
```
|
|
181
|
+
|
|
182
|
+
#### Programatically
|
|
183
|
+
|
|
184
|
+
Manually login programatically:
|
|
185
|
+
|
|
186
|
+
```js
|
|
187
|
+
const user = await api.auth.login('spoke', 'username', 'password', '2faCode');
|
|
188
|
+
```
|
|
189
|
+
|
|
190
|
+
</details>
|
|
191
|
+
|
|
192
|
+
<details>
|
|
193
|
+
<summary>
|
|
194
|
+
<h3 id="" style="display: inline">Slice Engine</h3>
|
|
195
|
+
</summary>
|
|
196
|
+
|
|
197
|
+
This library comes with LINQ style query language to help make interacting with Slices easier by providing types & intelisense.
|
|
198
|
+
|
|
199
|
+
#### Select
|
|
200
|
+
|
|
201
|
+
```ts
|
|
202
|
+
// Get a single record
|
|
203
|
+
const row = await api.slice<T>(12345)
|
|
204
|
+
.select(12345)
|
|
205
|
+
.exec().row();
|
|
206
|
+
|
|
207
|
+
// Get all slice records
|
|
208
|
+
const rows = await api.slice<T>(12345)
|
|
209
|
+
.select()
|
|
210
|
+
.exec().rows();
|
|
211
|
+
|
|
212
|
+
// Advanced queries
|
|
213
|
+
const rows = await api.slice<T>(12345)
|
|
214
|
+
.select()
|
|
215
|
+
.where('field1', '==', 'value')
|
|
216
|
+
.fields({'field1': 'field2'})
|
|
217
|
+
.order('field2', true /* ascending */)
|
|
218
|
+
.limit(10)
|
|
219
|
+
.exec().rows();
|
|
220
|
+
```
|
|
221
|
+
|
|
222
|
+
#### Insert
|
|
223
|
+
|
|
224
|
+
```ts
|
|
225
|
+
// Insert record
|
|
226
|
+
const key = await api.slice<Contact>(12345)
|
|
227
|
+
.insert({first: 'Bilbo', last: 'Baggins'})
|
|
228
|
+
.exec().key();
|
|
229
|
+
|
|
230
|
+
// Insert multiple rows
|
|
231
|
+
const keys = await api.slice<Contacts>(12345)
|
|
232
|
+
.insert([
|
|
233
|
+
{first: 'Darth', last: 'Vader'},
|
|
234
|
+
{first: 'John', last: 'Snow'}
|
|
235
|
+
])
|
|
236
|
+
.exec().keys();
|
|
237
|
+
```
|
|
238
|
+
|
|
239
|
+
#### Update
|
|
240
|
+
|
|
241
|
+
```ts
|
|
242
|
+
// Update a record
|
|
243
|
+
const success = await api.slice(12345)
|
|
244
|
+
.update({id: 1, first: 'James', last: 'Kirk'})
|
|
245
|
+
.exec().key();
|
|
246
|
+
|
|
247
|
+
// Update multiple rows with where
|
|
248
|
+
await api.slice(12345)
|
|
249
|
+
.update({evil: true})
|
|
250
|
+
.where({first: 'Darth'})
|
|
251
|
+
.exec().keys();
|
|
252
|
+
```
|
|
253
|
+
|
|
254
|
+
#### Delete
|
|
255
|
+
|
|
256
|
+
```ts
|
|
257
|
+
// Delete a record
|
|
258
|
+
const success = await api.slice(12345)
|
|
259
|
+
.delete(12345)
|
|
260
|
+
.exec().key();
|
|
261
|
+
|
|
262
|
+
// Dlete multiple rows with where
|
|
263
|
+
await api.slice(12345)
|
|
264
|
+
.delete()
|
|
265
|
+
.where({first: 'Darth'})
|
|
266
|
+
.exec().keys();
|
|
267
|
+
```
|
|
268
|
+
|
|
269
|
+
</details>
|
|
270
|
+
|
|
271
|
+
<details>
|
|
272
|
+
<summary>
|
|
273
|
+
<h3 id="" style="display: inline">Sockets</h3>
|
|
274
|
+
</summary>
|
|
275
|
+
|
|
276
|
+
|
|
277
|
+
#### Options
|
|
278
|
+
|
|
279
|
+
The socket can have it's endpoint overriden or be turned off by setting it to false:
|
|
280
|
+
```ts
|
|
281
|
+
const api = new Api('https://spoke.auxiliumgroup.com', {
|
|
282
|
+
socket: false, // Disable
|
|
283
|
+
// socket: 'http://localhost:3000', // Override
|
|
284
|
+
});
|
|
285
|
+
```
|
|
286
|
+
|
|
287
|
+
#### Slice Engine
|
|
288
|
+
|
|
289
|
+
The Slice Engine's cache can be sycned with the server & subscribed to using [RXJS](https://rxjs.dev):
|
|
290
|
+
|
|
291
|
+
```ts
|
|
292
|
+
// Create cache/store
|
|
293
|
+
const contacts = api.slice<Contact>(Slices.Contact);
|
|
294
|
+
|
|
295
|
+
// Enable syncing
|
|
296
|
+
contacts.sync();
|
|
297
|
+
|
|
298
|
+
// Use RXJS to listen for events
|
|
299
|
+
contacts.sync().pipe(...).subscribe((cache: Contact[]) => {...});
|
|
300
|
+
// Or using Angular templates
|
|
301
|
+
'{{ contacts.sync() | async }}'
|
|
302
|
+
|
|
303
|
+
// Disable syncing
|
|
304
|
+
contacts.sync(false);
|
|
305
|
+
```
|
|
306
|
+
|
|
307
|
+
#### Socket Events
|
|
308
|
+
|
|
309
|
+
Alternatively socket events can be listened to directly using callbacks:
|
|
310
|
+
|
|
311
|
+
```ts
|
|
312
|
+
api.socket.sliceEvents(123, callbackFn(event)); // Listen to a specific slice
|
|
313
|
+
api.socket.addListener(callbackFn(event)); // listen to all socket events
|
|
314
|
+
```
|
|
315
|
+
|
|
316
|
+
</details>
|
package/package.json
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
"name": "@auxilium/datalynk-client",
|
|
3
3
|
"description": "Datalynk client library",
|
|
4
4
|
"repository": "https://gitlab.auxiliumgroup.com/ztimson/datalynk-client",
|
|
5
|
-
"version": "0.4.
|
|
5
|
+
"version": "0.4.7",
|
|
6
6
|
"author": "Zak Timson",
|
|
7
7
|
"private": false,
|
|
8
8
|
"main": "./dist/index.cjs",
|