@abtnode/core 1.16.0-beta-58020de5 → 1.16.0-beta-b741bcb3
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/lib/api/team.js +10 -4
- package/lib/blocklet/manager/disk.js +141 -67
- package/lib/blocklet/manager/helper/install-application-from-dev.js +2 -13
- package/lib/event.js +1 -0
- package/lib/states/blocklet-extras.js +4 -0
- package/lib/states/user.js +22 -1
- package/lib/util/blocklet.js +42 -9
- package/package.json +17 -17
package/lib/api/team.js
CHANGED
|
@@ -136,7 +136,7 @@ class TeamAPI extends EventEmitter {
|
|
|
136
136
|
return doc;
|
|
137
137
|
}
|
|
138
138
|
|
|
139
|
-
async getUsers({ teamDid, query, paging: inputPaging, sort, dids }) {
|
|
139
|
+
async getUsers({ teamDid, query, paging: inputPaging, sort, dids, sourceIds }) {
|
|
140
140
|
const state = await this.getUserState(teamDid);
|
|
141
141
|
|
|
142
142
|
if (inputPaging?.pageSize > MAX_USER_PAGE_SIZE) {
|
|
@@ -158,6 +158,14 @@ class TeamAPI extends EventEmitter {
|
|
|
158
158
|
pageCount: 1,
|
|
159
159
|
page: 1,
|
|
160
160
|
};
|
|
161
|
+
} else if (sourceIds) {
|
|
162
|
+
list = await state.getUsersBySourceIds({ query, sourceIds });
|
|
163
|
+
paging = {
|
|
164
|
+
total: list.length,
|
|
165
|
+
pageSize: sourceIds.length,
|
|
166
|
+
pageCount: 1,
|
|
167
|
+
page: 1,
|
|
168
|
+
};
|
|
161
169
|
} else {
|
|
162
170
|
const doc = await state.getUsers({ query, sort, paging: { pageSize: 20, ...inputPaging } });
|
|
163
171
|
list = doc.list;
|
|
@@ -185,8 +193,7 @@ class TeamAPI extends EventEmitter {
|
|
|
185
193
|
'locale',
|
|
186
194
|
// oauth relate fields
|
|
187
195
|
'source',
|
|
188
|
-
'
|
|
189
|
-
'connectedAccounts',
|
|
196
|
+
'extraConfigs',
|
|
190
197
|
])
|
|
191
198
|
// eslint-disable-next-line function-paren-newline
|
|
192
199
|
),
|
|
@@ -647,7 +654,6 @@ class TeamAPI extends EventEmitter {
|
|
|
647
654
|
}),
|
|
648
655
|
ownerProfile: {
|
|
649
656
|
...currentUser,
|
|
650
|
-
// avatar: await parseUserAvatar(currentUser.avatar, { dataDir: blocklet.env.dataDir }),
|
|
651
657
|
},
|
|
652
658
|
preferredColor: passportColor,
|
|
653
659
|
});
|
|
@@ -11,12 +11,8 @@ const cloneDeep = require('lodash/cloneDeep');
|
|
|
11
11
|
const { isNFTExpired, getNftExpirationDate } = require('@abtnode/util/lib/nft');
|
|
12
12
|
const didDocument = require('@abtnode/util/lib/did-document');
|
|
13
13
|
const { sign } = require('@arcblock/jwt');
|
|
14
|
-
const { isEthereumDid } = require('@arcblock/did');
|
|
15
|
-
const { toSvg: createDidLogo } =
|
|
16
|
-
process.env.NODE_ENV !== 'test' ? require('@arcblock/did-motif') : require('@arcblock/did-motif/dist/did-motif.cjs');
|
|
17
|
-
const getBlockletInfo = require('@blocklet/meta/lib/info');
|
|
18
|
-
const { createBlockiesSvg } = require('@blocklet/meta/lib/blockies');
|
|
19
14
|
const sleep = require('@abtnode/util/lib/sleep');
|
|
15
|
+
const getBlockletInfo = require('@blocklet/meta/lib/info');
|
|
20
16
|
|
|
21
17
|
const logger = require('@abtnode/logger')('@abtnode/core:blocklet:manager');
|
|
22
18
|
const {
|
|
@@ -100,6 +96,7 @@ const {
|
|
|
100
96
|
isRotatingAppDid,
|
|
101
97
|
checkVersionCompatibility,
|
|
102
98
|
getBlockletKnownAs,
|
|
99
|
+
updateBlockletFallbackLogo,
|
|
103
100
|
} = require('../../util/blocklet');
|
|
104
101
|
const states = require('../../states');
|
|
105
102
|
const BaseBlockletManager = require('./base');
|
|
@@ -551,21 +548,29 @@ class BlockletManager extends BaseBlockletManager {
|
|
|
551
548
|
this.emit(BlockletEvents.statusChange, blocklet);
|
|
552
549
|
}
|
|
553
550
|
|
|
554
|
-
|
|
555
|
-
|
|
556
|
-
|
|
557
|
-
|
|
558
|
-
|
|
559
|
-
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
|
|
551
|
+
try {
|
|
552
|
+
const nodeEnvironments = await states.node.getEnvironments();
|
|
553
|
+
await stopBlockletProcess(blocklet, {
|
|
554
|
+
preStop: (b, { ancestors }) =>
|
|
555
|
+
hooks.preStop(b.env.processId, {
|
|
556
|
+
appDir: b.env.appDir,
|
|
557
|
+
hooks: Object.assign(b.meta.hooks || {}, b.meta.scripts || {}),
|
|
558
|
+
env: getRuntimeEnvironments(b, nodeEnvironments, ancestors),
|
|
559
|
+
did, // root blocklet did
|
|
560
|
+
notification: states.notification,
|
|
561
|
+
context,
|
|
562
|
+
exitOnError: false,
|
|
563
|
+
silent,
|
|
564
|
+
}),
|
|
565
|
+
});
|
|
566
|
+
} catch (error) {
|
|
567
|
+
logger.error('Failed to stop blocklet', { error, did });
|
|
568
|
+
if (updateStatus) {
|
|
569
|
+
const res = await states.blocklet.setBlockletStatus(did, BlockletStatus.error);
|
|
570
|
+
this.emit(BlockletEvents.statusChange, res);
|
|
571
|
+
}
|
|
572
|
+
throw error;
|
|
573
|
+
}
|
|
569
574
|
|
|
570
575
|
logger.info('blocklet stopped successfully', { processId, did });
|
|
571
576
|
|
|
@@ -1010,16 +1015,17 @@ class BlockletManager extends BaseBlockletManager {
|
|
|
1010
1015
|
const [rootDid, ...childDids] = dids;
|
|
1011
1016
|
logger.info('config blocklet', { dids });
|
|
1012
1017
|
|
|
1018
|
+
const ancestors = [];
|
|
1013
1019
|
let blocklet = await this.getBlocklet(rootDid);
|
|
1014
1020
|
for (const childDid of childDids) {
|
|
1021
|
+
ancestors.push(blocklet);
|
|
1015
1022
|
blocklet = blocklet.children.find((x) => x.meta.did === childDid);
|
|
1016
1023
|
if (!blocklet) {
|
|
1017
1024
|
throw new Error('Child blocklet does not exist', { dids });
|
|
1018
1025
|
}
|
|
1019
1026
|
}
|
|
1020
1027
|
|
|
1021
|
-
|
|
1022
|
-
const nodeEnvironments = await states.node.getEnvironments();
|
|
1028
|
+
const configObj = {};
|
|
1023
1029
|
for (const x of newConfigs) {
|
|
1024
1030
|
if (x.custom === true) {
|
|
1025
1031
|
// custom key
|
|
@@ -1039,21 +1045,25 @@ class BlockletManager extends BaseBlockletManager {
|
|
|
1039
1045
|
}
|
|
1040
1046
|
}
|
|
1041
1047
|
|
|
1042
|
-
|
|
1048
|
+
configObj[x.key] = x.value;
|
|
1043
1049
|
}
|
|
1044
1050
|
|
|
1051
|
+
// run hook
|
|
1045
1052
|
if (!skipHook) {
|
|
1053
|
+
const nodeEnvironments = await states.node.getEnvironments();
|
|
1046
1054
|
// FIXME: we should also call preConfig for child blocklets
|
|
1047
1055
|
await hooks.preConfig(blocklet.env.processId, {
|
|
1048
1056
|
appDir: blocklet.env.appDir,
|
|
1049
1057
|
hooks: Object.assign(blocklet.meta.hooks || {}, blocklet.meta.scripts || {}),
|
|
1050
1058
|
exitOnError: true,
|
|
1051
|
-
env: { ...getRuntimeEnvironments(blocklet, nodeEnvironments), ...
|
|
1059
|
+
env: { ...getRuntimeEnvironments(blocklet, nodeEnvironments, ancestors), ...configObj },
|
|
1052
1060
|
did,
|
|
1053
1061
|
context,
|
|
1054
1062
|
});
|
|
1055
1063
|
}
|
|
1056
1064
|
|
|
1065
|
+
Object.assign(blocklet.configObj, configObj);
|
|
1066
|
+
|
|
1057
1067
|
const willAppSkChange = isRotatingAppSk(newConfigs, blocklet.configs, blocklet.externalSk);
|
|
1058
1068
|
const willAppDidChange = isRotatingAppDid(newConfigs, blocklet.configs, blocklet.externalSk);
|
|
1059
1069
|
|
|
@@ -1407,6 +1417,7 @@ class BlockletManager extends BaseBlockletManager {
|
|
|
1407
1417
|
{
|
|
1408
1418
|
name: 'clean-expired-blocklet-data',
|
|
1409
1419
|
time: '0 */20 0 * * *', // 每天凌晨 0 点的每 20 分钟
|
|
1420
|
+
options: { runOnInit: false },
|
|
1410
1421
|
fn: () => this._cleanExpiredBlockletData(),
|
|
1411
1422
|
},
|
|
1412
1423
|
{
|
|
@@ -1723,6 +1734,7 @@ class BlockletManager extends BaseBlockletManager {
|
|
|
1723
1734
|
}
|
|
1724
1735
|
|
|
1725
1736
|
// update state to db
|
|
1737
|
+
await states.blockletExtras.updateByDid(did, { appDid: blocklet.appDid });
|
|
1726
1738
|
return states.blocklet.updateBlocklet(did, blocklet);
|
|
1727
1739
|
}
|
|
1728
1740
|
|
|
@@ -1854,24 +1866,46 @@ class BlockletManager extends BaseBlockletManager {
|
|
|
1854
1866
|
|
|
1855
1867
|
const children = component ? await this._getChildrenForInstallation(component) : [];
|
|
1856
1868
|
|
|
1857
|
-
|
|
1869
|
+
// FIXME @linchen
|
|
1870
|
+
// 当应用本身是容器时, 下载这个容器, 因为容器可能除 blocklet.yml 额外的文件
|
|
1871
|
+
// 本身就是容器的应用, 在容器中添加额外文件可能不是合理的做法
|
|
1872
|
+
// 容器只在安装时有效, 安装后容器无法升级
|
|
1873
|
+
const containerSourceUrl =
|
|
1874
|
+
component && component.meta.group === BlockletGroup.gateway && component.meta.dist && component.bundleSource?.url;
|
|
1875
|
+
|
|
1876
|
+
if (containerSourceUrl) {
|
|
1877
|
+
meta.bundleDid = component.meta.did;
|
|
1878
|
+
meta.bundleName = component.meta.name;
|
|
1879
|
+
meta.version = component.meta.version;
|
|
1880
|
+
meta.dist = component.meta.dist;
|
|
1881
|
+
meta.logo = component.meta.logo;
|
|
1882
|
+
} else if (children[0]?.meta?.logo) {
|
|
1858
1883
|
meta.logo = children[0].meta.logo;
|
|
1859
1884
|
}
|
|
1860
1885
|
|
|
1861
1886
|
await validateBlocklet({ meta, children });
|
|
1862
1887
|
|
|
1863
1888
|
// fake install bundle
|
|
1864
|
-
|
|
1865
|
-
|
|
1866
|
-
|
|
1889
|
+
if (!containerSourceUrl) {
|
|
1890
|
+
const bundleDir = getBundleDir(this.installDir, meta);
|
|
1891
|
+
fs.mkdirSync(bundleDir, { recursive: true });
|
|
1892
|
+
updateMetaFile(path.join(bundleDir, BLOCKLET_META_FILE), meta);
|
|
1893
|
+
}
|
|
1867
1894
|
|
|
1868
1895
|
// add blocklet to db
|
|
1869
|
-
const
|
|
1896
|
+
const params = {
|
|
1870
1897
|
meta,
|
|
1871
1898
|
source: BlockletSource.custom,
|
|
1872
1899
|
children,
|
|
1873
1900
|
mode,
|
|
1874
|
-
}
|
|
1901
|
+
};
|
|
1902
|
+
|
|
1903
|
+
if (containerSourceUrl) {
|
|
1904
|
+
params.source = BlockletSource.url;
|
|
1905
|
+
params.deployedFrom = containerSourceUrl;
|
|
1906
|
+
}
|
|
1907
|
+
|
|
1908
|
+
const blocklet = await states.blocklet.addBlocklet(params);
|
|
1875
1909
|
|
|
1876
1910
|
return blocklet;
|
|
1877
1911
|
}
|
|
@@ -1909,18 +1943,14 @@ class BlockletManager extends BaseBlockletManager {
|
|
|
1909
1943
|
logger.info('blocklet installed', { source, did: meta.did });
|
|
1910
1944
|
|
|
1911
1945
|
// logo
|
|
1912
|
-
if (blocklet.children[0]?.meta?.logo) {
|
|
1946
|
+
if (blocklet.source === BlockletSource.custom && blocklet.children[0]?.meta?.logo) {
|
|
1913
1947
|
const fileName = blocklet.children[0].meta.logo;
|
|
1914
1948
|
const src = path.join(getBundleDir(this.installDir, blocklet.children[0].meta), fileName);
|
|
1915
1949
|
const dist = path.join(getBundleDir(this.installDir, blocklet.meta), fileName);
|
|
1916
1950
|
await fs.copy(src, dist);
|
|
1917
1951
|
}
|
|
1918
1952
|
|
|
1919
|
-
|
|
1920
|
-
await fs.writeFile(path.join(blocklet.env.dataDir, 'logo.svg'), createBlockiesSvg(blocklet.meta.did));
|
|
1921
|
-
} else {
|
|
1922
|
-
await fs.writeFile(path.join(blocklet.env.dataDir, 'logo.svg'), createDidLogo(blocklet.meta.did));
|
|
1923
|
-
}
|
|
1953
|
+
await updateBlockletFallbackLogo(blocklet);
|
|
1924
1954
|
|
|
1925
1955
|
// Init db
|
|
1926
1956
|
await this.teamManager.initTeam(blocklet.meta.did);
|
|
@@ -1945,12 +1975,13 @@ class BlockletManager extends BaseBlockletManager {
|
|
|
1945
1975
|
if (blocklet.controller && process.env.NODE_ENV !== 'test') {
|
|
1946
1976
|
const nodeInfo = await states.node.read();
|
|
1947
1977
|
await consumeServerlessNFT({ nftId: blocklet.controller.nftId, nodeInfo, blocklet });
|
|
1978
|
+
this.emit(BlockletEvents.nftConsumed, { blocklet, context });
|
|
1948
1979
|
}
|
|
1949
1980
|
|
|
1950
1981
|
if (createNotification) {
|
|
1951
1982
|
this._createNotification(did, {
|
|
1952
1983
|
title: 'Blocklet Installed',
|
|
1953
|
-
description: `Blocklet ${meta.
|
|
1984
|
+
description: `Blocklet ${meta.title} is installed successfully. (Source: ${
|
|
1954
1985
|
deployedFrom || fromBlockletSource(source)
|
|
1955
1986
|
})`,
|
|
1956
1987
|
action: `/blocklets/${did}/overview`,
|
|
@@ -2065,7 +2096,7 @@ class BlockletManager extends BaseBlockletManager {
|
|
|
2065
2096
|
|
|
2066
2097
|
blocklet = await this.getBlocklet(did, context);
|
|
2067
2098
|
|
|
2068
|
-
await
|
|
2099
|
+
await updateBlockletFallbackLogo(blocklet);
|
|
2069
2100
|
|
|
2070
2101
|
await this._updateDependents(did);
|
|
2071
2102
|
|
|
@@ -2394,7 +2425,7 @@ class BlockletManager extends BaseBlockletManager {
|
|
|
2394
2425
|
controller: {
|
|
2395
2426
|
$exists: true,
|
|
2396
2427
|
},
|
|
2397
|
-
|
|
2428
|
+
expiredAt: {
|
|
2398
2429
|
$exists: false,
|
|
2399
2430
|
},
|
|
2400
2431
|
},
|
|
@@ -2412,11 +2443,21 @@ class BlockletManager extends BaseBlockletManager {
|
|
|
2412
2443
|
nftId: data.controller.nftId,
|
|
2413
2444
|
});
|
|
2414
2445
|
|
|
2415
|
-
await
|
|
2416
|
-
|
|
2417
|
-
|
|
2418
|
-
|
|
2419
|
-
|
|
2446
|
+
const blocklet = await states.blocklet.getBlocklet(data.meta.did);
|
|
2447
|
+
if (blocklet) {
|
|
2448
|
+
// 预防 Blocklet 已经删除,但是 blocklet extra data 没有清理的场景
|
|
2449
|
+
await this._backupToDisk({ blocklet });
|
|
2450
|
+
logger.info('backed up the expired blocklet', {
|
|
2451
|
+
blockletDid: data.meta.did,
|
|
2452
|
+
nftId: data.controller.nftId,
|
|
2453
|
+
});
|
|
2454
|
+
|
|
2455
|
+
await this.delete({ did: data.meta.did, keepData: true, keepConfigs: true, keepLogsDir: true });
|
|
2456
|
+
logger.info('the expired blocklet already deleted', {
|
|
2457
|
+
blockletDid: data.meta.did,
|
|
2458
|
+
nftId: data.controller.nftId,
|
|
2459
|
+
});
|
|
2460
|
+
}
|
|
2420
2461
|
|
|
2421
2462
|
const expiredAt = getNftExpirationDate(assetState);
|
|
2422
2463
|
await states.blockletExtras.updateExpireInfo({ did: data.meta.did, expiredAt });
|
|
@@ -2441,7 +2482,7 @@ class BlockletManager extends BaseBlockletManager {
|
|
|
2441
2482
|
|
|
2442
2483
|
logger.info('check expired external blocklet end');
|
|
2443
2484
|
} catch (error) {
|
|
2444
|
-
logger.
|
|
2485
|
+
logger.error('check expired external blocklet failed', { error });
|
|
2445
2486
|
}
|
|
2446
2487
|
}
|
|
2447
2488
|
|
|
@@ -2454,16 +2495,19 @@ class BlockletManager extends BaseBlockletManager {
|
|
|
2454
2495
|
return;
|
|
2455
2496
|
}
|
|
2456
2497
|
|
|
2457
|
-
const tasks = blockletExtras.map(async ({
|
|
2458
|
-
|
|
2459
|
-
|
|
2498
|
+
const tasks = blockletExtras.map(async ({ appDid, meta }) => {
|
|
2499
|
+
await this._cleanBlockletData({ blocklet: { meta }, keepData: false, keepLogsDir: false, keepConfigs: false });
|
|
2500
|
+
logger.info(`clean blocklet ${meta.did} extra data`);
|
|
2501
|
+
|
|
2502
|
+
await removeBackup(this.dataDirs.data, appDid);
|
|
2503
|
+
logger.info(`removed blocklet ${meta.did} backup`);
|
|
2460
2504
|
|
|
2461
2505
|
this.emit(BlockletEvents.dataCleaned, {
|
|
2462
|
-
blocklet,
|
|
2506
|
+
blocklet: { meta },
|
|
2463
2507
|
keepRouting: false,
|
|
2464
2508
|
});
|
|
2465
2509
|
|
|
2466
|
-
logger.info(`cleaned expired blocklet blocklet ${did} data`);
|
|
2510
|
+
logger.info(`cleaned expired blocklet blocklet ${meta.did} data`);
|
|
2467
2511
|
});
|
|
2468
2512
|
|
|
2469
2513
|
await Promise.all(tasks);
|
|
@@ -2578,16 +2622,32 @@ class BlockletManager extends BaseBlockletManager {
|
|
|
2578
2622
|
const spacesRestore = new SpacesRestore({ ...input, event: this, userDid, referrer: context.referrer });
|
|
2579
2623
|
const params = await spacesRestore.restore();
|
|
2580
2624
|
|
|
2625
|
+
const removeRestoreDir = () => {
|
|
2626
|
+
if (fs.existsSync(spacesRestore.restoreDir)) {
|
|
2627
|
+
fs.remove(spacesRestore.restoreDir).catch((err) => {
|
|
2628
|
+
logger.error('failed to remove restore dir', { error: err, dir: spacesRestore.restoreDir });
|
|
2629
|
+
});
|
|
2630
|
+
}
|
|
2631
|
+
};
|
|
2632
|
+
|
|
2581
2633
|
this.emit(BlockletEvents.restoreProgress, { appDid: input.appDid, status: RESTORE_PROGRESS_STATUS.installing });
|
|
2582
|
-
|
|
2583
|
-
|
|
2584
|
-
|
|
2585
|
-
|
|
2586
|
-
|
|
2587
|
-
|
|
2588
|
-
|
|
2589
|
-
|
|
2590
|
-
|
|
2634
|
+
|
|
2635
|
+
try {
|
|
2636
|
+
await installApplicationFromBackup({
|
|
2637
|
+
url: `file://${spacesRestore.restoreDir}`,
|
|
2638
|
+
moveDir: true,
|
|
2639
|
+
...merge(...params),
|
|
2640
|
+
manager: this,
|
|
2641
|
+
states,
|
|
2642
|
+
controller: input.controller,
|
|
2643
|
+
context: { ...context, startImmediately: true },
|
|
2644
|
+
});
|
|
2645
|
+
|
|
2646
|
+
removeRestoreDir();
|
|
2647
|
+
} catch (error) {
|
|
2648
|
+
removeRestoreDir();
|
|
2649
|
+
throw error;
|
|
2650
|
+
}
|
|
2591
2651
|
|
|
2592
2652
|
this.emit(BlockletEvents.restoreProgress, { appDid: input.appDid, status: RESTORE_PROGRESS_STATUS.completed });
|
|
2593
2653
|
}
|
|
@@ -2600,14 +2660,28 @@ class BlockletManager extends BaseBlockletManager {
|
|
|
2600
2660
|
const diskRestore = new DiskRestore({ ...input, event: this });
|
|
2601
2661
|
const params = await diskRestore.restore();
|
|
2602
2662
|
|
|
2603
|
-
|
|
2604
|
-
|
|
2605
|
-
|
|
2606
|
-
|
|
2607
|
-
|
|
2608
|
-
|
|
2609
|
-
|
|
2610
|
-
|
|
2663
|
+
const removeRestoreDir = () => {
|
|
2664
|
+
if (fs.existsSync(diskRestore.restoreDir)) {
|
|
2665
|
+
fs.remove(diskRestore.restoreDir).catch((err) => {
|
|
2666
|
+
logger.error('failed to remove restore dir', { error: err, dir: diskRestore.restoreDir });
|
|
2667
|
+
});
|
|
2668
|
+
}
|
|
2669
|
+
};
|
|
2670
|
+
|
|
2671
|
+
try {
|
|
2672
|
+
await installApplicationFromBackup({
|
|
2673
|
+
url: `file://${diskRestore.restoreDir}`,
|
|
2674
|
+
...merge(...params),
|
|
2675
|
+
manager: this,
|
|
2676
|
+
states,
|
|
2677
|
+
move: true,
|
|
2678
|
+
sync: false, // use queue to download and install application
|
|
2679
|
+
});
|
|
2680
|
+
removeRestoreDir();
|
|
2681
|
+
} catch (error) {
|
|
2682
|
+
removeRestoreDir();
|
|
2683
|
+
throw error;
|
|
2684
|
+
}
|
|
2611
2685
|
}
|
|
2612
2686
|
}
|
|
2613
2687
|
|
|
@@ -1,14 +1,7 @@
|
|
|
1
|
-
const path = require('path');
|
|
2
|
-
const fs = require('fs-extra');
|
|
3
|
-
const { isEthereumDid } = require('@arcblock/did');
|
|
4
|
-
const { createBlockiesSvg } = require('@blocklet/meta/lib/blockies');
|
|
5
|
-
|
|
6
|
-
const { toSvg: createDidLogo } =
|
|
7
|
-
process.env.NODE_ENV !== 'test' ? require('@arcblock/did-motif') : require('@arcblock/did-motif/dist/did-motif.cjs');
|
|
8
1
|
const { BlockletStatus, BLOCKLET_MODES, fromBlockletStatus, BlockletSource } = require('@blocklet/constant');
|
|
9
2
|
|
|
10
3
|
const logger = require('@abtnode/logger')('@abtnode/core:install-app-dev');
|
|
11
|
-
const { ensureMeta } = require('../../../util/blocklet');
|
|
4
|
+
const { ensureMeta, updateBlockletFallbackLogo } = require('../../../util/blocklet');
|
|
12
5
|
|
|
13
6
|
/**
|
|
14
7
|
*
|
|
@@ -88,11 +81,7 @@ const installApplicationFromDev = async ({ folder, meta, states, manager } = {})
|
|
|
88
81
|
|
|
89
82
|
blocklet = await manager.getBlocklet(did);
|
|
90
83
|
|
|
91
|
-
|
|
92
|
-
await fs.writeFile(path.join(blocklet.env.dataDir, 'logo.svg'), createBlockiesSvg(blocklet.meta.did));
|
|
93
|
-
} else {
|
|
94
|
-
await fs.writeFile(path.join(blocklet.env.dataDir, 'logo.svg'), createDidLogo(blocklet.meta.did));
|
|
95
|
-
}
|
|
84
|
+
await updateBlockletFallbackLogo(blocklet);
|
|
96
85
|
|
|
97
86
|
return blocklet;
|
|
98
87
|
};
|
package/lib/event.js
CHANGED
package/lib/states/user.js
CHANGED
|
@@ -193,7 +193,7 @@ class User extends BaseState {
|
|
|
193
193
|
|
|
194
194
|
// 根据 derivedDid 查询 user 信息(wallet 账户绑定 oauth 账户后,会有该字段)
|
|
195
195
|
if (derivedDid) {
|
|
196
|
-
queryParam['derivedAccount.did'] = derivedDid;
|
|
196
|
+
queryParam['extraConfigs.derivedAccount.did'] = derivedDid;
|
|
197
197
|
}
|
|
198
198
|
|
|
199
199
|
const sortParam = pickBy(sort, (x) => !isNullOrUndefined(x));
|
|
@@ -232,6 +232,27 @@ class User extends BaseState {
|
|
|
232
232
|
return this.find(queryParam);
|
|
233
233
|
}
|
|
234
234
|
|
|
235
|
+
/**
|
|
236
|
+
* get user list by sourceId list
|
|
237
|
+
* @param {string[]} sourceIds user sourceId list
|
|
238
|
+
* @returns {BlockletUser[]}
|
|
239
|
+
*/
|
|
240
|
+
async getUsersBySourceIds({ sourceIds, query } = {}) {
|
|
241
|
+
const { approved } = query || {};
|
|
242
|
+
const sourceIdList = sourceIds || [];
|
|
243
|
+
|
|
244
|
+
const queryParam = {
|
|
245
|
+
'extraConfigs.sourceId': { $in: sourceIdList },
|
|
246
|
+
};
|
|
247
|
+
|
|
248
|
+
if (!isNullOrUndefined(approved)) {
|
|
249
|
+
queryParam.approved = !!approved;
|
|
250
|
+
}
|
|
251
|
+
|
|
252
|
+
// get data
|
|
253
|
+
return this.find(queryParam);
|
|
254
|
+
}
|
|
255
|
+
|
|
235
256
|
/**
|
|
236
257
|
* get user by did
|
|
237
258
|
* @param {string} did user's did
|
package/lib/util/blocklet.js
CHANGED
|
@@ -5,6 +5,7 @@ const path = require('path');
|
|
|
5
5
|
const joinURL = require('url-join');
|
|
6
6
|
const shelljs = require('shelljs');
|
|
7
7
|
const os = require('os');
|
|
8
|
+
const pRetry = require('p-retry');
|
|
8
9
|
const tar = require('tar');
|
|
9
10
|
const get = require('lodash/get');
|
|
10
11
|
const isEmpty = require('lodash/isEmpty');
|
|
@@ -21,7 +22,7 @@ const { stableStringify } = require('@arcblock/vc');
|
|
|
21
22
|
const { fromSecretKey, WalletType } = require('@ocap/wallet');
|
|
22
23
|
const { toHex, toBase58, isHex, toDid } = require('@ocap/util');
|
|
23
24
|
const { types } = require('@ocap/mcrypto');
|
|
24
|
-
const { isValid: isValidDid } = require('@arcblock/did');
|
|
25
|
+
const { isValid: isValidDid, isEthereumDid } = require('@arcblock/did');
|
|
25
26
|
const logger = require('@abtnode/logger')('@abtnode/core:util:blocklet');
|
|
26
27
|
const pm2 = require('@abtnode/util/lib/async-pm2');
|
|
27
28
|
const sleep = require('@abtnode/util/lib/sleep');
|
|
@@ -39,6 +40,9 @@ const {
|
|
|
39
40
|
APP_STRUCT_VERSION,
|
|
40
41
|
} = require('@abtnode/constant');
|
|
41
42
|
const formatBackSlash = require('@abtnode/util/lib/format-back-slash');
|
|
43
|
+
const { toSvg: createDidLogo } =
|
|
44
|
+
process.env.NODE_ENV !== 'test' ? require('@arcblock/did-motif') : require('@arcblock/did-motif/dist/did-motif.cjs');
|
|
45
|
+
const { createBlockiesSvg } = require('@blocklet/meta/lib/blockies');
|
|
42
46
|
|
|
43
47
|
const SCRIPT_ENGINES_WHITE_LIST = ['npm', 'npx', 'pnpm', 'yarn'];
|
|
44
48
|
|
|
@@ -456,7 +460,10 @@ const getRuntimeEnvironments = (blocklet, nodeEnvironments, ancestors) => {
|
|
|
456
460
|
};
|
|
457
461
|
|
|
458
462
|
const isUsefulError = (err) =>
|
|
459
|
-
err &&
|
|
463
|
+
err &&
|
|
464
|
+
err.message !== 'process or namespace not found' &&
|
|
465
|
+
!/id unknown/.test(err.message) &&
|
|
466
|
+
!/^Process \d+ not found$/.test(err.message);
|
|
460
467
|
|
|
461
468
|
const getHealthyCheckTimeout = (blocklet, { checkHealthImmediately } = {}) => {
|
|
462
469
|
let minConsecutiveTime = 5000;
|
|
@@ -607,6 +614,10 @@ const stopBlockletProcess = async (blocklet, { preStop = noop, skippedProcessIds
|
|
|
607
614
|
await forEachBlocklet(
|
|
608
615
|
blocklet,
|
|
609
616
|
async (b, { ancestors }) => {
|
|
617
|
+
if (b.meta?.group === BlockletGroup.gateway) {
|
|
618
|
+
return;
|
|
619
|
+
}
|
|
620
|
+
|
|
610
621
|
if (skippedProcessIds.includes(b.env.processId)) {
|
|
611
622
|
logger.info(`skip stop process ${b.env.processId}`);
|
|
612
623
|
return;
|
|
@@ -802,9 +813,7 @@ const parseComponents = async (component, context = {}) => {
|
|
|
802
813
|
try {
|
|
803
814
|
rawMeta = await getBlockletMetaFromUrls(urls, { logger });
|
|
804
815
|
} catch (error) {
|
|
805
|
-
throw new Error(
|
|
806
|
-
`Failed get component meta. Component: ${rawMeta.title || rawMeta.did}, reason: ${error.message}`
|
|
807
|
-
);
|
|
816
|
+
throw new Error(`Failed get component meta. Component: ${urls.join(', ')}, reason: ${error.message}`);
|
|
808
817
|
}
|
|
809
818
|
|
|
810
819
|
if (rawMeta.group === BlockletGroup.gateway) {
|
|
@@ -1510,13 +1519,28 @@ const consumeServerlessNFT = async ({ nftId, nodeInfo, blocklet }) => {
|
|
|
1510
1519
|
const body = { nftId, appURL };
|
|
1511
1520
|
|
|
1512
1521
|
const { launcherUrl } = state.data.value;
|
|
1513
|
-
|
|
1514
|
-
|
|
1515
|
-
|
|
1522
|
+
|
|
1523
|
+
const func = async () => {
|
|
1524
|
+
const { data } = await axios.post(joinURL(launcherUrl, '/api/serverless/consume'), body, {
|
|
1525
|
+
headers: {
|
|
1526
|
+
'x-sig': toBase58(wallet.sign(stableStringify(body))),
|
|
1527
|
+
},
|
|
1528
|
+
});
|
|
1529
|
+
|
|
1530
|
+
return data;
|
|
1531
|
+
};
|
|
1532
|
+
|
|
1533
|
+
const delay = 10 * 1000;
|
|
1534
|
+
const result = await pRetry(func, {
|
|
1535
|
+
retries: 3,
|
|
1536
|
+
minTimeout: delay,
|
|
1537
|
+
maxTimeout: delay,
|
|
1538
|
+
onFailedAttempt: (error) => {
|
|
1539
|
+
logger.error(`attempt consume nft ${nftId} failed`, { error });
|
|
1516
1540
|
},
|
|
1517
1541
|
});
|
|
1518
1542
|
|
|
1519
|
-
logger.error('consume serverless nft success', { nftId, hash:
|
|
1543
|
+
logger.error('consume serverless nft success', { nftId, hash: result.hash });
|
|
1520
1544
|
} catch (error) {
|
|
1521
1545
|
logger.error('consume serverless nft failed', { nftId, error });
|
|
1522
1546
|
|
|
@@ -1863,7 +1887,16 @@ const getFixedBundleSource = (component) => {
|
|
|
1863
1887
|
return null;
|
|
1864
1888
|
};
|
|
1865
1889
|
|
|
1890
|
+
const updateBlockletFallbackLogo = async (blocklet) => {
|
|
1891
|
+
if (isEthereumDid(blocklet.meta.did)) {
|
|
1892
|
+
await fs.writeFile(path.join(blocklet.env.dataDir, 'logo.svg'), createBlockiesSvg(blocklet.meta.did));
|
|
1893
|
+
} else {
|
|
1894
|
+
await fs.writeFile(path.join(blocklet.env.dataDir, 'logo.svg'), createDidLogo(blocklet.meta.did));
|
|
1895
|
+
}
|
|
1896
|
+
};
|
|
1897
|
+
|
|
1866
1898
|
module.exports = {
|
|
1899
|
+
updateBlockletFallbackLogo,
|
|
1867
1900
|
consumeServerlessNFT,
|
|
1868
1901
|
forEachBlocklet,
|
|
1869
1902
|
getBlockletMetaFromUrl: (url) => getBlockletMetaFromUrl(url, { logger }),
|
package/package.json
CHANGED
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
"publishConfig": {
|
|
4
4
|
"access": "public"
|
|
5
5
|
},
|
|
6
|
-
"version": "1.16.0-beta-
|
|
6
|
+
"version": "1.16.0-beta-b741bcb3",
|
|
7
7
|
"description": "",
|
|
8
8
|
"main": "lib/index.js",
|
|
9
9
|
"files": [
|
|
@@ -19,18 +19,18 @@
|
|
|
19
19
|
"author": "wangshijun <wangshijun2010@gmail.com> (http://github.com/wangshijun)",
|
|
20
20
|
"license": "MIT",
|
|
21
21
|
"dependencies": {
|
|
22
|
-
"@abtnode/auth": "1.16.0-beta-
|
|
23
|
-
"@abtnode/certificate-manager": "1.16.0-beta-
|
|
24
|
-
"@abtnode/constant": "1.16.0-beta-
|
|
25
|
-
"@abtnode/cron": "1.16.0-beta-
|
|
26
|
-
"@abtnode/db": "1.16.0-beta-
|
|
27
|
-
"@abtnode/logger": "1.16.0-beta-
|
|
28
|
-
"@abtnode/queue": "1.16.0-beta-
|
|
29
|
-
"@abtnode/rbac": "1.16.0-beta-
|
|
30
|
-
"@abtnode/router-provider": "1.16.0-beta-
|
|
31
|
-
"@abtnode/static-server": "1.16.0-beta-
|
|
32
|
-
"@abtnode/timemachine": "1.16.0-beta-
|
|
33
|
-
"@abtnode/util": "1.16.0-beta-
|
|
22
|
+
"@abtnode/auth": "1.16.0-beta-b741bcb3",
|
|
23
|
+
"@abtnode/certificate-manager": "1.16.0-beta-b741bcb3",
|
|
24
|
+
"@abtnode/constant": "1.16.0-beta-b741bcb3",
|
|
25
|
+
"@abtnode/cron": "1.16.0-beta-b741bcb3",
|
|
26
|
+
"@abtnode/db": "1.16.0-beta-b741bcb3",
|
|
27
|
+
"@abtnode/logger": "1.16.0-beta-b741bcb3",
|
|
28
|
+
"@abtnode/queue": "1.16.0-beta-b741bcb3",
|
|
29
|
+
"@abtnode/rbac": "1.16.0-beta-b741bcb3",
|
|
30
|
+
"@abtnode/router-provider": "1.16.0-beta-b741bcb3",
|
|
31
|
+
"@abtnode/static-server": "1.16.0-beta-b741bcb3",
|
|
32
|
+
"@abtnode/timemachine": "1.16.0-beta-b741bcb3",
|
|
33
|
+
"@abtnode/util": "1.16.0-beta-b741bcb3",
|
|
34
34
|
"@arcblock/did": "1.18.64",
|
|
35
35
|
"@arcblock/did-motif": "^1.1.10",
|
|
36
36
|
"@arcblock/did-util": "1.18.64",
|
|
@@ -38,9 +38,9 @@
|
|
|
38
38
|
"@arcblock/jwt": "^1.18.64",
|
|
39
39
|
"@arcblock/pm2-events": "^0.0.5",
|
|
40
40
|
"@arcblock/vc": "1.18.64",
|
|
41
|
-
"@blocklet/constant": "1.16.0-beta-
|
|
42
|
-
"@blocklet/meta": "1.16.0-beta-
|
|
43
|
-
"@blocklet/sdk": "1.16.0-beta-
|
|
41
|
+
"@blocklet/constant": "1.16.0-beta-b741bcb3",
|
|
42
|
+
"@blocklet/meta": "1.16.0-beta-b741bcb3",
|
|
43
|
+
"@blocklet/sdk": "1.16.0-beta-b741bcb3",
|
|
44
44
|
"@did-space/client": "^0.2.45",
|
|
45
45
|
"@fidm/x509": "^1.2.1",
|
|
46
46
|
"@ocap/client": "1.18.64",
|
|
@@ -91,5 +91,5 @@
|
|
|
91
91
|
"express": "^4.18.2",
|
|
92
92
|
"jest": "^27.5.1"
|
|
93
93
|
},
|
|
94
|
-
"gitHead": "
|
|
94
|
+
"gitHead": "f41666daf2c499566ff2f8e76a2de4fa6e1122ba"
|
|
95
95
|
}
|