cozy-harvest-lib 9.3.0 → 9.5.1
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/CHANGELOG.md +31 -0
- package/dist/components/TriggerManager.js +8 -4
- package/dist/helpers/oauth.js +7 -5
- package/dist/services/biWebView.js +113 -11
- package/dist/services/biWebView.spec.js +1 -1
- package/dist/services/budget-insight.js +1 -13
- package/dist/types.js +22 -0
- package/package.json +3 -3
- package/src/components/TriggerManager.jsx +25 -10
- package/src/helpers/oauth.js +9 -5
- package/src/services/biWebView.js +72 -7
- package/src/services/biWebView.spec.js +1 -1
- package/src/services/budget-insight.js +1 -13
- package/src/types.js +22 -0
package/CHANGELOG.md
CHANGED
|
@@ -3,6 +3,37 @@
|
|
|
3
3
|
All notable changes to this project will be documented in this file.
|
|
4
4
|
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
|
5
5
|
|
|
6
|
+
## [9.5.1](https://github.com/cozy/cozy-libs/compare/cozy-harvest-lib@9.5.0...cozy-harvest-lib@9.5.1) (2022-05-25)
|
|
7
|
+
|
|
8
|
+
**Note:** Version bump only for package cozy-harvest-lib
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
# [9.5.0](https://github.com/cozy/cozy-libs/compare/cozy-harvest-lib@9.4.0...cozy-harvest-lib@9.5.0) (2022-05-23)
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
### Features
|
|
18
|
+
|
|
19
|
+
* Handle banks with mulitple bank ids ([a944201](https://github.com/cozy/cozy-libs/commit/a944201ca5752766a49689f42531c84f03798002))
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
# [9.4.0](https://github.com/cozy/cozy-libs/compare/cozy-harvest-lib@9.3.0...cozy-harvest-lib@9.4.0) (2022-05-18)
|
|
26
|
+
|
|
27
|
+
|
|
28
|
+
### Features
|
|
29
|
+
|
|
30
|
+
* **harvest:** HandleOAuthResponse can deal with cozy-data from DOM ([7c6ac1a](https://github.com/cozy/cozy-libs/commit/7c6ac1a8de7dd2b136530d0aafdb1e3f9e28fa56))
|
|
31
|
+
* **harvest:** OAuthFormWrapperComp can be passed to TriggerManager ([76ee8b7](https://github.com/cozy/cozy-libs/commit/76ee8b74d9314d3c66593dfe925880e6a296b420))
|
|
32
|
+
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
|
|
36
|
+
|
|
6
37
|
# [9.3.0](https://github.com/cozy/cozy-libs/compare/cozy-harvest-lib@9.2.7...cozy-harvest-lib@9.3.0) (2022-05-17)
|
|
7
38
|
|
|
8
39
|
|
|
@@ -506,7 +506,8 @@ export var DumbTriggerManager = /*#__PURE__*/function (_Component) {
|
|
|
506
506
|
fieldOptions = _this$props5.fieldOptions,
|
|
507
507
|
flow = _this$props5.flow,
|
|
508
508
|
flowState = _this$props5.flowState,
|
|
509
|
-
client = _this$props5.client
|
|
509
|
+
client = _this$props5.client,
|
|
510
|
+
OAuthFormWrapperComp = _this$props5.OAuthFormWrapperComp;
|
|
510
511
|
var submitting = flowState.running;
|
|
511
512
|
var _this$state = this.state,
|
|
512
513
|
account = _this$state.account,
|
|
@@ -521,13 +522,14 @@ export var DumbTriggerManager = /*#__PURE__*/function (_Component) {
|
|
|
521
522
|
var konnectorPolicy = findKonnectorPolicy(konnector);
|
|
522
523
|
|
|
523
524
|
if (oauth || konnectorPolicy.isBIWebView) {
|
|
524
|
-
|
|
525
|
+
var Wrapper = OAuthFormWrapperComp ? OAuthFormWrapperComp : React.Fragment;
|
|
526
|
+
return /*#__PURE__*/React.createElement(Wrapper, null, /*#__PURE__*/React.createElement(OAuthForm, {
|
|
525
527
|
client: client,
|
|
526
528
|
flow: flow,
|
|
527
529
|
account: account,
|
|
528
530
|
konnector: konnector,
|
|
529
531
|
onSuccess: this.handleOAuthAccountId
|
|
530
|
-
});
|
|
532
|
+
}));
|
|
531
533
|
}
|
|
532
534
|
|
|
533
535
|
if (showSpinner) {
|
|
@@ -613,7 +615,9 @@ DumbTriggerManager.propTypes = {
|
|
|
613
615
|
*/
|
|
614
616
|
fieldOptions: PropTypes.object,
|
|
615
617
|
flow: PropTypes.object,
|
|
616
|
-
flowState: PropTypes.object
|
|
618
|
+
flowState: PropTypes.object,
|
|
619
|
+
// Used to inject a component around OAuthForm, and so customize the UI from the app
|
|
620
|
+
OAuthFormWrapperComp: PropTypes.node
|
|
617
621
|
};
|
|
618
622
|
var TriggerManager = compose(translate(), withClient, withVaultUnlockContext, withConnectionFlow())(DumbTriggerManager); // TriggerManager is exported wrapped in FlowProvider to avoid breaking changes.
|
|
619
623
|
|
package/dist/helpers/oauth.js
CHANGED
|
@@ -1,8 +1,9 @@
|
|
|
1
1
|
import uuid from 'uuid/v4';
|
|
2
|
-
import
|
|
2
|
+
import get from 'lodash/get';
|
|
3
3
|
import CozyClient from 'cozy-client';
|
|
4
4
|
import CozyRealtime from 'cozy-realtime';
|
|
5
|
-
import
|
|
5
|
+
import { readCozyDataFromDOM } from 'cozy-ui/transpiled/react/helpers/appDataset';
|
|
6
|
+
import * as konnectors from './konnectors';
|
|
6
7
|
export var OAUTH_REALTIME_CHANNEL = 'oauth-popup';
|
|
7
8
|
/**
|
|
8
9
|
* Checks that the given data for the given konnector is consistent with the
|
|
@@ -51,10 +52,11 @@ export var handleOAuthResponse = function handleOAuthResponse() {
|
|
|
51
52
|
var client = options.client;
|
|
52
53
|
|
|
53
54
|
if (!client) {
|
|
54
|
-
var
|
|
55
|
+
var domain = readCozyDataFromDOM('domain');
|
|
56
|
+
var token = readCozyDataFromDOM('token');
|
|
55
57
|
client = new CozyClient({
|
|
56
|
-
uri: "".concat(window.location.protocol, "//").concat(
|
|
57
|
-
token:
|
|
58
|
+
uri: "".concat(window.location.protocol, "//").concat(domain),
|
|
59
|
+
token: token
|
|
58
60
|
});
|
|
59
61
|
}
|
|
60
62
|
|
|
@@ -18,8 +18,11 @@ import { getBIConnection } from './bi-http';
|
|
|
18
18
|
import assert from '../assert';
|
|
19
19
|
import logger from '../logger';
|
|
20
20
|
import flag from 'cozy-flags';
|
|
21
|
-
import {
|
|
21
|
+
import { setBIConnectionId, saveBIConfig, findAccountWithBiConnection, convertBIErrortoKonnectorJobError, isBudgetInsightConnector } from './budget-insight';
|
|
22
22
|
import { KonnectorJobError } from '../helpers/konnectors';
|
|
23
|
+
import { waitForRealtimeEvent } from './jobUtils';
|
|
24
|
+
import '../types';
|
|
25
|
+
var TEMP_TOKEN_TIMOUT_S = 60;
|
|
23
26
|
export var isBiWebViewConnector = function isBiWebViewConnector(konnector) {
|
|
24
27
|
return flag('harvest.bi.webview') && isBudgetInsightConnector(konnector);
|
|
25
28
|
};
|
|
@@ -116,19 +119,19 @@ export var checkBIConnection = /*#__PURE__*/function () {
|
|
|
116
119
|
|
|
117
120
|
export var handleOAuthAccount = /*#__PURE__*/function () {
|
|
118
121
|
var _ref4 = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime.mark(function _callee2(_ref3) {
|
|
119
|
-
var account, flow, konnector, client, t,
|
|
122
|
+
var account, flow, konnector, client, t, cozyBankIds, biWebviewAccount, connectionId;
|
|
120
123
|
return _regeneratorRuntime.wrap(function _callee2$(_context2) {
|
|
121
124
|
while (1) {
|
|
122
125
|
switch (_context2.prev = _context2.next) {
|
|
123
126
|
case 0:
|
|
124
127
|
account = _ref3.account, flow = _ref3.flow, konnector = _ref3.konnector, client = _ref3.client, t = _ref3.t;
|
|
125
|
-
|
|
128
|
+
cozyBankIds = getCozyBankIds({
|
|
126
129
|
konnector: konnector,
|
|
127
130
|
account: account
|
|
128
131
|
});
|
|
129
|
-
biWebviewAccount = _objectSpread(_objectSpread({}, account),
|
|
132
|
+
biWebviewAccount = _objectSpread(_objectSpread({}, account), cozyBankIds ? {
|
|
130
133
|
auth: {
|
|
131
|
-
|
|
134
|
+
bankIds: cozyBankIds
|
|
132
135
|
}
|
|
133
136
|
} : {});
|
|
134
137
|
connectionId = getWebviewBIConnectionId(biWebviewAccount);
|
|
@@ -240,26 +243,125 @@ export var onBIAccountCreation = /*#__PURE__*/function () {
|
|
|
240
243
|
return _ref6.apply(this, arguments);
|
|
241
244
|
};
|
|
242
245
|
}();
|
|
246
|
+
export var fetchExtraOAuthUrlParams = /*#__PURE__*/function () {
|
|
247
|
+
var _ref8 = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime.mark(function _callee4(_ref7) {
|
|
248
|
+
var client, konnector, account, _yield$createTemporar, token, biBankId, biBankIds;
|
|
249
|
+
|
|
250
|
+
return _regeneratorRuntime.wrap(function _callee4$(_context4) {
|
|
251
|
+
while (1) {
|
|
252
|
+
switch (_context4.prev = _context4.next) {
|
|
253
|
+
case 0:
|
|
254
|
+
client = _ref7.client, konnector = _ref7.konnector, account = _ref7.account;
|
|
255
|
+
_context4.next = 3;
|
|
256
|
+
return createTemporaryToken({
|
|
257
|
+
client: client,
|
|
258
|
+
konnector: konnector,
|
|
259
|
+
account: account
|
|
260
|
+
});
|
|
261
|
+
|
|
262
|
+
case 3:
|
|
263
|
+
_yield$createTemporar = _context4.sent;
|
|
264
|
+
token = _yield$createTemporar.code;
|
|
265
|
+
biBankId = _yield$createTemporar.biBankId;
|
|
266
|
+
biBankIds = _yield$createTemporar.biBankIds;
|
|
267
|
+
return _context4.abrupt("return", {
|
|
268
|
+
id_connector: biBankId || biBankIds,
|
|
269
|
+
token: token
|
|
270
|
+
});
|
|
271
|
+
|
|
272
|
+
case 8:
|
|
273
|
+
case "end":
|
|
274
|
+
return _context4.stop();
|
|
275
|
+
}
|
|
276
|
+
}
|
|
277
|
+
}, _callee4);
|
|
278
|
+
}));
|
|
279
|
+
|
|
280
|
+
return function fetchExtraOAuthUrlParams(_x4) {
|
|
281
|
+
return _ref8.apply(this, arguments);
|
|
282
|
+
};
|
|
283
|
+
}();
|
|
243
284
|
/**
|
|
244
285
|
* Finds the current bankIid in a given konnector or account
|
|
245
286
|
*
|
|
246
287
|
* @param {io.cozy.accounts} options.account The account content
|
|
247
288
|
* @param {io.cozy.konnectors} options.konnector connector manifest content
|
|
289
|
+
* @return {Array<String>} - list of bank ids
|
|
248
290
|
*/
|
|
249
291
|
|
|
250
|
-
export var
|
|
251
|
-
var _konnector$parameters, _account$auth;
|
|
292
|
+
export var getCozyBankIds = function getCozyBankIds(_ref9) {
|
|
293
|
+
var _konnector$parameters, _account$auth, _konnector$fields, _konnector$fields$ban;
|
|
252
294
|
|
|
253
|
-
var konnector =
|
|
254
|
-
account =
|
|
295
|
+
var konnector = _ref9.konnector,
|
|
296
|
+
account = _ref9.account;
|
|
255
297
|
var cozyBankId = (konnector === null || konnector === void 0 ? void 0 : (_konnector$parameters = konnector.parameters) === null || _konnector$parameters === void 0 ? void 0 : _konnector$parameters.bankId) || (account === null || account === void 0 ? void 0 : (_account$auth = account.auth) === null || _account$auth === void 0 ? void 0 : _account$auth.bankId);
|
|
256
298
|
|
|
257
|
-
if (
|
|
299
|
+
if (cozyBankId) {
|
|
300
|
+
return [cozyBankId];
|
|
301
|
+
}
|
|
302
|
+
|
|
303
|
+
var cozyBankIds = konnector === null || konnector === void 0 ? void 0 : (_konnector$fields = konnector.fields) === null || _konnector$fields === void 0 ? void 0 : (_konnector$fields$ban = _konnector$fields.bankId) === null || _konnector$fields$ban === void 0 ? void 0 : _konnector$fields$ban.options.map(function (opt) {
|
|
304
|
+
return opt === null || opt === void 0 ? void 0 : opt.value;
|
|
305
|
+
});
|
|
306
|
+
|
|
307
|
+
if (!(cozyBankIds !== null && cozyBankIds !== void 0 && cozyBankIds.length)) {
|
|
258
308
|
logger.error('Could not find any bank id');
|
|
259
309
|
}
|
|
260
310
|
|
|
261
|
-
return
|
|
311
|
+
return cozyBankIds;
|
|
262
312
|
};
|
|
313
|
+
/**
|
|
314
|
+
* Gets a temporary token corresponding to the current BI user
|
|
315
|
+
*
|
|
316
|
+
* @param {CozyClient} options.client - CozyClient instance
|
|
317
|
+
* @param {io.cozy.konnectors} options.konnector connector manifest content
|
|
318
|
+
* @param {io.cozy.accounts} options.account The account content
|
|
319
|
+
*
|
|
320
|
+
* @returns {createTemporaryTokenResponse}
|
|
321
|
+
*/
|
|
322
|
+
|
|
323
|
+
export var createTemporaryToken = /*#__PURE__*/function () {
|
|
324
|
+
var _ref11 = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime.mark(function _callee5(_ref10) {
|
|
325
|
+
var client, konnector, account, cozyBankIds, jobResponse, event;
|
|
326
|
+
return _regeneratorRuntime.wrap(function _callee5$(_context5) {
|
|
327
|
+
while (1) {
|
|
328
|
+
switch (_context5.prev = _context5.next) {
|
|
329
|
+
case 0:
|
|
330
|
+
client = _ref10.client, konnector = _ref10.konnector, account = _ref10.account;
|
|
331
|
+
assert(konnector.slug, 'createTemporaryToken: konnector passed in options has no slug');
|
|
332
|
+
cozyBankIds = getCozyBankIds({
|
|
333
|
+
konnector: konnector,
|
|
334
|
+
account: account
|
|
335
|
+
});
|
|
336
|
+
assert(cozyBankIds.length, 'createTemporaryToken: Could not determine cozyBankId from account or konnector');
|
|
337
|
+
_context5.next = 6;
|
|
338
|
+
return client.stackClient.jobs.create('konnector', {
|
|
339
|
+
mode: 'getTemporaryToken',
|
|
340
|
+
konnector: konnector.slug,
|
|
341
|
+
bankIds: cozyBankIds
|
|
342
|
+
}, {}, true);
|
|
343
|
+
|
|
344
|
+
case 6:
|
|
345
|
+
jobResponse = _context5.sent;
|
|
346
|
+
_context5.next = 9;
|
|
347
|
+
return waitForRealtimeEvent(client, jobResponse.data.attributes, 'result', TEMP_TOKEN_TIMOUT_S * 1000);
|
|
348
|
+
|
|
349
|
+
case 9:
|
|
350
|
+
event = _context5.sent;
|
|
351
|
+
return _context5.abrupt("return", event.data.result);
|
|
352
|
+
|
|
353
|
+
case 11:
|
|
354
|
+
case "end":
|
|
355
|
+
return _context5.stop();
|
|
356
|
+
}
|
|
357
|
+
}
|
|
358
|
+
}, _callee5);
|
|
359
|
+
}));
|
|
360
|
+
|
|
361
|
+
return function createTemporaryToken(_x5) {
|
|
362
|
+
return _ref11.apply(this, arguments);
|
|
363
|
+
};
|
|
364
|
+
}();
|
|
263
365
|
export var konnectorPolicy = {
|
|
264
366
|
isBIWebView: true,
|
|
265
367
|
name: 'budget-insight-webview',
|
|
@@ -34,6 +34,7 @@ import { mkConnAuth, biErrorMap } from 'cozy-bi-auth';
|
|
|
34
34
|
import { KonnectorJobError } from '../helpers/konnectors';
|
|
35
35
|
import { LOGIN_SUCCESS_EVENT } from '../models/flowEvents';
|
|
36
36
|
import logger from '../logger';
|
|
37
|
+
import '../types';
|
|
37
38
|
var DECOUPLED_ERROR = 'decoupled';
|
|
38
39
|
var ADDITIONAL_INFORMATION_NEEDED_ERROR = 'additionalInformationNeeded';
|
|
39
40
|
var TEMP_TOKEN_TIMOUT_S = 60;
|
|
@@ -401,19 +402,6 @@ export var resumeBIConnection = function resumeBIConnection(flow) {
|
|
|
401
402
|
resume: 'true'
|
|
402
403
|
});
|
|
403
404
|
};
|
|
404
|
-
/**
|
|
405
|
-
* @typedef biConnection
|
|
406
|
-
* @property {number} id
|
|
407
|
-
* @property {number} id_user
|
|
408
|
-
* @property {number} id_connector
|
|
409
|
-
* @property {string|null} state - ( wrongpass | additionalInformationNeeded | websiteUnavailable | actionNeeded | SCARequired | decoupled | passwordExpired | webauthRequired | rateLimiting | bug). Null indicates a success
|
|
410
|
-
* @property {string|null} last_update - Date string: Last successful update.
|
|
411
|
-
* @property {string|null} created - Date string: Creation date
|
|
412
|
-
* @property {boolean} active - Whether this connection is active and will be automatically synced.
|
|
413
|
-
* @property {string|null} last_push - Date string: Last successfull push
|
|
414
|
-
* @property {string|null} next_try - Date string: Date of next synchronization.
|
|
415
|
-
*/
|
|
416
|
-
|
|
417
405
|
/**
|
|
418
406
|
* Checks for any number 2FA and/or decoupled requests
|
|
419
407
|
*
|
package/dist/types.js
ADDED
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @typedef createTemporaryTokenResponse
|
|
3
|
+
* @property {String} code - the temporary token
|
|
4
|
+
* @property {String} url - BI environment url
|
|
5
|
+
* @property {String} bankId - Cozy bank id corresponding to the current connector (deprecated once bi webviews are in production)
|
|
6
|
+
* @property {String} biBankId - BI bank id corresponding to the bankId translated by the connector (deprecated once bi webviews are in production)
|
|
7
|
+
* @property {Array<String>} bankIds - Cozy bank ids corresponding to the current connector
|
|
8
|
+
* @property {Array<String>} biBankIds - BI bank ids corresponding to the bankIds translated by the connector
|
|
9
|
+
*/
|
|
10
|
+
|
|
11
|
+
/**
|
|
12
|
+
* @typedef biConnection
|
|
13
|
+
* @property {number} id
|
|
14
|
+
* @property {number} id_user
|
|
15
|
+
* @property {number} id_connector
|
|
16
|
+
* @property {string|null} state - ( wrongpass | additionalInformationNeeded | websiteUnavailable | actionNeeded | SCARequired | decoupled | passwordExpired | webauthRequired | rateLimiting | bug). Null indicates a success
|
|
17
|
+
* @property {string|null} last_update - Date string: Last successful update.
|
|
18
|
+
* @property {string|null} created - Date string: Creation date
|
|
19
|
+
* @property {boolean} active - Whether this connection is active and will be automatically synced.
|
|
20
|
+
* @property {string|null} last_push - Date string: Last successfull push
|
|
21
|
+
* @property {string|null} next_try - Date string: Date of next synchronization.
|
|
22
|
+
*/
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "cozy-harvest-lib",
|
|
3
|
-
"version": "9.
|
|
3
|
+
"version": "9.5.1",
|
|
4
4
|
"description": "Provides logic, modules and components for Cozy's harvest applications.",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"author": "Cozy",
|
|
@@ -44,7 +44,7 @@
|
|
|
44
44
|
"@babel/cli": "7.16.8",
|
|
45
45
|
"@babel/core": "7.16.12",
|
|
46
46
|
"@babel/register": "7.16.9",
|
|
47
|
-
"@cozy/cli-tree": "^0.
|
|
47
|
+
"@cozy/cli-tree": "^0.6.0",
|
|
48
48
|
"@material-ui/core": "4.11.3",
|
|
49
49
|
"@material-ui/lab": "4.0.0-alpha.60",
|
|
50
50
|
"@testing-library/jest-dom": "5.16.4",
|
|
@@ -87,5 +87,5 @@
|
|
|
87
87
|
"react-router-dom": "^5.0.1"
|
|
88
88
|
},
|
|
89
89
|
"sideEffects": false,
|
|
90
|
-
"gitHead": "
|
|
90
|
+
"gitHead": "059a5e08c80f9576846d12f23a23f59441d0988d"
|
|
91
91
|
}
|
|
@@ -312,8 +312,16 @@ export class DumbTriggerManager extends Component {
|
|
|
312
312
|
}
|
|
313
313
|
|
|
314
314
|
render() {
|
|
315
|
-
const {
|
|
316
|
-
|
|
315
|
+
const {
|
|
316
|
+
konnector,
|
|
317
|
+
showError,
|
|
318
|
+
t,
|
|
319
|
+
fieldOptions,
|
|
320
|
+
flow,
|
|
321
|
+
flowState,
|
|
322
|
+
client,
|
|
323
|
+
OAuthFormWrapperComp
|
|
324
|
+
} = this.props
|
|
317
325
|
|
|
318
326
|
const submitting = flowState.running
|
|
319
327
|
|
|
@@ -328,14 +336,19 @@ export class DumbTriggerManager extends Component {
|
|
|
328
336
|
const konnectorPolicy = findKonnectorPolicy(konnector)
|
|
329
337
|
|
|
330
338
|
if (oauth || konnectorPolicy.isBIWebView) {
|
|
339
|
+
const Wrapper = OAuthFormWrapperComp
|
|
340
|
+
? OAuthFormWrapperComp
|
|
341
|
+
: React.Fragment
|
|
331
342
|
return (
|
|
332
|
-
<
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
343
|
+
<Wrapper>
|
|
344
|
+
<OAuthForm
|
|
345
|
+
client={client}
|
|
346
|
+
flow={flow}
|
|
347
|
+
account={account}
|
|
348
|
+
konnector={konnector}
|
|
349
|
+
onSuccess={this.handleOAuthAccountId}
|
|
350
|
+
/>
|
|
351
|
+
</Wrapper>
|
|
339
352
|
)
|
|
340
353
|
}
|
|
341
354
|
|
|
@@ -429,7 +442,9 @@ DumbTriggerManager.propTypes = {
|
|
|
429
442
|
*/
|
|
430
443
|
fieldOptions: PropTypes.object,
|
|
431
444
|
flow: PropTypes.object,
|
|
432
|
-
flowState: PropTypes.object
|
|
445
|
+
flowState: PropTypes.object,
|
|
446
|
+
// Used to inject a component around OAuthForm, and so customize the UI from the app
|
|
447
|
+
OAuthFormWrapperComp: PropTypes.node
|
|
433
448
|
}
|
|
434
449
|
|
|
435
450
|
const TriggerManager = compose(
|
package/src/helpers/oauth.js
CHANGED
|
@@ -1,9 +1,11 @@
|
|
|
1
1
|
import uuid from 'uuid/v4'
|
|
2
|
+
import get from 'lodash/get'
|
|
2
3
|
|
|
3
|
-
import * as konnectors from './konnectors'
|
|
4
4
|
import CozyClient from 'cozy-client'
|
|
5
5
|
import CozyRealtime from 'cozy-realtime'
|
|
6
|
-
import
|
|
6
|
+
import { readCozyDataFromDOM } from 'cozy-ui/transpiled/react/helpers/appDataset'
|
|
7
|
+
|
|
8
|
+
import * as konnectors from './konnectors'
|
|
7
9
|
|
|
8
10
|
export const OAUTH_REALTIME_CHANNEL = 'oauth-popup'
|
|
9
11
|
|
|
@@ -55,10 +57,12 @@ export const handleOAuthResponse = (options = {}) => {
|
|
|
55
57
|
if (!realtime) {
|
|
56
58
|
let client = options.client
|
|
57
59
|
if (!client) {
|
|
58
|
-
const
|
|
60
|
+
const domain = readCozyDataFromDOM('domain')
|
|
61
|
+
const token = readCozyDataFromDOM('token')
|
|
62
|
+
|
|
59
63
|
client = new CozyClient({
|
|
60
|
-
uri: `${window.location.protocol}//${
|
|
61
|
-
token:
|
|
64
|
+
uri: `${window.location.protocol}//${domain}`,
|
|
65
|
+
token: token
|
|
62
66
|
})
|
|
63
67
|
}
|
|
64
68
|
realtime = new CozyRealtime({ client })
|
|
@@ -9,8 +9,6 @@ import assert from '../assert'
|
|
|
9
9
|
import logger from '../logger'
|
|
10
10
|
import flag from 'cozy-flags'
|
|
11
11
|
import {
|
|
12
|
-
fetchExtraOAuthUrlParams,
|
|
13
|
-
createTemporaryToken,
|
|
14
12
|
setBIConnectionId,
|
|
15
13
|
saveBIConfig,
|
|
16
14
|
findAccountWithBiConnection,
|
|
@@ -18,6 +16,10 @@ import {
|
|
|
18
16
|
isBudgetInsightConnector
|
|
19
17
|
} from './budget-insight'
|
|
20
18
|
import { KonnectorJobError } from '../helpers/konnectors'
|
|
19
|
+
import { waitForRealtimeEvent } from './jobUtils'
|
|
20
|
+
import '../types'
|
|
21
|
+
|
|
22
|
+
const TEMP_TOKEN_TIMOUT_S = 60
|
|
21
23
|
|
|
22
24
|
export const isBiWebViewConnector = konnector =>
|
|
23
25
|
flag('harvest.bi.webview') && isBudgetInsightConnector(konnector)
|
|
@@ -94,10 +96,10 @@ export const handleOAuthAccount = async ({
|
|
|
94
96
|
client,
|
|
95
97
|
t
|
|
96
98
|
}) => {
|
|
97
|
-
const
|
|
99
|
+
const cozyBankIds = getCozyBankIds({ konnector, account })
|
|
98
100
|
let biWebviewAccount = {
|
|
99
101
|
...account,
|
|
100
|
-
...(
|
|
102
|
+
...(cozyBankIds ? { auth: { bankIds: cozyBankIds } } : {})
|
|
101
103
|
}
|
|
102
104
|
|
|
103
105
|
const connectionId = getWebviewBIConnectionId(biWebviewAccount)
|
|
@@ -167,18 +169,81 @@ export const onBIAccountCreation = async ({
|
|
|
167
169
|
return await flow.saveAccount(setBIConnectionId(account, biConnection.id))
|
|
168
170
|
}
|
|
169
171
|
|
|
172
|
+
export const fetchExtraOAuthUrlParams = async ({
|
|
173
|
+
client,
|
|
174
|
+
konnector,
|
|
175
|
+
account
|
|
176
|
+
}) => {
|
|
177
|
+
const {
|
|
178
|
+
code: token,
|
|
179
|
+
biBankId,
|
|
180
|
+
biBankIds
|
|
181
|
+
} = await createTemporaryToken({
|
|
182
|
+
client,
|
|
183
|
+
konnector,
|
|
184
|
+
account
|
|
185
|
+
})
|
|
186
|
+
|
|
187
|
+
return { id_connector: biBankId || biBankIds, token }
|
|
188
|
+
}
|
|
189
|
+
|
|
170
190
|
/**
|
|
171
191
|
* Finds the current bankIid in a given konnector or account
|
|
172
192
|
*
|
|
173
193
|
* @param {io.cozy.accounts} options.account The account content
|
|
174
194
|
* @param {io.cozy.konnectors} options.konnector connector manifest content
|
|
195
|
+
* @return {Array<String>} - list of bank ids
|
|
175
196
|
*/
|
|
176
|
-
export const
|
|
197
|
+
export const getCozyBankIds = ({ konnector, account }) => {
|
|
177
198
|
const cozyBankId = konnector?.parameters?.bankId || account?.auth?.bankId
|
|
178
|
-
|
|
199
|
+
|
|
200
|
+
if (cozyBankId) {
|
|
201
|
+
return [cozyBankId]
|
|
202
|
+
}
|
|
203
|
+
|
|
204
|
+
const cozyBankIds = konnector?.fields?.bankId?.options.map(opt => opt?.value)
|
|
205
|
+
if (!cozyBankIds?.length) {
|
|
179
206
|
logger.error('Could not find any bank id')
|
|
180
207
|
}
|
|
181
|
-
return
|
|
208
|
+
return cozyBankIds
|
|
209
|
+
}
|
|
210
|
+
|
|
211
|
+
/**
|
|
212
|
+
* Gets a temporary token corresponding to the current BI user
|
|
213
|
+
*
|
|
214
|
+
* @param {CozyClient} options.client - CozyClient instance
|
|
215
|
+
* @param {io.cozy.konnectors} options.konnector connector manifest content
|
|
216
|
+
* @param {io.cozy.accounts} options.account The account content
|
|
217
|
+
*
|
|
218
|
+
* @returns {createTemporaryTokenResponse}
|
|
219
|
+
*/
|
|
220
|
+
export const createTemporaryToken = async ({ client, konnector, account }) => {
|
|
221
|
+
assert(
|
|
222
|
+
konnector.slug,
|
|
223
|
+
'createTemporaryToken: konnector passed in options has no slug'
|
|
224
|
+
)
|
|
225
|
+
const cozyBankIds = getCozyBankIds({ konnector, account })
|
|
226
|
+
assert(
|
|
227
|
+
cozyBankIds.length,
|
|
228
|
+
'createTemporaryToken: Could not determine cozyBankId from account or konnector'
|
|
229
|
+
)
|
|
230
|
+
const jobResponse = await client.stackClient.jobs.create(
|
|
231
|
+
'konnector',
|
|
232
|
+
{
|
|
233
|
+
mode: 'getTemporaryToken',
|
|
234
|
+
konnector: konnector.slug,
|
|
235
|
+
bankIds: cozyBankIds
|
|
236
|
+
},
|
|
237
|
+
{},
|
|
238
|
+
true
|
|
239
|
+
)
|
|
240
|
+
const event = await waitForRealtimeEvent(
|
|
241
|
+
client,
|
|
242
|
+
jobResponse.data.attributes,
|
|
243
|
+
'result',
|
|
244
|
+
TEMP_TOKEN_TIMOUT_S * 1000
|
|
245
|
+
)
|
|
246
|
+
return event.data.result
|
|
182
247
|
}
|
|
183
248
|
|
|
184
249
|
export const konnectorPolicy = {
|
|
@@ -27,6 +27,7 @@ import { mkConnAuth, biErrorMap } from 'cozy-bi-auth'
|
|
|
27
27
|
import { KonnectorJobError } from '../helpers/konnectors'
|
|
28
28
|
import { LOGIN_SUCCESS_EVENT } from '../models/flowEvents'
|
|
29
29
|
import logger from '../logger'
|
|
30
|
+
import '../types'
|
|
30
31
|
|
|
31
32
|
const DECOUPLED_ERROR = 'decoupled'
|
|
32
33
|
const ADDITIONAL_INFORMATION_NEEDED_ERROR = 'additionalInformationNeeded'
|
|
@@ -292,19 +293,6 @@ export const resumeBIConnection = flow => {
|
|
|
292
293
|
return updateBIConnectionFromFlow(flow, { resume: 'true' })
|
|
293
294
|
}
|
|
294
295
|
|
|
295
|
-
/**
|
|
296
|
-
* @typedef biConnection
|
|
297
|
-
* @property {number} id
|
|
298
|
-
* @property {number} id_user
|
|
299
|
-
* @property {number} id_connector
|
|
300
|
-
* @property {string|null} state - ( wrongpass | additionalInformationNeeded | websiteUnavailable | actionNeeded | SCARequired | decoupled | passwordExpired | webauthRequired | rateLimiting | bug). Null indicates a success
|
|
301
|
-
* @property {string|null} last_update - Date string: Last successful update.
|
|
302
|
-
* @property {string|null} created - Date string: Creation date
|
|
303
|
-
* @property {boolean} active - Whether this connection is active and will be automatically synced.
|
|
304
|
-
* @property {string|null} last_push - Date string: Last successfull push
|
|
305
|
-
* @property {string|null} next_try - Date string: Date of next synchronization.
|
|
306
|
-
*/
|
|
307
|
-
|
|
308
296
|
/**
|
|
309
297
|
* Checks for any number 2FA and/or decoupled requests
|
|
310
298
|
*
|
package/src/types.js
ADDED
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @typedef createTemporaryTokenResponse
|
|
3
|
+
* @property {String} code - the temporary token
|
|
4
|
+
* @property {String} url - BI environment url
|
|
5
|
+
* @property {String} bankId - Cozy bank id corresponding to the current connector (deprecated once bi webviews are in production)
|
|
6
|
+
* @property {String} biBankId - BI bank id corresponding to the bankId translated by the connector (deprecated once bi webviews are in production)
|
|
7
|
+
* @property {Array<String>} bankIds - Cozy bank ids corresponding to the current connector
|
|
8
|
+
* @property {Array<String>} biBankIds - BI bank ids corresponding to the bankIds translated by the connector
|
|
9
|
+
*/
|
|
10
|
+
|
|
11
|
+
/**
|
|
12
|
+
* @typedef biConnection
|
|
13
|
+
* @property {number} id
|
|
14
|
+
* @property {number} id_user
|
|
15
|
+
* @property {number} id_connector
|
|
16
|
+
* @property {string|null} state - ( wrongpass | additionalInformationNeeded | websiteUnavailable | actionNeeded | SCARequired | decoupled | passwordExpired | webauthRequired | rateLimiting | bug). Null indicates a success
|
|
17
|
+
* @property {string|null} last_update - Date string: Last successful update.
|
|
18
|
+
* @property {string|null} created - Date string: Creation date
|
|
19
|
+
* @property {boolean} active - Whether this connection is active and will be automatically synced.
|
|
20
|
+
* @property {string|null} last_push - Date string: Last successfull push
|
|
21
|
+
* @property {string|null} next_try - Date string: Date of next synchronization.
|
|
22
|
+
*/
|