@abtnode/auth 1.16.54-beta-20251021-070951-25e3083c → 1.16.54-beta-20251024-030947-6f2889bf

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.
Files changed (2) hide show
  1. package/lib/util/federated.js +131 -1
  2. package/package.json +20 -19
@@ -1,4 +1,9 @@
1
- const { WELLKNOWN_SERVICE_PATH_PREFIX, USER_AVATAR_URL_PREFIX, USER_AVATAR_PATH_PREFIX } = require('@abtnode/constant');
1
+ const {
2
+ WELLKNOWN_SERVICE_PATH_PREFIX,
3
+ USER_AVATAR_URL_PREFIX,
4
+ USER_AVATAR_PATH_PREFIX,
5
+ FEDERATED,
6
+ } = require('@abtnode/constant');
2
7
  const { Joi } = require('@arcblock/validator');
3
8
  const pRetry = require('p-retry');
4
9
  const { signV2 } = require('@arcblock/jwt');
@@ -9,10 +14,50 @@ const { getSignData } = require('@blocklet/sdk/lib/util/verify-sign');
9
14
  const { SIG_VERSION } = require('@blocklet/constant');
10
15
  const cloneDeep = require('@abtnode/util/lib/deep-clone');
11
16
  const defaults = require('lodash/defaults');
17
+ const pick = require('lodash/pick');
18
+ const isUndefined = require('lodash/isUndefined');
19
+ const pLimit = require('p-limit');
12
20
 
13
21
  const request = require('./request');
14
22
  const logger = require('../logger');
15
23
 
24
+ const USER_PROFILE_SYNC_FIELDS = [
25
+ 'action', // 表示对该 user 的操作
26
+ 'did',
27
+ 'pk',
28
+ 'avatar',
29
+ 'fullName',
30
+ 'email',
31
+ 'connectedAccount',
32
+ 'disconnectedAccount',
33
+ 'sourceAppPid',
34
+ 'inviter',
35
+ 'generation',
36
+ 'emailVerified',
37
+ 'phoneVerified',
38
+ ];
39
+
40
+ const SITE_SYNC_FIELDS = [
41
+ 'action',
42
+ 'appId',
43
+ 'appPid',
44
+ 'aliasDid',
45
+ 'appName',
46
+ 'appDescription',
47
+ 'appUrl',
48
+ 'aliasDomain',
49
+ 'appLogo',
50
+ 'appLogoRect',
51
+ 'appliedAt',
52
+ 'did',
53
+ 'pk',
54
+ 'serverId',
55
+ 'serverVersion',
56
+ 'version',
57
+ 'isMaster',
58
+ 'status',
59
+ ];
60
+
16
61
  const federatedEnvSchema = Joi.object({
17
62
  sigVersion: Joi.string().optional().allow('').default(''),
18
63
  }).unknown(true);
@@ -192,8 +237,93 @@ async function migrateFederatedAccount({ blocklet, blockletInfo, fromUserDid, to
192
237
  return result;
193
238
  }
194
239
 
240
+ /**
241
+ * 同步统一登录站点群信息
242
+ * 可同步的信息包括:站点成员列表(全量)、站点成员信息(增量)
243
+ * @param {object} options
244
+ * @param {object} options.blocklet - 当前 blocklet 数据
245
+ * @param {object} options.data - 需要同步的数据
246
+ * @param {Array} [options.data.users] - 需要同步的数据(用户)
247
+ * @param {Array} [options.data.sites] - 需要同步的数据(站点)
248
+ * @param {Array} [options.nodeInfo] - 当前 blocklet-server 的 info
249
+ * @returns
250
+ */
251
+ async function syncFederated({
252
+ data = {},
253
+ syncSites,
254
+ allowStatus = ['approved', 'revoked'],
255
+ userFields = USER_PROFILE_SYNC_FIELDS,
256
+ siteFields = SITE_SYNC_FIELDS,
257
+ nodeInfo,
258
+ blocklet,
259
+ } = {}) {
260
+ const federated = safeGetFederated(blocklet);
261
+
262
+ const safeData = {};
263
+ const { users, sites } = data;
264
+ if (users && Array.isArray(users)) {
265
+ safeData.users = users.map((item) => pick(item, userFields));
266
+ }
267
+
268
+ if (sites && Array.isArray(sites)) {
269
+ safeData.sites = sites.map((item) => pick(item, siteFields));
270
+ }
271
+
272
+ const { permanentWallet } = getBlockletInfo(blocklet, nodeInfo.sk);
273
+ const limitSync = pLimit(FEDERATED.SYNC_LIMIT);
274
+
275
+ const waitingList = federated.sites
276
+ .filter((item) => !item.status || allowStatus.includes(item.status))
277
+ .filter((item) => {
278
+ // 未指定 syncSites 向全员通知(除了自己)
279
+ if (isUndefined(syncSites)) {
280
+ // 排除通知自己
281
+ return item.appPid !== blocklet.appPid;
282
+ }
283
+ // 如果指定了要通知的站点,则按指定的站点来过滤
284
+ if (Array.isArray(syncSites)) {
285
+ return syncSites.some((x) => x.appPid === item.appPid);
286
+ }
287
+ return false;
288
+ })
289
+ .map(async (item) => {
290
+ const resultItem = await limitSync(async () => {
291
+ try {
292
+ // NOTICE: 即使通知某个站点失败了,也不影响其他站点接收同步结果
293
+ const result = await callFederated({
294
+ action: 'sync',
295
+ permanentWallet,
296
+ site: item,
297
+ data: safeData,
298
+ });
299
+ logger.info('Sync federated sites successfully', {
300
+ action: 'sync',
301
+ site: item,
302
+ data: safeData,
303
+ });
304
+ return result;
305
+ } catch (error) {
306
+ logger.error('Failed to sync federated sites', {
307
+ error,
308
+ action: 'sync',
309
+ site: item,
310
+ data: safeData,
311
+ });
312
+ return null;
313
+ }
314
+ });
315
+ return {
316
+ site: item,
317
+ result: resultItem,
318
+ };
319
+ });
320
+ const resultList = await Promise.all(waitingList);
321
+ return resultList;
322
+ }
323
+
195
324
  module.exports = {
196
325
  callFederated,
326
+ syncFederated,
197
327
  getFederatedSiteEnv,
198
328
  getUserAvatarUrl,
199
329
  shouldSyncFederated,
package/package.json CHANGED
@@ -3,7 +3,7 @@
3
3
  "publishConfig": {
4
4
  "access": "public"
5
5
  },
6
- "version": "1.16.54-beta-20251021-070951-25e3083c",
6
+ "version": "1.16.54-beta-20251024-030947-6f2889bf",
7
7
  "description": "Simple lib to manage auth in ABT Node",
8
8
  "main": "lib/index.js",
9
9
  "files": [
@@ -20,25 +20,25 @@
20
20
  "author": "linchen <linchen1987@foxmail.com> (http://github.com/linchen1987)",
21
21
  "license": "Apache-2.0",
22
22
  "dependencies": {
23
- "@abtnode/constant": "1.16.54-beta-20251021-070951-25e3083c",
24
- "@abtnode/logger": "1.16.54-beta-20251021-070951-25e3083c",
25
- "@abtnode/util": "1.16.54-beta-20251021-070951-25e3083c",
26
- "@arcblock/did": "^1.26.2",
27
- "@arcblock/did-connect-js": "^1.26.2",
28
- "@arcblock/did-ext": "^1.26.2",
29
- "@arcblock/did-util": "^1.26.2",
30
- "@arcblock/jwt": "^1.26.2",
23
+ "@abtnode/constant": "1.16.54-beta-20251024-030947-6f2889bf",
24
+ "@abtnode/logger": "1.16.54-beta-20251024-030947-6f2889bf",
25
+ "@abtnode/util": "1.16.54-beta-20251024-030947-6f2889bf",
26
+ "@arcblock/did": "^1.26.3",
27
+ "@arcblock/did-connect-js": "^1.26.3",
28
+ "@arcblock/did-ext": "^1.26.3",
29
+ "@arcblock/did-util": "^1.26.3",
30
+ "@arcblock/jwt": "^1.26.3",
31
31
  "@arcblock/nft-display": "^3.1.51",
32
- "@arcblock/validator": "^1.26.2",
33
- "@arcblock/vc": "^1.26.2",
34
- "@blocklet/constant": "1.16.54-beta-20251021-070951-25e3083c",
32
+ "@arcblock/validator": "^1.26.3",
33
+ "@arcblock/vc": "^1.26.3",
34
+ "@blocklet/constant": "1.16.54-beta-20251024-030947-6f2889bf",
35
35
  "@blocklet/error": "^0.2.5",
36
- "@blocklet/meta": "1.16.54-beta-20251021-070951-25e3083c",
37
- "@blocklet/sdk": "1.16.54-beta-20251021-070951-25e3083c",
38
- "@ocap/client": "^1.26.2",
39
- "@ocap/mcrypto": "^1.26.2",
40
- "@ocap/util": "^1.26.2",
41
- "@ocap/wallet": "^1.26.2",
36
+ "@blocklet/meta": "1.16.54-beta-20251024-030947-6f2889bf",
37
+ "@blocklet/sdk": "1.16.54-beta-20251024-030947-6f2889bf",
38
+ "@ocap/client": "^1.26.3",
39
+ "@ocap/mcrypto": "^1.26.3",
40
+ "@ocap/util": "^1.26.3",
41
+ "@ocap/wallet": "^1.26.3",
42
42
  "@simplewebauthn/server": "^13.1.1",
43
43
  "axios": "^1.7.9",
44
44
  "flat": "^5.0.2",
@@ -48,6 +48,7 @@
48
48
  "jsonwebtoken": "^9.0.0",
49
49
  "jwks-rsa": "^3.1.0",
50
50
  "lodash": "^4.17.21",
51
+ "p-limit": "^3.1.0",
51
52
  "p-retry": "^4.6.2",
52
53
  "semver": "^7.6.3",
53
54
  "transliteration": "^2.3.5",
@@ -57,5 +58,5 @@
57
58
  "axios-mock-adapter": "^2.1.0",
58
59
  "jest": "^29.7.0"
59
60
  },
60
- "gitHead": "db517e9013dbad744e38883f56e4eba1fa1615c1"
61
+ "gitHead": "73e5a3a80b82a2a7c62d42fdc08207b28e67633e"
61
62
  }