pryv 2.2.0 → 2.3.2
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 +291 -299
- package/package.json +11 -45
- package/src/Auth/AuthController.js +43 -50
- package/src/Auth/AuthStates.js +12 -12
- package/src/Auth/LoginMessages.js +17 -14
- package/src/Auth/index.js +18 -15
- package/src/Browser/CookieUtils.js +37 -27
- package/src/Browser/LoginButton.js +42 -37
- package/src/Browser/index.js +16 -42
- package/src/Connection.js +102 -95
- package/src/Service.js +47 -45
- package/src/ServiceAssets.js +42 -34
- package/src/browser-index-bundle.js +8 -0
- package/src/browser-index.js +7 -0
- package/src/index.d.ts +37 -48
- package/src/index.js +20 -3
- package/src/lib/browser-getEventStreamed.js +21 -19
- package/src/lib/json-parser.js +23 -24
- package/src/utils.js +55 -43
- package/test/Browser.AuthController.test.js +19 -21
- package/test/Browser.test.js +23 -26
- package/test/Connection.test.js +135 -151
- package/test/Service.test.js +30 -44
- package/test/ServiceAssets.test.js +16 -22
- package/test/browser-index.html +26 -0
- package/test/utils.test.js +30 -35
- package/.jsdoc-conf.json +0 -29
- package/.mocharc.js +0 -13
- package/LICENSE.md +0 -27
- package/scripts/setup-environment-dev.sh +0 -28
- package/scripts/upload.sh +0 -15
- package/src/Pryv.js +0 -19
- package/src/index-socket.io-monitor.js +0 -4
- package/src/index.html +0 -17
- package/test/browser-index.js +0 -11
- package/test/browser-tests.html +0 -31
- package/test/helpers.js +0 -8
- package/test/load-test-account.js +0 -108
- package/test/test-data.js +0 -95
- package/web-demos/auth-with-redirection.html +0 -72
- package/web-demos/auth.html +0 -77
- package/web-demos/custom-login-button.html +0 -158
- package/web-demos/index.html +0 -186
- package/web-demos/service-info.json +0 -13
- package/web-demos/stream-examples.html +0 -80
- package/webpack.config.js +0 -83
package/README.md
CHANGED
|
@@ -1,120 +1,97 @@
|
|
|
1
|
-
#
|
|
1
|
+
# `pryv`: JS library for Pryv.io
|
|
2
|
+
|
|
3
|
+
JavaScript library and add-ons for writing Node.js and browser apps connecting to a Pryv.io platform. It follows the [Pryv.io app guidelines](https://api.pryv.com/guides/app-guidelines/).
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
## Table of Contents <!-- omit in toc -->
|
|
7
|
+
|
|
8
|
+
1. [Usage](#usage)
|
|
9
|
+
1. [Importing](#importing)
|
|
10
|
+
2. [Quick example](#quick-example)
|
|
11
|
+
3. [Obtaining a `pryv.Connection`](#obtaining-a-pryvconnection)
|
|
12
|
+
4. [API calls](#api-calls)
|
|
13
|
+
5. [Get events streamed](#get-events-streamed)
|
|
14
|
+
6. [Events with attachments](#events-with-attachments)
|
|
15
|
+
7. [High Frequency (HF) events](#high-frequency-hf-events)
|
|
16
|
+
8. [Service information and assets](#service-information-and-assets)
|
|
17
|
+
9. [`pryv.Browser` & visual assets](#pryvbrowser--visual-assets)
|
|
18
|
+
10. [Customize the authentication process](#customize-the-authentication-process)
|
|
19
|
+
11. [Running examples locally](#running-examples-locally)
|
|
20
|
+
2. [Contributing](#contributing)
|
|
21
|
+
1. [Installation](#installation)
|
|
22
|
+
2. [Dev environment basics](#dev-environment-basics)
|
|
23
|
+
3. [Building for the browser](#building-for-the-browser)
|
|
24
|
+
4. [Testing](#testing)
|
|
25
|
+
5. [Publishing](#publishing)
|
|
26
|
+
3. [Changelog](#changelog)
|
|
27
|
+
4. [License](#license)
|
|
2
28
|
|
|
3
|
-
This JavaScript library is meant to facilitate writing NodeJS and browser apps for a Pryv.io platform, it follows the [Pryv.io App Guidelines](https://api.pryv.com/guides/app-guidelines/).
|
|
4
29
|
|
|
5
|
-
##
|
|
6
|
-
|
|
7
|
-
*Prerequisites*: Node 12
|
|
8
|
-
|
|
9
|
-
- Setup: `npm run setup`
|
|
10
|
-
|
|
11
|
-
- Build pryv.js library for browsers: `npm run build`, the result is published in `./dist`
|
|
12
|
-
|
|
13
|
-
- Build documentation: `npm run doc`, the result is published in `./dist/docs`
|
|
14
|
-
|
|
15
|
-
Note: as per v2.1.7 `jsdoc` dev dependency has been removed from package.json .. it should be installed with `npm install jsoc --dev`
|
|
30
|
+
## Usage
|
|
16
31
|
|
|
17
|
-
- Node Tests: `npm run test`
|
|
18
32
|
|
|
19
|
-
|
|
33
|
+
### Importing
|
|
20
34
|
|
|
21
|
-
|
|
35
|
+
#### NPM
|
|
22
36
|
|
|
23
|
-
|
|
37
|
+
`npm install --save pryv`, then in your code:
|
|
24
38
|
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
+ [Import](#import)
|
|
30
|
-
- [Browser](#browser)
|
|
31
|
-
- [Node.js](#nodejs)
|
|
32
|
-
+ [Obtaining a Pryv.Connection](#obtaining-a-pryvconnection)
|
|
33
|
-
- [Using an API endpoint](#using-an-api-endpoint)
|
|
34
|
-
- [Using a Username & Token (knowing the service information URL)](#using-a-username--token-knowing-the-service-information-url)
|
|
35
|
-
- [Within a WebPage with a login button](#within-a-webpage-with-a-login-button)
|
|
36
|
-
- [Fetch access info](#fetch-access-info)
|
|
37
|
-
- [Using Service.login() *(trusted apps only)*](#using-servicelogin-trusted-apps-only)
|
|
38
|
-
- [Performing the authentication request with your own UI](#customize-auth-process)
|
|
39
|
-
+ [API calls](#api-calls)
|
|
40
|
-
+ [Advanced usage of API calls with optional individual result and progress callbacks](#advanced-usage-of-api-calls-with-optional-individual-result-and-progress-callbacks)
|
|
41
|
-
+ [Get Events Streamed](#get-events-streamed)
|
|
42
|
-
- [Example](#example)
|
|
43
|
-
- [result](#result)
|
|
44
|
-
+ [Events with Attachments](#events-with-attachments)
|
|
45
|
-
- [Node.js](#nodejs-1)
|
|
46
|
-
- [Browser](#browser-1)
|
|
47
|
-
+ [High Frequency Events](#high-frequency-events)
|
|
48
|
-
+ [Service Information and assets](#service-information-and-assets)
|
|
49
|
-
- [Pryv.Service](#pryvservice)
|
|
50
|
-
* [Initizalization with a service info URL](#initizalization-with-a-service-info-url)
|
|
51
|
-
* [Usage of Pryv.Service.](#usage-of-pryvservice)
|
|
52
|
-
+ [Pryv.Browser & Visual assets](#pryvbrowser--visual-assets)
|
|
53
|
-
- [Pryv.Browser - retrieve serviceInfo from query URL](#pryvbrowser---retrieve-serviceinfo-from-query-url)
|
|
54
|
-
- [Visual assets](#visual-assets)
|
|
55
|
-
+ [Customize Auth process](#customize-auth-process)
|
|
56
|
-
- [Using a custom login button](using-a-custom-login-button)
|
|
57
|
-
- [Redirect user to the authentication page](#redirect-user-to-the-authentication-page)
|
|
58
|
-
+ [Launch web demos locally](#launch-web-demos-locally)
|
|
59
|
-
|
|
60
|
-
### Import
|
|
39
|
+
```js
|
|
40
|
+
const pryv = require('pryv');
|
|
41
|
+
```
|
|
61
42
|
|
|
62
|
-
####
|
|
43
|
+
#### `<script>` tag
|
|
63
44
|
|
|
64
45
|
```html
|
|
65
46
|
<script src="https://api.pryv.com/lib-js/pryv.js"></script>
|
|
66
47
|
```
|
|
67
48
|
|
|
68
|
-
|
|
49
|
+
Other distributions available:
|
|
69
50
|
|
|
70
51
|
- ES6: `https://api.pryv.com/lib-js/pryv-es6.js`
|
|
71
|
-
-
|
|
72
|
-
This library can be extended with two packages:
|
|
73
|
-
- Socket.io extension: [https://github.com/pryv/lib-js-socket.io](https://github.com/pryv/lib-js-socket.io)
|
|
74
|
-
- Monitor extension: [https://github.com/pryv/lib-js-monitor](https://github.com/pryv/lib-js-monitor)
|
|
52
|
+
- Library bundled with Socket.IO and Monitor add-ons: `https://api.pryv.com/lib-js/pryv-socket.io-monitor.js`.
|
|
75
53
|
|
|
76
|
-
####
|
|
54
|
+
#### Add-ons
|
|
77
55
|
|
|
78
|
-
-
|
|
56
|
+
- Socket.IO: [NPM package](https://www.npmjs.com/package/@pryv/socket.io), [README](https://github.com/pryv/lib-js/tree/master/components/pryv-socket.io#readme)
|
|
57
|
+
- Monitor: [NPM package](https://www.npmjs.com/package/@pryv/monitor), [README](https://github.com/pryv/lib-js/tree/master/components/pryv-monitor#readme)
|
|
79
58
|
|
|
80
|
-
#### Node.js
|
|
81
59
|
|
|
82
|
-
|
|
60
|
+
### Quick example
|
|
61
|
+
|
|
62
|
+
- [A simple form to save notes and measurements (CodePen)](https://codepen.io/pryv/pen/ExVYemE)
|
|
83
63
|
|
|
84
|
-
```javascript
|
|
85
|
-
const Pryv = require('pryv');
|
|
86
|
-
```
|
|
87
64
|
|
|
88
|
-
### Obtaining a
|
|
65
|
+
### Obtaining a `pryv.Connection`
|
|
89
66
|
|
|
90
67
|
A connection is an authenticated link to a Pryv.io account.
|
|
91
68
|
|
|
92
|
-
####
|
|
69
|
+
#### With an API endpoint
|
|
93
70
|
|
|
94
|
-
The format of the API endpoint can be found in your platform's [service information](https://api.pryv.com/reference/#service-info) under the `api` property.
|
|
71
|
+
The format of the API endpoint can be found in your platform's [service information](https://api.pryv.com/reference/#service-info) under the `api` property. It usually looks like: `https://{token}@{hostname}`
|
|
95
72
|
|
|
96
|
-
```
|
|
73
|
+
```js
|
|
97
74
|
const apiEndpoint = 'https://ck6bwmcar00041ep87c8ujf90@drtom.pryv.me';
|
|
98
|
-
const connection = new
|
|
75
|
+
const connection = new pryv.Connection(apiEndpoint);
|
|
99
76
|
```
|
|
100
77
|
|
|
101
|
-
####
|
|
78
|
+
#### With username & token (knowing the service information URL)
|
|
102
79
|
|
|
103
|
-
```
|
|
104
|
-
const service = new
|
|
80
|
+
```js
|
|
81
|
+
const service = new pryv.Service('https://reg.pryv.me/service/info');
|
|
105
82
|
const apiEndpoint = await service.apiEndpointFor(username, token);
|
|
106
|
-
const connection = new
|
|
83
|
+
const connection = new pryv.Connection(apiEndpoint);
|
|
107
84
|
```
|
|
108
85
|
|
|
109
|
-
#### Within a
|
|
86
|
+
#### Within a web page with a login button
|
|
110
87
|
|
|
111
|
-
|
|
88
|
+
Here is an implementation of the [Pryv.io authentication process](https://api.pryv.com/reference/#authenticate-your-app):
|
|
112
89
|
|
|
113
90
|
```html
|
|
114
91
|
<!doctype html>
|
|
115
92
|
<html>
|
|
116
93
|
<head>
|
|
117
|
-
<title>Pryv
|
|
94
|
+
<title>Pryv authentication example</title>
|
|
118
95
|
<script src="https://api.pryv.com/lib-js/pryv.js"></script>
|
|
119
96
|
</head>
|
|
120
97
|
<body>
|
|
@@ -123,11 +100,11 @@ The following code is an implementation of the [Pryv.io Authentication process](
|
|
|
123
100
|
var connection = null;
|
|
124
101
|
|
|
125
102
|
var authSettings = {
|
|
126
|
-
spanButtonID: 'pryv-button', //
|
|
127
|
-
onStateChange:
|
|
103
|
+
spanButtonID: 'pryv-button', // id of the <span> that will be replaced by the service-specific button
|
|
104
|
+
onStateChange: authStateChanged, // event listener for authentication steps
|
|
128
105
|
authRequest: { // See: https://api.pryv.com/reference/#auth-request
|
|
129
106
|
requestingAppId: 'lib-js-test',
|
|
130
|
-
languageCode: 'fr', // optional (default
|
|
107
|
+
languageCode: 'fr', // optional (default: 'en')
|
|
131
108
|
requestedPermissions: [
|
|
132
109
|
{
|
|
133
110
|
streamId: 'test',
|
|
@@ -143,53 +120,56 @@ The following code is an implementation of the [Pryv.io Authentication process](
|
|
|
143
120
|
// referer: 'my test with lib-js', // optional string to track registration source
|
|
144
121
|
}
|
|
145
122
|
};
|
|
123
|
+
var serviceInfoUrl = 'https://api.pryv.com/lib-js/examples/service-info.json';
|
|
124
|
+
(async function () {
|
|
125
|
+
var service = await pryv.Auth.setupAuth(authSettings, serviceInfoUrl);
|
|
126
|
+
})();
|
|
146
127
|
|
|
147
|
-
function
|
|
148
|
-
console.log('
|
|
149
|
-
if (state.id ===
|
|
150
|
-
connection = new
|
|
128
|
+
function authStateChanged(state) { // called each time the authentication state changes
|
|
129
|
+
console.log('# Auth state changed:', state);
|
|
130
|
+
if (state.id === pryv.Auth.AuthStates.AUTHORIZED) {
|
|
131
|
+
connection = new pryv.Connection(state.apiEndpoint);
|
|
151
132
|
logToConsole('# Browser succeeded for user ' + connection.apiEndpoint);
|
|
152
133
|
}
|
|
153
|
-
if (state.id ===
|
|
134
|
+
if (state.id === pryv.Auth.AuthStates.SIGNOUT) {
|
|
154
135
|
connection = null;
|
|
155
|
-
logToConsole('#
|
|
136
|
+
logToConsole('# Signed out');
|
|
156
137
|
}
|
|
157
|
-
|
|
158
|
-
var serviceInfoUrl = 'https://api.pryv.com/lib-js/demos/service-info.json';
|
|
159
|
-
(async function () {
|
|
160
|
-
var service = await Pryv.Auth.setupAuth(authSettings, serviceInfoUrl);
|
|
161
|
-
})();
|
|
138
|
+
}
|
|
162
139
|
</script>
|
|
163
140
|
</body>
|
|
164
141
|
</html>
|
|
165
142
|
```
|
|
166
143
|
|
|
167
|
-
####
|
|
144
|
+
#### Fetching access info
|
|
168
145
|
|
|
169
|
-
|
|
146
|
+
[API reference](https://api.pryv.com/reference/#access-info).
|
|
170
147
|
|
|
171
148
|
```js
|
|
172
149
|
const apiEndpoint = 'https://ck6bwmcar00041ep87c8ujf90@drtom.pryv.me';
|
|
173
|
-
const connection = new
|
|
150
|
+
const connection = new pryv.Connection(apiEndpoint);
|
|
174
151
|
const accessInfo = await connection.accessInfo();
|
|
175
152
|
```
|
|
176
153
|
|
|
177
|
-
#### Using Service.login()
|
|
154
|
+
#### Using `pryv.Service.login()` _(trusted apps only)_
|
|
178
155
|
|
|
179
|
-
[
|
|
156
|
+
[API reference](https://api.pryv.com/reference-full/#login-user)
|
|
180
157
|
|
|
181
|
-
```
|
|
158
|
+
```js
|
|
182
159
|
const serviceInfoUrl = 'https://reg.pryv.me/service/info';
|
|
183
160
|
const appId = 'lib-js-sample';
|
|
184
|
-
const service = new
|
|
161
|
+
const service = new pryv.Service(serviceInfoUrl);
|
|
185
162
|
const connection = await service.login(username, password, appId);
|
|
186
163
|
```
|
|
187
164
|
|
|
165
|
+
|
|
188
166
|
### API calls
|
|
189
167
|
|
|
190
|
-
|
|
168
|
+
API calls are based on the "batch" call specification: [Call batch API reference](https://api.pryv.com/reference/#call-batch)
|
|
191
169
|
|
|
192
|
-
|
|
170
|
+
#### Simple usage
|
|
171
|
+
|
|
172
|
+
```js
|
|
193
173
|
const apiCalls = [
|
|
194
174
|
{
|
|
195
175
|
"method": "streams.create",
|
|
@@ -197,11 +177,11 @@ const apiCalls = [
|
|
|
197
177
|
},
|
|
198
178
|
{
|
|
199
179
|
"method": "events.create",
|
|
200
|
-
"params": { "time": 1385046854.282, "
|
|
180
|
+
"params": { "time": 1385046854.282, "streamIds": ["heart"], "type": "frequency/bpm", "content": 90 }
|
|
201
181
|
},
|
|
202
182
|
{
|
|
203
183
|
"method": "events.create",
|
|
204
|
-
"params": { "time": 1385046854.283, "
|
|
184
|
+
"params": { "time": 1385046854.283, "streamIds": ["heart"], "type": "frequency/bpm", "content": 120 }
|
|
205
185
|
}
|
|
206
186
|
]
|
|
207
187
|
|
|
@@ -212,9 +192,9 @@ try {
|
|
|
212
192
|
}
|
|
213
193
|
```
|
|
214
194
|
|
|
215
|
-
|
|
195
|
+
#### Advanced usage with optional individual result and progress callbacks
|
|
216
196
|
|
|
217
|
-
```
|
|
197
|
+
```js
|
|
218
198
|
let count = 0;
|
|
219
199
|
// the following will be called on each API method result it was provided for
|
|
220
200
|
function handleResult(result) { console.log('Got result ' + count++ + ': ' + JSON.stringify(result)); }
|
|
@@ -228,12 +208,12 @@ const apiCalls = [
|
|
|
228
208
|
},
|
|
229
209
|
{
|
|
230
210
|
method: 'events.create',
|
|
231
|
-
params: { time: 1385046854.282,
|
|
211
|
+
params: { time: 1385046854.282, streamIds: ['heart'], type: 'frequency/bpm', content: 90 },
|
|
232
212
|
handleResult: handleResult
|
|
233
213
|
},
|
|
234
214
|
{
|
|
235
215
|
method: 'events.create',
|
|
236
|
-
params: { time: 1385046854.283,
|
|
216
|
+
params: { time: 1385046854.283, streamIds: ['heart'], type: 'frequency/bpm', content: 120 },
|
|
237
217
|
handleResult: handleResult
|
|
238
218
|
}
|
|
239
219
|
]
|
|
@@ -245,18 +225,18 @@ try {
|
|
|
245
225
|
}
|
|
246
226
|
```
|
|
247
227
|
|
|
248
|
-
|
|
228
|
+
|
|
229
|
+
### Get events streamed
|
|
249
230
|
|
|
250
231
|
When `events.get` will provide a large result set, it is recommended to use a method that streams the result instead of the batch API call.
|
|
251
232
|
|
|
252
|
-
`
|
|
233
|
+
`pryv.Connection.getEventsStreamed()` parses the response JSON as soon as data is available and calls the `forEachEvent` callback for each event object.
|
|
253
234
|
|
|
254
|
-
The callback is meant to store the events data, as the function does not return the API call result, which could overflow memory in case of JSON deserialization of a very large data set.
|
|
255
|
-
Instead, the function returns an events count and eventually event deletions count as well as the [common metadata](https://api.pryv.com/reference/#common-metadata).
|
|
235
|
+
The callback is meant to store the events data, as the function does not return the API call result, which could overflow memory in case of JSON deserialization of a very large data set. Instead, the function returns an events count and possibly event deletions count as well as the [common metadata](https://api.pryv.com/reference/#common-metadata).
|
|
256
236
|
|
|
257
|
-
#### Example
|
|
237
|
+
#### Example
|
|
258
238
|
|
|
259
|
-
|
|
239
|
+
```js
|
|
260
240
|
const now = (new Date()).getTime() / 1000;
|
|
261
241
|
const queryParams = { fromTime: 0, toTime: now, limit: 10000};
|
|
262
242
|
const events = [];
|
|
@@ -269,11 +249,11 @@ try {
|
|
|
269
249
|
} catch (e) {
|
|
270
250
|
// handle error
|
|
271
251
|
}
|
|
272
|
-
|
|
252
|
+
```
|
|
273
253
|
|
|
274
|
-
|
|
254
|
+
`result`:
|
|
275
255
|
|
|
276
|
-
```
|
|
256
|
+
```js
|
|
277
257
|
{
|
|
278
258
|
eventsCount: 10000,
|
|
279
259
|
meta:
|
|
@@ -285,15 +265,15 @@ try {
|
|
|
285
265
|
}
|
|
286
266
|
```
|
|
287
267
|
|
|
288
|
-
#### Example
|
|
268
|
+
#### Example including deletions
|
|
289
269
|
|
|
290
|
-
|
|
270
|
+
```js
|
|
291
271
|
const now = (new Date()).getTime() / 1000;
|
|
292
272
|
const queryParams = { fromTime: 0, toTime: now, includeDeletions: true, modifiedSince: 0};
|
|
293
273
|
const events = [];
|
|
294
274
|
function forEachEvent(event) {
|
|
295
275
|
events.push(event);
|
|
296
|
-
// events with
|
|
276
|
+
// events with `deleted` or/and `trashed` properties can be tracked here
|
|
297
277
|
}
|
|
298
278
|
|
|
299
279
|
try {
|
|
@@ -301,11 +281,11 @@ try {
|
|
|
301
281
|
} catch (e) {
|
|
302
282
|
// handle error
|
|
303
283
|
}
|
|
304
|
-
|
|
284
|
+
```
|
|
305
285
|
|
|
306
|
-
|
|
286
|
+
`result`:
|
|
307
287
|
|
|
308
|
-
```
|
|
288
|
+
```js
|
|
309
289
|
{
|
|
310
290
|
eventDeletionsCount: 150,
|
|
311
291
|
eventsCount: 10000,
|
|
@@ -319,120 +299,91 @@ try {
|
|
|
319
299
|
```
|
|
320
300
|
|
|
321
301
|
|
|
302
|
+
### Events with attachments
|
|
322
303
|
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
### Events with Attachments
|
|
326
|
-
|
|
327
|
-
This shortcut allows to create an event with an attachment in a single API call.
|
|
304
|
+
You can create an event with an attachment in a single API call.
|
|
328
305
|
|
|
329
306
|
#### Node.js
|
|
330
307
|
|
|
331
|
-
```
|
|
308
|
+
```js
|
|
332
309
|
const filePath = './test/my_image.png';
|
|
333
|
-
const result = await connection.createEventWithFile(
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
},
|
|
338
|
-
filePath
|
|
339
|
-
);
|
|
310
|
+
const result = await connection.createEventWithFile({
|
|
311
|
+
type: 'picture/attached',
|
|
312
|
+
streamIds: ['data']
|
|
313
|
+
}, filePath);
|
|
340
314
|
```
|
|
341
315
|
|
|
342
|
-
|
|
316
|
+
Or from a `Buffer`:
|
|
343
317
|
|
|
344
|
-
```
|
|
318
|
+
```js
|
|
345
319
|
const filePath = './test/my_image.png';
|
|
346
320
|
const bufferData = fs.readFileSync(filePath);
|
|
347
321
|
|
|
348
|
-
const result = await connection.createEventWithFileFromBuffer(
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
},
|
|
353
|
-
bufferData,
|
|
354
|
-
'my_image.png' // filename
|
|
355
|
-
);
|
|
322
|
+
const result = await connection.createEventWithFileFromBuffer({
|
|
323
|
+
type: 'picture/attached',
|
|
324
|
+
streamIds: ['data']
|
|
325
|
+
}, bufferData, 'my_image.png' /* ← filename */);
|
|
356
326
|
```
|
|
357
327
|
|
|
358
328
|
#### Browser
|
|
359
329
|
|
|
360
|
-
From an
|
|
330
|
+
From an `<input>`:
|
|
361
331
|
|
|
362
332
|
```html
|
|
363
333
|
<input type="file" id="file-upload"><button onClick='uploadFile()'>Save Value</button>
|
|
364
334
|
|
|
365
335
|
<script>
|
|
366
336
|
var formData = new FormData();
|
|
367
|
-
formData.append(
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
streamId: 'test'
|
|
376
|
-
},
|
|
377
|
-
formData)
|
|
378
|
-
.then(function (res, err) {
|
|
379
|
-
// handle result here
|
|
380
|
-
}
|
|
381
|
-
);
|
|
337
|
+
formData.append('file0', document.getElementById('create-file').files[0]) ;
|
|
338
|
+
|
|
339
|
+
connection.createEventWithFormData({
|
|
340
|
+
type: 'file/attached',
|
|
341
|
+
streamIds: ['test']
|
|
342
|
+
}, formData).then(function (res, err) {
|
|
343
|
+
// handle result
|
|
344
|
+
});
|
|
382
345
|
</script>
|
|
383
346
|
```
|
|
384
347
|
|
|
385
|
-
|
|
348
|
+
Programmatically created content:
|
|
386
349
|
|
|
387
|
-
```
|
|
350
|
+
```js
|
|
388
351
|
var formData = new FormData();
|
|
389
|
-
var blob = new Blob(
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
)
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
connect.createEventWithFileFromBuffer(
|
|
409
|
-
{
|
|
410
|
-
type: 'file/attached',
|
|
411
|
-
streamId: 'data'
|
|
412
|
-
},
|
|
413
|
-
blob, 'filename.txt') // here we can directly use the blob
|
|
414
|
-
.then(function (res, err) {
|
|
415
|
-
// handle result here
|
|
416
|
-
}
|
|
417
|
-
);
|
|
418
|
-
|
|
419
|
-
|
|
352
|
+
var blob = new Blob(['Hello'], { type: "text/txt" });
|
|
353
|
+
formData.append("file", blob);
|
|
354
|
+
|
|
355
|
+
connect.createEventWithFormData({
|
|
356
|
+
type: 'file/attached',
|
|
357
|
+
streamIds: ['data']
|
|
358
|
+
}, formData).then(function (res, err) {
|
|
359
|
+
// handle result
|
|
360
|
+
});
|
|
361
|
+
|
|
362
|
+
// Alternative with a filename
|
|
363
|
+
|
|
364
|
+
connect.createEventWithFileFromBuffer({
|
|
365
|
+
type: 'file/attached',
|
|
366
|
+
streamIds: ['data']
|
|
367
|
+
}, blob /* ← here we can directly use the blob*/, 'filename.txt').then(function (res, err) {
|
|
368
|
+
// handle result
|
|
369
|
+
});
|
|
420
370
|
```
|
|
421
371
|
|
|
422
|
-
### High Frequency Events
|
|
423
372
|
|
|
424
|
-
|
|
373
|
+
### High Frequency (HF) events
|
|
374
|
+
|
|
375
|
+
[API reference](https://api.pryv.com/reference/#hf-events)
|
|
425
376
|
|
|
426
|
-
```
|
|
427
|
-
function
|
|
428
|
-
const
|
|
377
|
+
```js
|
|
378
|
+
function generateSeries() {
|
|
379
|
+
const series = [];
|
|
429
380
|
for (let t = 0; t < 100000, t++) { // t will be the deltaTime in seconds
|
|
430
|
-
|
|
381
|
+
series.push([t, Math.sin(t/1000)]);
|
|
431
382
|
}
|
|
432
|
-
return
|
|
383
|
+
return series;
|
|
433
384
|
}
|
|
434
|
-
const pointsA =
|
|
435
|
-
const pointsB =
|
|
385
|
+
const pointsA = generateSeries();
|
|
386
|
+
const pointsB = generateSeries();
|
|
436
387
|
|
|
437
388
|
function postHFData(points) { // must return a Promise
|
|
438
389
|
return async function (result) { // will be called each time an HF event is created
|
|
@@ -451,121 +402,113 @@ const apiCalls = [
|
|
|
451
402
|
},
|
|
452
403
|
{
|
|
453
404
|
method: 'events.create',
|
|
454
|
-
params: {
|
|
405
|
+
params: { streamIds: ['signal1'], type: 'series:frequency/bpm' },
|
|
455
406
|
handleResult: postHFData(pointsA)
|
|
456
407
|
},
|
|
457
408
|
{
|
|
458
409
|
method: 'events.create',
|
|
459
|
-
params: {
|
|
410
|
+
params: { streamIds: ['signal2'], type: 'series:frequency/bpm' },
|
|
460
411
|
handleResult: postHFData(pointsB)
|
|
461
412
|
}
|
|
462
|
-
]
|
|
413
|
+
];
|
|
463
414
|
|
|
464
415
|
try {
|
|
465
|
-
const result = await connection.api(apiCalls)
|
|
416
|
+
const result = await connection.api(apiCalls);
|
|
466
417
|
} catch (e) {
|
|
467
418
|
// handle error
|
|
468
419
|
}
|
|
469
|
-
|
|
470
420
|
```
|
|
471
421
|
|
|
472
|
-
### Service Information and assets
|
|
473
422
|
|
|
474
|
-
|
|
423
|
+
### Service information and assets
|
|
475
424
|
|
|
476
|
-
|
|
425
|
+
Each Pryv.io platform is considered a "service"; for example **Pryv Lab**, which is deployed on the **pryv.me** domain.
|
|
426
|
+
It is described by a **service information** settings object (see the [service info API reference](https://api.pryv.com/reference/#service-info)).
|
|
477
427
|
|
|
478
|
-
|
|
428
|
+
`pryv.Service` exposes tools to interact with Pryv.io at the "platform" level.
|
|
479
429
|
|
|
480
|
-
|
|
430
|
+
#### Initializing with a service info URL
|
|
481
431
|
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
```javascript
|
|
485
|
-
const service = new Pryv.Service('https://reg.pryv.me/service/info');
|
|
432
|
+
```js
|
|
433
|
+
const service = new pryv.Service('https://reg.pryv.me/service/info');
|
|
486
434
|
```
|
|
487
435
|
|
|
488
|
-
|
|
436
|
+
#### Initializing with a service info settings object
|
|
489
437
|
|
|
490
|
-
Service information properties can be
|
|
438
|
+
Service information properties can be overridden, which can be useful to test new designs on production platforms.
|
|
491
439
|
|
|
492
|
-
```
|
|
440
|
+
```js
|
|
493
441
|
const serviceInfoUrl = 'https://reg.pryv.me/service/info';
|
|
494
|
-
const
|
|
442
|
+
const overrides = {
|
|
495
443
|
name: 'Pryv Lab 2',
|
|
496
444
|
assets: {
|
|
497
445
|
definitions: 'https://pryv.github.io/assets-pryv.me/index.json'
|
|
498
446
|
}
|
|
499
447
|
}
|
|
500
|
-
const service = new
|
|
448
|
+
const service = new pryv.Service(serviceInfoUrl, overrides);
|
|
501
449
|
```
|
|
502
450
|
|
|
503
|
-
|
|
451
|
+
#### Methods
|
|
504
452
|
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
|
|
508
|
-
|
|
509
|
-
```javascript
|
|
510
|
-
// example: get the name of the platform
|
|
453
|
+
- `service.info()` returns the service information in a Promise
|
|
454
|
+
```js
|
|
455
|
+
// get the name of the platform
|
|
511
456
|
const serviceName = await service.info().name
|
|
512
457
|
```
|
|
458
|
+
- `service.infoSync()` returns the cached service info; requires `service.info()` to be called beforehand
|
|
459
|
+
- `service.apiEndpointFor(username, token)` returns the corresponding API endpoint for the provided credentials (`token` is optional)
|
|
513
460
|
|
|
514
|
-
- `service.infoSync()`: returns the cached content of the serviceInfo, requires `service.info()` to be called first.
|
|
515
461
|
|
|
516
|
-
|
|
462
|
+
### `pryv.Browser` & visual assets
|
|
517
463
|
|
|
518
|
-
|
|
464
|
+
#### Retrieving the service info from a query parameter
|
|
519
465
|
|
|
520
|
-
|
|
466
|
+
A single web app might need to run on different Pryv.io platforms (this is the case of most Pryv.io example apps).
|
|
521
467
|
|
|
522
|
-
|
|
468
|
+
The Pryv.io platform can be specified by passing the service information URL in a query parameter `pryvServiceInfoUrl` (as per the [Pryv app guidelines](https://api.pryv.com/guides/app-guidelines/)), which can be extracted with `pryv.Browser.serviceInfoFromUrl()`.
|
|
523
469
|
|
|
524
|
-
|
|
470
|
+
For example: `https://api.pryv.com/app-web-access/?pryvServiceInfoUrl=https://reg.pryv.me/service/info`
|
|
525
471
|
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
```javascript
|
|
472
|
+
```js
|
|
529
473
|
let defaultServiceInfoUrl = 'https://reg.pryv.me/service/info';
|
|
530
|
-
// if present override serviceInfoURL from
|
|
531
|
-
serviceInfoUrl =
|
|
474
|
+
// if present, override serviceInfoURL from query param `pryvServiceInfoUrl`
|
|
475
|
+
serviceInfoUrl = pryv.Browser.serviceInfoFromUrl() || defaultServiceInfoUrl;
|
|
532
476
|
|
|
533
477
|
(async function () {
|
|
534
|
-
var service = await
|
|
478
|
+
var service = await pryv.Auth.setupAuth(authSettings, serviceInfoUrl, serviceCustomizations);
|
|
535
479
|
})();
|
|
536
480
|
```
|
|
537
481
|
|
|
538
482
|
#### Visual assets
|
|
539
483
|
|
|
540
|
-
To customize assets
|
|
484
|
+
To customize visual assets, please refer to the [pryv.me assets repository](https://github.com/pryv/assets-pryv.me). For example, see [how to customize the sign-in button](https://github.com/pryv/assets-pryv.me/tree/master/lib-js/).
|
|
541
485
|
|
|
542
|
-
|
|
486
|
+
`(await service.assets()).setAllDefaults()` loads the `css` and `favicon` properties of assets definitions:
|
|
543
487
|
|
|
544
|
-
|
|
545
|
-
|
|
546
|
-
```javascript
|
|
488
|
+
```js
|
|
547
489
|
(async function () {
|
|
548
|
-
const service = await
|
|
549
|
-
(await service.assets()).setAllDefaults(); // will load the default
|
|
490
|
+
const service = await pryv.Auth.setupAuth(authSettings, serviceInfoUrl);
|
|
491
|
+
(await service.assets()).setAllDefaults(); // will load the default favicon and CSS for this platform
|
|
550
492
|
})();
|
|
551
493
|
```
|
|
552
494
|
|
|
553
|
-
### Customize Auth process
|
|
554
495
|
|
|
555
|
-
|
|
496
|
+
### Customize the authentication process
|
|
556
497
|
|
|
557
|
-
|
|
558
|
-
|
|
498
|
+
You can customize the authentication process ([API reference](https://api.pryv.com/reference/#authenticate-your-app)) at different levels:
|
|
499
|
+
|
|
500
|
+
- Using a custom login button
|
|
501
|
+
- Using a custom UI, including the flow of [app-web-auth3](https://github.com/pryv/app-web-auth3)
|
|
559
502
|
|
|
560
503
|
#### Using a custom login button
|
|
561
504
|
|
|
562
|
-
You will need to implement a class that instanciates an [AuthController](src/Auth/AuthController.js) object and implements a few methods. We will go through this guide using the Browser's default [
|
|
505
|
+
You will need to implement a class that instanciates an [AuthController](src/Auth/AuthController.js) object and implements a few methods. We will go through this guide using the Browser's default [login button](src/Browser/LoginButton.js) provided with this library as example.
|
|
563
506
|
|
|
564
507
|
##### Initialization
|
|
565
508
|
|
|
566
|
-
You should provide
|
|
509
|
+
You should provide auth settings (see [obtaining a `pryv.Connection`](#within-a-webpage-with-a-login-button)) and an instance of [pryv.Service](src/Service.js) at initialization. As this phase might contain asynchronous calls, we like to split it between the constructor and an `async init()` function. In particular, you will need to instanciate an [AuthController](src/Auth/AuthController.js) object.
|
|
567
510
|
|
|
568
|
-
```
|
|
511
|
+
```js
|
|
569
512
|
constructor(authSettings, service) {
|
|
570
513
|
this.authSettings = authSettings;
|
|
571
514
|
this.service = service;
|
|
@@ -587,9 +530,9 @@ async init () {
|
|
|
587
530
|
|
|
588
531
|
##### Authorization data
|
|
589
532
|
|
|
590
|
-
At initialization, the [AuthController](src/Auth/AuthController.js) will attempt to fetch
|
|
533
|
+
At initialization, the [AuthController](src/Auth/AuthController.js) will attempt to fetch persisted authorization credentials, using `LoginButton.getAuthorizationData()`. In the browser, we are using a client-side cookie. For other frameworks, use an appropriate secure storage.
|
|
591
534
|
|
|
592
|
-
```
|
|
535
|
+
```js
|
|
593
536
|
getAuthorizationData () {
|
|
594
537
|
return Cookies.get(this._cookieKey);
|
|
595
538
|
}
|
|
@@ -597,18 +540,18 @@ getAuthorizationData () {
|
|
|
597
540
|
|
|
598
541
|
##### Authentication lifecycle
|
|
599
542
|
|
|
600
|
-
The [authentication process](https://api.pryv.com/reference/#authenticate-your-app) implementation on the frontend
|
|
543
|
+
The [authentication process](https://api.pryv.com/reference/#authenticate-your-app) implementation on the frontend can go through the following states:
|
|
601
544
|
|
|
602
|
-
1.
|
|
603
|
-
2.
|
|
604
|
-
3.
|
|
605
|
-
4.
|
|
606
|
-
5.
|
|
607
|
-
6.
|
|
545
|
+
1. `LOADING`: while the visual assets are loading
|
|
546
|
+
2. `INITIALIZED`: visuals assets are loaded, or when [polling](https://api.pryv.com/reference/#poll-request) concludes with **Result: Refused**
|
|
547
|
+
3. `NEED_SIGNIN`: from the response of the [auth request](https://api.pryv.com/reference/#auth-request) through [polling](https://api.pryv.com/reference/#poll-request)
|
|
548
|
+
4. `AUTHORIZED`: When [polling](https://api.pryv.com/reference/#poll-request) concludes with **Result: Accepted**
|
|
549
|
+
5. `SIGNOUT`: when the user triggers a deletion of the client-side authorization credentials, usually by clicking the button after being signed in
|
|
550
|
+
6. `ERROR`: see message for more information
|
|
608
551
|
|
|
609
|
-
You will need to provide a function to
|
|
552
|
+
You will need to provide a function to react depending on the state. The states `NEED_SIGNIN` and `AUTHORIZED` carry the same properties as the [auth process polling responses](https://api.pryv.com/reference/#poll-request). `LOADING`, `INITIALIZED` and `SIGNOUT` only have `status`. The `ERROR` state carries a `message` property.
|
|
610
553
|
|
|
611
|
-
```
|
|
554
|
+
```js
|
|
612
555
|
async onStateChange (state) {
|
|
613
556
|
switch (state.status) {
|
|
614
557
|
case AuthStates.LOADING:
|
|
@@ -656,14 +599,14 @@ async onStateChange (state) {
|
|
|
656
599
|
|
|
657
600
|
The button actions should be handled by the [AuthController](src/Auth/AuthController.js) in the following way:
|
|
658
601
|
|
|
659
|
-
```
|
|
602
|
+
```js
|
|
660
603
|
// LoginButton.js
|
|
661
604
|
onClick () {
|
|
662
605
|
this.auth.handleClick();
|
|
663
606
|
}
|
|
664
607
|
```
|
|
665
608
|
|
|
666
|
-
```
|
|
609
|
+
```js
|
|
667
610
|
// AuthController.js
|
|
668
611
|
async handleClick () {
|
|
669
612
|
if (isAuthorized.call(this)) {
|
|
@@ -681,10 +624,10 @@ async handleClick () {
|
|
|
681
624
|
|
|
682
625
|
##### Custom button usage
|
|
683
626
|
|
|
684
|
-
You must then provide this class as
|
|
627
|
+
You must then provide this class as follows:
|
|
685
628
|
|
|
686
|
-
```
|
|
687
|
-
let service = await
|
|
629
|
+
```js
|
|
630
|
+
let service = await pryv.Auth.setupAuth(
|
|
688
631
|
authSettings, // See https://github.com/pryv/lib-js#within-a-webpage-with-a-login-button
|
|
689
632
|
serviceInfoUrl,
|
|
690
633
|
serviceCustomizations,
|
|
@@ -692,51 +635,100 @@ let service = await Pryv.Auth.setupAuth(
|
|
|
692
635
|
);
|
|
693
636
|
```
|
|
694
637
|
|
|
695
|
-
You will find a working example
|
|
696
|
-
|
|
697
|
-
Follow the instructions below on [how to run these examples locally](#launch-web-demos-locally).
|
|
638
|
+
You will find a working example [here](https://github.com/pryv/lib-js/blob/master/examples/custom-login-button.html), and try it running [there](https://api.pryv.com/lib-js/examples/custom-login-button.html). To run these examples locally, see below.
|
|
698
639
|
|
|
699
|
-
For a more advanced scenario, you can check the default button implementation
|
|
640
|
+
For a more advanced scenario, you can check the default button implementation in [`./src/Browser/LoginButton.js`](/src/Browser/LoginButton.js).
|
|
700
641
|
|
|
701
642
|
#### Redirect user to the authentication page
|
|
702
643
|
|
|
703
|
-
There is a possibility that you would like to register the user in another page. You can
|
|
704
|
-
|
|
705
|
-
Here is the explanation how to [launch web-demos locally](#launch-web-demos-locally)
|
|
644
|
+
There is a possibility that you would like to register the user in another page. You can find an example [here](https://github.com/pryv/lib-js/blob/master/examples/auth-with-redirection.html), and try it running [there](https://api.pryv.com/lib-js/examples/auth-with-redirection.html). Again, to run these examples locally, see below.
|
|
645
|
+
|
|
706
646
|
|
|
707
|
-
###
|
|
647
|
+
### Running examples locally
|
|
708
648
|
|
|
709
|
-
You can find
|
|
649
|
+
You can find HTML examples in the [`./examples`](https://github.com/pryv/lib-js/blob/master/examples) directory. You can run them in two ways:
|
|
710
650
|
|
|
711
|
-
1.
|
|
651
|
+
1. With [rec.la](https://github.com/pryv/rec.la), which allows to run local code with a valid SSL certificate (you must have run `just build` beforehand):
|
|
652
|
+
```
|
|
653
|
+
just serve
|
|
654
|
+
```
|
|
655
|
+
then open the desired example page (e.g. [https://l.rec.la:9443/examples/auth.html](https://l.rec.la:9443/examples/auth.html)
|
|
656
|
+
2. As a simple HTML file, passing service information as JSON to avoid CORS issues
|
|
712
657
|
|
|
713
|
-
```bash
|
|
714
|
-
npm run webserver
|
|
715
|
-
```
|
|
716
658
|
|
|
717
|
-
|
|
659
|
+
## Contributing
|
|
718
660
|
|
|
719
|
-
|
|
661
|
+
### Installation
|
|
720
662
|
|
|
721
|
-
|
|
663
|
+
Prerequisites: [Node.js](https://nodejs.org/en/download/) 16, [just](https://github.com/casey/just#installation)
|
|
722
664
|
|
|
723
|
-
|
|
665
|
+
Then:
|
|
666
|
+
1. `just setup-dev-env`
|
|
667
|
+
2. `just install` to install node modules
|
|
668
|
+
3. `just build` for the initial webpack build
|
|
724
669
|
|
|
725
|
-
|
|
670
|
+
Running `just` with no argument displays the available commands (defined in `justfile`).
|
|
726
671
|
|
|
727
|
-
|
|
672
|
+
### Dev environment basics
|
|
728
673
|
|
|
729
|
-
|
|
674
|
+
The project is structured as a monorepo with components (a.k.a. workspaces in NPM), each component defining its `package.json`, tests, etc. in `components/`:
|
|
675
|
+
- `pryv`: the library
|
|
676
|
+
- `pryv-socket.io`: Socket.IO add-on
|
|
677
|
+
- `pryv-monitor`: Monitor add-on
|
|
678
|
+
|
|
679
|
+
The code follows the [Semi-Standard](https://github.com/standard/semistandard) style.
|
|
680
|
+
|
|
681
|
+
### Building for the browser
|
|
682
|
+
|
|
683
|
+
```
|
|
684
|
+
just build[-watch]
|
|
685
|
+
```
|
|
686
|
+
to build the library, add-ons and examples into `dist/`, and the browser tests into `test-browser/`
|
|
687
|
+
|
|
688
|
+
### Testing
|
|
689
|
+
|
|
690
|
+
#### Node.js
|
|
691
|
+
|
|
692
|
+
```
|
|
693
|
+
just test <component> [...params]
|
|
694
|
+
```
|
|
695
|
+
- `component` is an existing component's name, or `all` to run tests on all components
|
|
696
|
+
- Extra parameters at the end are passed on to [Mocha](https://mochajs.org/) (default settings are defined in `.mocharc.js` files)
|
|
697
|
+
- Replace `test` with `test-debug`, `test-cover` for common presets
|
|
698
|
+
|
|
699
|
+
#### Browser
|
|
700
|
+
|
|
701
|
+
Assuming browser files have been built (see above):
|
|
702
|
+
```
|
|
703
|
+
just test-browser
|
|
704
|
+
```
|
|
705
|
+
to run the tests in a browser window.
|
|
706
|
+
|
|
707
|
+
- Update on CDN: After running **setup** and **build** scripts, run `npm run gh-pages ${COMMIT_MESSAGE}`. If this fails, run `npm run clear` to rebuild a fresh `dist/` folder
|
|
708
|
+
|
|
709
|
+
### Publishing
|
|
710
|
+
|
|
711
|
+
Assuming browser files are built and everything is up-to-date, including the READMEs and [changelog](https://github.com/pryv/lib-js/blob/master/CHANGELOG.md):
|
|
712
|
+
|
|
713
|
+
```
|
|
714
|
+
just version <version>
|
|
715
|
+
```
|
|
716
|
+
to update the version number of the lib and add-ons in lockstep, git commit and tag included
|
|
717
|
+
|
|
718
|
+
```
|
|
719
|
+
just publish-npm
|
|
720
|
+
```
|
|
721
|
+
to publish the new versions of the lib and add-ons to NPM
|
|
722
|
+
|
|
723
|
+
```
|
|
724
|
+
just publish-browser
|
|
725
|
+
```
|
|
726
|
+
to commit and push the `gh-pages` branch from `dist/`, publishing the browser files to be served via CDN on `api.pryv.com/lib-js`
|
|
730
727
|
|
|
731
|
-
## 2.1.0
|
|
732
728
|
|
|
733
|
-
|
|
734
|
-
- Extendable UI feature was added
|
|
729
|
+
## [Changelog](CHANGELOG.md)
|
|
735
730
|
|
|
736
|
-
## 2.0.3
|
|
737
731
|
|
|
738
|
-
|
|
739
|
-
- Various dependencies upgrades
|
|
740
|
-
- Fixing Origin header in Browser distribution
|
|
732
|
+
## License
|
|
741
733
|
|
|
742
|
-
|
|
734
|
+
[BSD-3-Clause](https://github.com/pryv/lib-js/blob/master/LICENSE)
|