@abtnode/core 1.16.13 → 1.16.14-beta-0c29907f
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 +5 -3
- package/lib/blocklet/manager/disk.js +301 -126
- package/lib/blocklet/manager/helper/install-application-from-backup.js +7 -6
- package/lib/blocklet/manager/helper/install-application-from-general.js +5 -5
- package/lib/blocklet/manager/helper/install-component-from-upload.js +3 -1
- package/lib/blocklet/manager/helper/install-component-from-url.js +22 -5
- package/lib/blocklet/manager/helper/upgrade-components.js +21 -6
- package/lib/event.js +32 -32
- package/lib/index.js +4 -0
- package/lib/states/audit-log.js +64 -70
- package/lib/states/blocklet.js +1 -0
- package/lib/states/notification.js +2 -2
- package/lib/util/blocklet.js +11 -0
- package/lib/util/get-accessible-external-node-ip.js +2 -2
- package/lib/util/get-domain-for-blocklet.js +2 -2
- package/lib/util/launcher.js +11 -5
- package/lib/util/store.js +7 -7
- package/lib/webhook/index.js +25 -14
- package/package.json +32 -32
|
@@ -6,6 +6,7 @@ const { forEachBlockletSync, getBlockletAppIdList } = require('@blocklet/meta/li
|
|
|
6
6
|
const getBlockletInfo = require('@blocklet/meta/lib/info');
|
|
7
7
|
|
|
8
8
|
const { BLOCKLET_CONFIGURABLE_KEY, BlockletEvents, BlockletStatus } = require('@blocklet/constant');
|
|
9
|
+
const { INSTALL_ACTIONS } = require('@abtnode/constant');
|
|
9
10
|
|
|
10
11
|
const logger = require('@abtnode/logger')('@abtnode/core:install-app-backup');
|
|
11
12
|
|
|
@@ -195,7 +196,7 @@ const installApplicationFromBackup = async ({
|
|
|
195
196
|
} catch (error) {
|
|
196
197
|
logger.error('installFromBackup failed', { did, error });
|
|
197
198
|
|
|
198
|
-
await manager._rollback(
|
|
199
|
+
await manager._rollback(INSTALL_ACTIONS.INSTALL, did);
|
|
199
200
|
|
|
200
201
|
throw error;
|
|
201
202
|
}
|
|
@@ -213,7 +214,7 @@ const installApplicationFromBackup = async ({
|
|
|
213
214
|
} catch (error) {
|
|
214
215
|
logger.error('download blocklet failed', { did, error });
|
|
215
216
|
|
|
216
|
-
await manager._rollback(
|
|
217
|
+
await manager._rollback(INSTALL_ACTIONS.INSTALL, did);
|
|
217
218
|
|
|
218
219
|
throw error;
|
|
219
220
|
}
|
|
@@ -233,11 +234,11 @@ const installApplicationFromBackup = async ({
|
|
|
233
234
|
blocklet: { ...blocklet1 },
|
|
234
235
|
skipCheckIntegrity: true,
|
|
235
236
|
context,
|
|
236
|
-
postAction:
|
|
237
|
+
postAction: INSTALL_ACTIONS.INSTALL,
|
|
237
238
|
};
|
|
238
239
|
|
|
239
240
|
// backup rollback data
|
|
240
|
-
await manager._rollbackCache.backup({ did, action:
|
|
241
|
+
await manager._rollbackCache.backup({ did, action: INSTALL_ACTIONS.INSTALL });
|
|
241
242
|
|
|
242
243
|
const ticket = manager.installQueue.push(
|
|
243
244
|
{
|
|
@@ -251,7 +252,7 @@ const installApplicationFromBackup = async ({
|
|
|
251
252
|
ticket.on('failed', async (err) => {
|
|
252
253
|
logger.error('failed to install blocklet', { did, error: err });
|
|
253
254
|
try {
|
|
254
|
-
await manager._rollback(
|
|
255
|
+
await manager._rollback(INSTALL_ACTIONS.INSTALL, did, {});
|
|
255
256
|
} catch (e) {
|
|
256
257
|
logger.error('failed to remove blocklet on install error', { did, error: e });
|
|
257
258
|
}
|
|
@@ -272,7 +273,7 @@ const installApplicationFromBackup = async ({
|
|
|
272
273
|
logger.error('failed to install blocklet', { did, error: err });
|
|
273
274
|
|
|
274
275
|
try {
|
|
275
|
-
await manager._rollback(
|
|
276
|
+
await manager._rollback(INSTALL_ACTIONS.INSTALL, did, {});
|
|
276
277
|
} catch (e) {
|
|
277
278
|
logger.error('failed to remove blocklet on install error', { did, error: e });
|
|
278
279
|
}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
const joi = require('joi');
|
|
2
2
|
|
|
3
|
-
const { BLOCKLET_INSTALL_TYPE, NODE_MODES } = require('@abtnode/constant');
|
|
3
|
+
const { BLOCKLET_INSTALL_TYPE, NODE_MODES, INSTALL_ACTIONS } = require('@abtnode/constant');
|
|
4
4
|
const { BlockletStatus, BlockletEvents, BLOCKLET_CONFIGURABLE_KEY } = require('@blocklet/constant');
|
|
5
5
|
|
|
6
6
|
const logger = require('@abtnode/logger')('@abtnode/core:install-app-general');
|
|
@@ -122,7 +122,7 @@ const installApplicationFromGeneral = async ({
|
|
|
122
122
|
logger.error('failed to create blocklet extras', { did, componentDid, error: err });
|
|
123
123
|
|
|
124
124
|
try {
|
|
125
|
-
await manager._rollback(
|
|
125
|
+
await manager._rollback(INSTALL_ACTIONS.INSTALL, did, {});
|
|
126
126
|
} catch (e) {
|
|
127
127
|
logger.error('failed to remove blocklet on create extras error', { did, componentDid, error: e });
|
|
128
128
|
}
|
|
@@ -146,7 +146,7 @@ const installApplicationFromGeneral = async ({
|
|
|
146
146
|
const blocklet1 = await states.blocklet.setBlockletStatus(did, BlockletStatus.waiting);
|
|
147
147
|
manager.emit(BlockletEvents.added, blocklet1);
|
|
148
148
|
|
|
149
|
-
const action =
|
|
149
|
+
const action = INSTALL_ACTIONS.INSTALL;
|
|
150
150
|
const downloadParams = {
|
|
151
151
|
blocklet: { ...blocklet1 },
|
|
152
152
|
context,
|
|
@@ -175,7 +175,7 @@ const installApplicationFromGeneral = async ({
|
|
|
175
175
|
const componentDid = component?.meta?.did;
|
|
176
176
|
logger.error('failed to install blocklet', { did, componentDid, error: err });
|
|
177
177
|
try {
|
|
178
|
-
await manager._rollback(
|
|
178
|
+
await manager._rollback(INSTALL_ACTIONS.INSTALL, did, {});
|
|
179
179
|
} catch (e) {
|
|
180
180
|
logger.error('failed to remove blocklet on install error', { did, componentDid, error: e });
|
|
181
181
|
}
|
|
@@ -198,7 +198,7 @@ const installApplicationFromGeneral = async ({
|
|
|
198
198
|
logger.error('failed to install blocklet', { did, componentDid, error: err });
|
|
199
199
|
|
|
200
200
|
try {
|
|
201
|
-
await manager._rollback(
|
|
201
|
+
await manager._rollback(INSTALL_ACTIONS.INSTALL, did, {});
|
|
202
202
|
} catch (e) {
|
|
203
203
|
logger.error('failed to remove blocklet on install error', { did, componentDid, error: e });
|
|
204
204
|
}
|
|
@@ -5,6 +5,7 @@ const getComponentProcessId = require('@blocklet/meta/lib/get-component-process-
|
|
|
5
5
|
const { isInProgress } = require('@blocklet/meta/lib/util');
|
|
6
6
|
|
|
7
7
|
const { BlockletSource, BlockletGroup, fromBlockletStatus } = require('@blocklet/constant');
|
|
8
|
+
const { INSTALL_ACTIONS } = require('@abtnode/constant');
|
|
8
9
|
const {
|
|
9
10
|
parseComponents,
|
|
10
11
|
filterDuplicateComponents,
|
|
@@ -96,6 +97,8 @@ const installComponentFromUpload = async ({
|
|
|
96
97
|
newBlocklet.children.push(newChild);
|
|
97
98
|
}
|
|
98
99
|
|
|
100
|
+
const action = index >= 0 ? INSTALL_ACTIONS.UPGRADE_COMPONENT : INSTALL_ACTIONS.INSTALL_COMPONENT;
|
|
101
|
+
|
|
99
102
|
const { dynamicComponents } = await parseComponents(newChild);
|
|
100
103
|
const newChildren = filterDuplicateComponents(dynamicComponents, newBlocklet.children);
|
|
101
104
|
|
|
@@ -104,7 +107,6 @@ const installComponentFromUpload = async ({
|
|
|
104
107
|
checkVersionCompatibility(newBlocklet.children);
|
|
105
108
|
|
|
106
109
|
// backup rollback data
|
|
107
|
-
const action = 'upgrade';
|
|
108
110
|
await manager._rollbackCache.backup({ did: newBlocklet.meta.did, action, oldBlocklet });
|
|
109
111
|
|
|
110
112
|
const componentDids = [newChild.meta.did, ...newChildren.map((x) => x.meta.did)];
|
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
const capitalize = require('lodash/capitalize');
|
|
2
1
|
const { sign } = require('@arcblock/jwt');
|
|
3
2
|
|
|
4
3
|
const logger = require('@abtnode/logger')('@abtnode/core:install-component-url');
|
|
@@ -8,6 +7,7 @@ const { titleSchema } = require('@blocklet/meta/lib/schema');
|
|
|
8
7
|
const hasReservedKey = require('@blocklet/meta/lib/has-reserved-key');
|
|
9
8
|
|
|
10
9
|
const { BlockletStatus, BlockletEvents, BlockletGroup } = require('@blocklet/constant');
|
|
10
|
+
const { INSTALL_ACTIONS } = require('@abtnode/constant');
|
|
11
11
|
const {
|
|
12
12
|
getBlockletMetaFromUrl,
|
|
13
13
|
parseComponents,
|
|
@@ -16,6 +16,7 @@ const {
|
|
|
16
16
|
checkStructVersion,
|
|
17
17
|
checkVersionCompatibility,
|
|
18
18
|
validateBlocklet,
|
|
19
|
+
getComponentNamesWithVersion,
|
|
19
20
|
} = require('../../../util/blocklet');
|
|
20
21
|
const StoreUtil = require('../../../util/store');
|
|
21
22
|
const { formatName } = require('../../../util/get-domain-for-blocklet');
|
|
@@ -105,7 +106,7 @@ const installComponentFromUrl = async ({
|
|
|
105
106
|
checkVersionCompatibility(blocklet.children);
|
|
106
107
|
|
|
107
108
|
const oldBlocklet = await manager._getBlockletForInstallation(rootDid);
|
|
108
|
-
const action =
|
|
109
|
+
const action = index > 0 ? INSTALL_ACTIONS.UPGRADE_COMPONENT : INSTALL_ACTIONS.INSTALL_COMPONENT;
|
|
109
110
|
try {
|
|
110
111
|
// add component to db
|
|
111
112
|
await states.blocklet.addChildren(rootDid, newChildren);
|
|
@@ -141,6 +142,7 @@ const installComponentFromUrl = async ({
|
|
|
141
142
|
oldBlocklet: { ...oldBlocklet },
|
|
142
143
|
blocklet: { ...newBlocklet },
|
|
143
144
|
componentDids,
|
|
145
|
+
addedComponentDids: componentDids,
|
|
144
146
|
context,
|
|
145
147
|
postAction: action,
|
|
146
148
|
};
|
|
@@ -148,6 +150,8 @@ const installComponentFromUrl = async ({
|
|
|
148
150
|
// backup rollback data
|
|
149
151
|
await manager._rollbackCache.backup({ did: rootDid, action, oldBlocklet });
|
|
150
152
|
|
|
153
|
+
logger.info('install component from url', { rootDid, url, mountPoint, sync, componentDids });
|
|
154
|
+
|
|
151
155
|
if (sync) {
|
|
152
156
|
await manager._downloadAndInstall({ ...downloadParams, throwOnError: true });
|
|
153
157
|
return states.blocklet.getBlocklet(rootDid);
|
|
@@ -167,10 +171,23 @@ const installComponentFromUrl = async ({
|
|
|
167
171
|
ticket.on('failed', async (err) => {
|
|
168
172
|
logger.error('queue failed', { entity: 'blocklet', action, did: rootDid, error: err });
|
|
169
173
|
await manager._rollback(action, rootDid, oldBlocklet);
|
|
170
|
-
|
|
174
|
+
|
|
175
|
+
const notificationEvent =
|
|
176
|
+
action === INSTALL_ACTIONS.INSTALL_COMPONENT
|
|
177
|
+
? BlockletEvents.componentInstallFailed
|
|
178
|
+
: BlockletEvents.componentUpgradeFailed;
|
|
179
|
+
const actionName = action === INSTALL_ACTIONS.INSTALL_COMPONENT ? 'install' : 'upgrade';
|
|
180
|
+
|
|
181
|
+
manager.emit(notificationEvent, {
|
|
182
|
+
blocklet: { ...newBlocklet, componentDids, error: { message: err.message } },
|
|
183
|
+
context: { ...context, createAuditLog: false },
|
|
184
|
+
});
|
|
185
|
+
|
|
171
186
|
manager._createNotification(rootDid, {
|
|
172
|
-
title:
|
|
173
|
-
description:
|
|
187
|
+
title: '',
|
|
188
|
+
description: `${getComponentNamesWithVersion(newBlocklet, componentDids)} ${actionName} failed for ${
|
|
189
|
+
newBlocklet.meta.title
|
|
190
|
+
}: ${err.message || 'queue exception'}.`,
|
|
174
191
|
entityType: 'blocklet',
|
|
175
192
|
entityId: rootDid,
|
|
176
193
|
severity: 'error',
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
/* eslint-disable no-await-in-loop */
|
|
2
2
|
const cloneDeep = require('lodash/cloneDeep');
|
|
3
|
-
const capitalize = require('lodash/capitalize');
|
|
4
3
|
|
|
5
4
|
const logger = require('@abtnode/logger')('@abtnode/core:upgrade-component');
|
|
6
5
|
|
|
7
6
|
const { BlockletStatus, BlockletEvents } = require('@blocklet/constant');
|
|
7
|
+
const { INSTALL_ACTIONS } = require('@abtnode/constant');
|
|
8
8
|
const {
|
|
9
9
|
getUpdateMetaList,
|
|
10
10
|
parseComponents,
|
|
@@ -14,6 +14,7 @@ const {
|
|
|
14
14
|
checkVersionCompatibility,
|
|
15
15
|
validateBlocklet,
|
|
16
16
|
getFixedBundleSource,
|
|
17
|
+
getComponentNamesWithVersion,
|
|
17
18
|
} = require('../../../util/blocklet');
|
|
18
19
|
|
|
19
20
|
const check = async ({ did, states }) => {
|
|
@@ -83,6 +84,12 @@ const upgrade = async ({ updateId, componentDids, context, states, manager }) =>
|
|
|
83
84
|
const oldBlocklet = await manager._getBlockletForInstallation(did);
|
|
84
85
|
checkStructVersion(oldBlocklet);
|
|
85
86
|
|
|
87
|
+
logger.info('upgrade blocklet components', {
|
|
88
|
+
componentDids,
|
|
89
|
+
updateId,
|
|
90
|
+
did,
|
|
91
|
+
});
|
|
92
|
+
|
|
86
93
|
// parse children
|
|
87
94
|
let dynamicComponents = [];
|
|
88
95
|
const children = cloneDeep(oldBlocklet.children).map((oldComponent) => {
|
|
@@ -102,7 +109,7 @@ const upgrade = async ({ updateId, componentDids, context, states, manager }) =>
|
|
|
102
109
|
|
|
103
110
|
checkVersionCompatibility(children);
|
|
104
111
|
|
|
105
|
-
logger.info('
|
|
112
|
+
logger.info('blocklet components to upgrade', {
|
|
106
113
|
did,
|
|
107
114
|
children: children.map((x) => ({ name: x.meta.name, version: x.meta.version })),
|
|
108
115
|
});
|
|
@@ -115,7 +122,7 @@ const upgrade = async ({ updateId, componentDids, context, states, manager }) =>
|
|
|
115
122
|
|
|
116
123
|
manager.emit(BlockletEvents.statusChange, newBlocklet);
|
|
117
124
|
|
|
118
|
-
const action =
|
|
125
|
+
const action = INSTALL_ACTIONS.UPGRADE_COMPONENT;
|
|
119
126
|
|
|
120
127
|
// backup rollback data
|
|
121
128
|
await manager._rollbackCache.backup({ did, action, oldBlocklet });
|
|
@@ -138,15 +145,23 @@ const upgrade = async ({ updateId, componentDids, context, states, manager }) =>
|
|
|
138
145
|
ticket.on('failed', async (err) => {
|
|
139
146
|
logger.error('queue failed', { entity: 'blocklet', action, did, error: err });
|
|
140
147
|
await manager._rollback(action, did, oldBlocklet);
|
|
141
|
-
|
|
148
|
+
|
|
149
|
+
manager.emit(BlockletEvents.componentUpgradeFailed, {
|
|
150
|
+
blocklet: { ...oldBlocklet, componentDids, error: { message: err.message } },
|
|
151
|
+
context: { ...context, createAuditLog: false },
|
|
152
|
+
});
|
|
153
|
+
|
|
142
154
|
manager._createNotification(did, {
|
|
143
|
-
title:
|
|
144
|
-
description:
|
|
155
|
+
title: '',
|
|
156
|
+
description: `${getComponentNamesWithVersion(oldBlocklet, componentDids)} upgrade failed for ${
|
|
157
|
+
oldBlocklet.meta.title
|
|
158
|
+
}: ${err.message || 'queue exception'}.`,
|
|
145
159
|
entityType: 'blocklet',
|
|
146
160
|
entityId: did,
|
|
147
161
|
severity: 'error',
|
|
148
162
|
});
|
|
149
163
|
});
|
|
164
|
+
|
|
150
165
|
return newBlocklet;
|
|
151
166
|
};
|
|
152
167
|
|
package/lib/event.js
CHANGED
|
@@ -233,10 +233,28 @@ module.exports = ({
|
|
|
233
233
|
} catch (error) {
|
|
234
234
|
logger.error('Failed to createAuditLog for installBlocklet', { error });
|
|
235
235
|
}
|
|
236
|
-
} else if ([BlockletEvents.upgraded
|
|
236
|
+
} else if ([BlockletEvents.upgraded].includes(eventName)) {
|
|
237
237
|
await handleBlockletUpgrade(eventName, payload);
|
|
238
|
-
|
|
238
|
+
} else if ([BlockletEvents.removed, BlockletEvents.dataCleaned].includes(eventName)) {
|
|
239
|
+
await handleBlockletRemove(eventName, payload);
|
|
240
|
+
} else if ([BlockletEvents.started].includes(eventName)) {
|
|
241
|
+
const { publicToStore } = blocklet.settings || {};
|
|
242
|
+
if (publicToStore) {
|
|
243
|
+
handleInstanceInStore(blocklet, { publicToStore }).catch((error) => {
|
|
244
|
+
logger.error('handleInstanceInStore failed', { message: error.message });
|
|
245
|
+
});
|
|
246
|
+
}
|
|
247
|
+
} else if (
|
|
248
|
+
[
|
|
249
|
+
BlockletEvents.componentInstalled,
|
|
250
|
+
BlockletEvents.componentInstallFailed,
|
|
251
|
+
BlockletEvents.componentUpgradeFailed,
|
|
252
|
+
BlockletEvents.componentUpgraded,
|
|
253
|
+
].includes(eventName)
|
|
254
|
+
) {
|
|
239
255
|
if (payload?.context?.createAuditLog !== false) {
|
|
256
|
+
const resultStatus = [BlockletEvents.componentInstallFailed, BlockletEvents.componentUpgradeFailed].includes(eventName) ? 'failed' : 'success'; // prettier-ignore
|
|
257
|
+
const action = [BlockletEvents.componentInstalled, BlockletEvents.componentInstallFailed].includes(eventName) ? 'installed' : 'upgraded'; // prettier-ignore
|
|
240
258
|
try {
|
|
241
259
|
await node.createAuditLog({
|
|
242
260
|
action: 'upgradeBlocklet',
|
|
@@ -244,37 +262,16 @@ module.exports = ({
|
|
|
244
262
|
did: blocklet.meta.did,
|
|
245
263
|
},
|
|
246
264
|
context: payload.context || {},
|
|
247
|
-
result:
|
|
265
|
+
result: {
|
|
266
|
+
...blocklet,
|
|
267
|
+
resultStatus,
|
|
268
|
+
action,
|
|
269
|
+
},
|
|
248
270
|
});
|
|
249
271
|
} catch (error) {
|
|
250
|
-
logger.error('Failed to createAuditLog for upgradeBlocklet', { error });
|
|
272
|
+
logger.error('Failed to createAuditLog for upgradeBlocklet failed', { error });
|
|
251
273
|
}
|
|
252
274
|
}
|
|
253
|
-
} else if ([BlockletEvents.removed, BlockletEvents.dataCleaned].includes(eventName)) {
|
|
254
|
-
await handleBlockletRemove(eventName, payload);
|
|
255
|
-
} else if ([BlockletEvents.started].includes(eventName)) {
|
|
256
|
-
const { publicToStore } = blocklet.settings || {};
|
|
257
|
-
if (publicToStore) {
|
|
258
|
-
handleInstanceInStore(blocklet, { publicToStore }).catch((error) => {
|
|
259
|
-
logger.error('handleInstanceInStore failed', { message: error.message });
|
|
260
|
-
});
|
|
261
|
-
}
|
|
262
|
-
} else if ([BlockletEvents.upgradeFailed, BlockletEvents.downgradeFailed].includes(eventName)) {
|
|
263
|
-
try {
|
|
264
|
-
await node.createAuditLog({
|
|
265
|
-
action: 'upgradeBlocklet',
|
|
266
|
-
args: {
|
|
267
|
-
did: blocklet.meta.did,
|
|
268
|
-
},
|
|
269
|
-
context: payload.context || {},
|
|
270
|
-
result: {
|
|
271
|
-
...blocklet,
|
|
272
|
-
resultStatus: 'failed',
|
|
273
|
-
},
|
|
274
|
-
});
|
|
275
|
-
} catch (error) {
|
|
276
|
-
logger.error('Failed to createAuditLog for upgradeBlocklet failed', { error });
|
|
277
|
-
}
|
|
278
275
|
} else if (BlockletEvents.appDidChanged === eventName) {
|
|
279
276
|
const hash = await takeRoutingSnapshot(
|
|
280
277
|
{ message: `${routingSnapshotPrefix(blocklet)}Update blocklet ${blocklet.meta.name} app did`, dryRun: false },
|
|
@@ -361,9 +358,6 @@ module.exports = ({
|
|
|
361
358
|
BlockletEvents.installed,
|
|
362
359
|
BlockletEvents.installFailed,
|
|
363
360
|
BlockletEvents.upgraded,
|
|
364
|
-
BlockletEvents.upgradeFailed,
|
|
365
|
-
BlockletEvents.downgraded,
|
|
366
|
-
BlockletEvents.downgradeFailed,
|
|
367
361
|
BlockletEvents.updated,
|
|
368
362
|
BlockletEvents.statusChange,
|
|
369
363
|
BlockletEvents.removed,
|
|
@@ -372,6 +366,12 @@ module.exports = ({
|
|
|
372
366
|
BlockletEvents.stopped,
|
|
373
367
|
BlockletEvents.appDidChanged,
|
|
374
368
|
|
|
369
|
+
BlockletEvents.componentInstalled,
|
|
370
|
+
BlockletEvents.componentInstallFailed,
|
|
371
|
+
BlockletEvents.componentUpgraded,
|
|
372
|
+
BlockletEvents.componentUpgradeFailed,
|
|
373
|
+
BlockletEvents.componentRemoved,
|
|
374
|
+
|
|
375
375
|
BlockletEvents.backupProgress,
|
|
376
376
|
BlockletEvents.restoreProgress,
|
|
377
377
|
BlockletEvents.downloadBundleProgress,
|
package/lib/index.js
CHANGED
|
@@ -258,6 +258,10 @@ function ABTNode(options) {
|
|
|
258
258
|
configPublicToStore: blockletManager.configPublicToStore.bind(blockletManager),
|
|
259
259
|
configNavigations: blockletManager.configNavigations.bind(blockletManager),
|
|
260
260
|
configOAuth: blockletManager.configOAuth.bind(blockletManager),
|
|
261
|
+
joinFederatedLogin: blockletManager.joinFederatedLogin.bind(blockletManager),
|
|
262
|
+
auditFederatedLogin: blockletManager.auditFederatedLogin.bind(blockletManager),
|
|
263
|
+
configFederated: blockletManager.configFederated.bind(blockletManager),
|
|
264
|
+
setFederated: blockletManager.setFederated.bind(blockletManager),
|
|
261
265
|
configNotification: blockletManager.configNotification.bind(blockletManager),
|
|
262
266
|
updateWhoCanAccess: blockletManager.updateWhoCanAccess.bind(blockletManager),
|
|
263
267
|
updateAppSessionConfig: blockletManager.updateAppSessionConfig.bind(blockletManager),
|
package/lib/states/audit-log.js
CHANGED
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
/* eslint-disable no-async-promise-executor */
|
|
3
3
|
const pick = require('lodash/pick');
|
|
4
4
|
const get = require('lodash/get');
|
|
5
|
+
const uniq = require('lodash/uniq');
|
|
5
6
|
const joinUrl = require('url-join');
|
|
6
7
|
const { getDisplayName } = require('@blocklet/meta/lib/util');
|
|
7
8
|
const { BLOCKLET_SITE_GROUP_SUFFIX, NODE_SERVICES } = require('@abtnode/constant');
|
|
@@ -20,20 +21,18 @@ const getServerInfo = (info) => `[${info.name}](${joinUrl(info.routing.adminPath
|
|
|
20
21
|
* }} info
|
|
21
22
|
* @returns {string}
|
|
22
23
|
*/
|
|
23
|
-
const getBlockletInfo = (blocklet, info) => `[${getDisplayName(blocklet)}
|
|
24
|
-
const
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
24
|
+
const getBlockletInfo = (blocklet, info) => `[${getDisplayName(blocklet)}](${joinUrl(info.routing.adminPath, '/blocklets/', blocklet.meta.did, '/overview')})`; // prettier-ignore
|
|
25
|
+
const componentOrApplication = (componentDids) => (componentDids?.length ? 'component' : 'application');
|
|
26
|
+
const getComponentNamesWithVersion = (blocklet, componentDids) =>
|
|
27
|
+
uniq(componentDids || [])
|
|
28
|
+
.map((x) => {
|
|
29
|
+
const component = blocklet.children.find((y) => y.meta.did === x);
|
|
30
|
+
return `${component.meta.title}@${component.meta.version}`;
|
|
31
|
+
})
|
|
32
|
+
.join(', ');
|
|
33
|
+
const componentOrApplicationInfo = (app, componentDids) =>
|
|
34
|
+
`${componentOrApplication(componentDids)} ${getComponentNamesWithVersion(app, componentDids)}`;
|
|
28
35
|
|
|
29
|
-
if (teamDid === info.did) {
|
|
30
|
-
return getServerInfo(info);
|
|
31
|
-
}
|
|
32
|
-
|
|
33
|
-
const { blocklet } = node.states;
|
|
34
|
-
const doc = await blocklet.getBlocklet(teamDid);
|
|
35
|
-
return doc ? getBlockletInfo(doc, info) : '';
|
|
36
|
-
};
|
|
37
36
|
const expandSite = async (siteId, info, node) => {
|
|
38
37
|
if (!siteId) {
|
|
39
38
|
return '';
|
|
@@ -97,8 +96,7 @@ const expandUser = async (teamDid, userDid, passportId, info, node) => {
|
|
|
97
96
|
* @return {string} the generated markdown source
|
|
98
97
|
*/
|
|
99
98
|
const getLogContent = async (action, args, context, result, info, node) => {
|
|
100
|
-
const [
|
|
101
|
-
expandTeam(args.teamDid, info, node),
|
|
99
|
+
const [site, [user, passport]] = await Promise.all([
|
|
102
100
|
expandSite(args.id, info, node),
|
|
103
101
|
expandUser(args.teamDid, args.userDid || get(args, 'user.did') || args.ownerDid, args.passportId, info, node),
|
|
104
102
|
]);
|
|
@@ -106,60 +104,56 @@ const getLogContent = async (action, args, context, result, info, node) => {
|
|
|
106
104
|
switch (action) {
|
|
107
105
|
// blocklets
|
|
108
106
|
case 'installBlocklet':
|
|
109
|
-
return `installed
|
|
107
|
+
return `installed application ${result.meta.title}`;
|
|
108
|
+
case 'deleteBlocklet':
|
|
109
|
+
return `removed application ${result.meta.title}`; // prettier-ignore
|
|
110
|
+
case 'backupBlocklet':
|
|
111
|
+
return `backup application ${result.meta.title}`; // prettier-ignore
|
|
110
112
|
case 'startBlocklet':
|
|
111
|
-
return `started
|
|
113
|
+
return `started ${componentOrApplicationInfo(result, args.componentDids)}`;
|
|
112
114
|
case 'restartBlocklet':
|
|
113
|
-
return `restarted
|
|
115
|
+
return `restarted ${componentOrApplicationInfo(result, args.componentDids)}`;
|
|
114
116
|
case 'reloadBlocklet':
|
|
115
|
-
return `reloaded
|
|
117
|
+
return `reloaded ${componentOrApplicationInfo(result, args.componentDids)}`;
|
|
116
118
|
case 'stopBlocklet':
|
|
117
|
-
return `stopped
|
|
119
|
+
return `stopped ${componentOrApplicationInfo(result, args.componentDids)}`;
|
|
118
120
|
case 'resetBlocklet':
|
|
119
|
-
return `reset
|
|
120
|
-
case 'deleteBlocklet':
|
|
121
|
-
return `removed blocklet ${getBlockletInfo(result, info)} ${args.keepData ? 'but kept its data and config' : 'and its data and config'}`; // prettier-ignore
|
|
122
|
-
case 'installComponent':
|
|
123
|
-
return `added component from ${args.file ? 'Upload' : args.url} at **${args.mountPoint}** to ${getBlockletInfo(result, info)}`; // prettier-ignore
|
|
124
|
-
case 'deleteComponent':
|
|
125
|
-
return `removed component ${args.did} from blocklet ${getBlockletInfo(result, info)}`;
|
|
126
|
-
case 'configBlocklet':
|
|
127
|
-
return `updated following config for blocklet ${getBlockletInfo(result, info)}:\n${args.configs.map(x => `* ${x.key}: ${x.value}`).join('\n')}`; // prettier-ignore
|
|
121
|
+
return `reset ${componentOrApplicationInfo(result, args.childDid ? [args.childDid] : [])}`;
|
|
128
122
|
case 'upgradeBlocklet':
|
|
123
|
+
const actionName = result.action || 'upgraded';
|
|
129
124
|
if (result.resultStatus === 'failed') {
|
|
130
|
-
return
|
|
125
|
+
return `${actionName} component failed: **${getComponentNamesWithVersion(result, result.componentDids)}**`;
|
|
131
126
|
}
|
|
132
|
-
return
|
|
127
|
+
return `${actionName} component: **${getComponentNamesWithVersion(result, result.componentDids)}**`;
|
|
128
|
+
case 'deleteComponent':
|
|
129
|
+
return `removed ${result.deletedComponent.meta.title}@${result.deletedComponent.meta.version} ${ args.keepData !== false ? 'but kept its data and config' : 'and its data and config' }`; // prettier-ignore
|
|
130
|
+
case 'configBlocklet':
|
|
131
|
+
return `updated following config for ${args.did?.length > 1 ? componentOrApplicationInfo(result, [args.did[1]]) : 'application'}: ${args.configs.map(x => `* ${x.key}`).join(', ')}`; // prettier-ignore
|
|
133
132
|
case 'backupToSpaces':
|
|
134
133
|
if (args?.success) {
|
|
135
|
-
return `Backup ${
|
|
136
|
-
args.url
|
|
137
|
-
} successfully:\n- Backup files have been stored [here](${args.backupUrl})`;
|
|
134
|
+
return `Backup application to ${args.url} successfully:\n- Backup files have been stored [here](${args.backupUrl})`;
|
|
138
135
|
}
|
|
139
|
-
return `Backup ${
|
|
140
|
-
args.url
|
|
141
|
-
} failed:\n- The reason for the error is: <span style='color:red'>${args.errorMessage}</span>`;
|
|
142
|
-
|
|
143
|
-
case 'upgradeComponents':
|
|
144
|
-
return `upgraded components for blocklet ${getBlockletInfo(result, info)}`;
|
|
136
|
+
return `Backup application to ${args.url} failed:\n- The reason for the error is: <span style='color:red'>${args.errorMessage}</span>`;
|
|
145
137
|
case 'configPublicToStore':
|
|
146
|
-
|
|
147
|
-
return `set publicToStore to true for blocklet ${getBlockletInfo(result, info)}`;
|
|
148
|
-
}
|
|
149
|
-
return `set publicToStore to false for blocklet ${getBlockletInfo(result, info)}`;
|
|
138
|
+
return `set publicToStore to ${args.publicToStore ? 'true' : 'false'}`;
|
|
150
139
|
case 'configNavigations':
|
|
151
140
|
// eslint-disable-next-line prettier/prettier
|
|
152
|
-
return `updated following navigations
|
|
141
|
+
return `updated following navigations:\n${args.navigations.map(
|
|
153
142
|
(x) => `- ${x.title}: ${x.link}\n`
|
|
154
143
|
)}`;
|
|
155
144
|
case 'configOAuth':
|
|
156
145
|
return `updated following OAuth for blocklet ${getBlockletInfo(result, info)}:\n${args.oauth}`;
|
|
146
|
+
// TODO: @zhanghan 配置审计日志
|
|
147
|
+
case 'joinFederatedLogin':
|
|
148
|
+
return `updated following OAuth for blocklet ${getBlockletInfo(result, info)}:\n${args.oauth}`;
|
|
149
|
+
case 'auditFederatedLogin':
|
|
150
|
+
return `updated following OAuth:\n${args.oauth}`;
|
|
157
151
|
case 'configNotification':
|
|
158
|
-
return `updated following notification setting
|
|
152
|
+
return `updated following notification setting: ${args.notification}`;
|
|
159
153
|
case 'updateComponentTitle':
|
|
160
|
-
return `update component title to **${args.title}
|
|
154
|
+
return `update component title to **${args.title}**`;
|
|
161
155
|
case 'updateComponentMountPoint':
|
|
162
|
-
return `update component mount point to **${args.mountPoint}
|
|
156
|
+
return `update component mount point to **${args.mountPoint}**`;
|
|
163
157
|
// store
|
|
164
158
|
case 'addBlockletStore':
|
|
165
159
|
return `added blocklet store ${args.url}`;
|
|
@@ -173,57 +167,57 @@ const getLogContent = async (action, args, context, result, info, node) => {
|
|
|
173
167
|
// teams: members/passports
|
|
174
168
|
case 'addUser':
|
|
175
169
|
if (args.passport) {
|
|
176
|
-
return `${args.reason} and received **${args.passport.name}** passport
|
|
170
|
+
return `${args.reason} and received **${args.passport.name}** passport`;
|
|
177
171
|
}
|
|
178
|
-
return `joined team
|
|
172
|
+
return `joined team by ${args.reason}`;
|
|
179
173
|
case 'updateUser':
|
|
180
|
-
return `${args.reason} and received **${args.passport.name}** passport
|
|
174
|
+
return `${args.reason} and received **${args.passport.name}** passport`;
|
|
181
175
|
case 'connectAccount':
|
|
182
176
|
return `user ${user} connect with account ${args.connectedAccount.provider}: ${args.connectedAccount.did}`;
|
|
183
177
|
case 'switchProfile':
|
|
184
|
-
return `switched profile to ${args.profile.fullName}
|
|
178
|
+
return `switched profile to ${args.profile.fullName}`;
|
|
185
179
|
case 'switchPassport':
|
|
186
|
-
return `${args.provider} user ${user} switched passport to ${args.passport.name}
|
|
180
|
+
return `${args.provider} user ${user} switched passport to ${args.passport.name}`;
|
|
187
181
|
case 'login':
|
|
188
|
-
return `${args.provider} user ${user} logged in
|
|
182
|
+
return `${args.provider} user ${user} logged in with passport ${args.passport.name}`;
|
|
189
183
|
case 'updateWhoCanAccess':
|
|
190
184
|
return `updated access control policy to **${args.whoCanAccess}**`;
|
|
191
185
|
case 'configPassportIssuance':
|
|
192
|
-
return `${args.enabled ? 'enabled' : 'disabled'} passport issuance
|
|
186
|
+
return `${args.enabled ? 'enabled' : 'disabled'} passport issuance`;
|
|
193
187
|
case 'createPassportIssuance':
|
|
194
|
-
return `issued **${args.name}** passport to ${user}
|
|
188
|
+
return `issued **${args.name}** passport to ${user}, issuance id: ${result.id}`;
|
|
195
189
|
case 'processPassportIssuance':
|
|
196
|
-
return `claimed passport **${args.name}
|
|
190
|
+
return `claimed passport **${args.name}**, issuance id: ${args.sessionId}`;
|
|
197
191
|
case 'revokeUserPassport':
|
|
198
|
-
return `revoked **${passport}** passport of user ${user}
|
|
192
|
+
return `revoked **${passport}** passport of user ${user}`;
|
|
199
193
|
case 'enableUserPassport':
|
|
200
|
-
return `enabled **${passport}** passport of user ${user}
|
|
194
|
+
return `enabled **${passport}** passport of user ${user}`;
|
|
201
195
|
case 'updateUserApproval':
|
|
202
|
-
return `${args.user.approved ? 'enabled' : 'disabled'} user ${user}
|
|
196
|
+
return `${args.user.approved ? 'enabled' : 'disabled'} user ${user}`;
|
|
203
197
|
case 'deletePassportIssuance':
|
|
204
|
-
return `removed passport issuance ${args.sessionId}
|
|
198
|
+
return `removed passport issuance ${args.sessionId}`;
|
|
205
199
|
case 'createMemberInvitation':
|
|
206
|
-
return `created member invitation(${result.inviteId}: ${args.remark}) with **${args.role}** passport
|
|
200
|
+
return `created member invitation(${result.inviteId}: ${args.remark}) with **${args.role}** passport`; // prettier-ignore
|
|
207
201
|
case 'deleteInvitation':
|
|
208
|
-
return `removed unused member invitation(${args.inviteId})
|
|
202
|
+
return `removed unused member invitation(${args.inviteId})`;
|
|
209
203
|
case 'createRole':
|
|
210
|
-
return `created passport ${args.name}(${args.title})
|
|
204
|
+
return `created passport ${args.name}(${args.title})`;
|
|
211
205
|
case 'updateRole':
|
|
212
|
-
return `updated passport ${args.role.name}(${args.role.title})
|
|
206
|
+
return `updated passport ${args.role.name}(${args.role.title})`;
|
|
213
207
|
case 'updatePermissionsForRole':
|
|
214
|
-
return `granted following permissions to passport ${args.roleName}
|
|
208
|
+
return `granted following permissions to passport ${args.roleName}: \n${args.grantNames.map(x => `- ${x}`).join('\n')}`; // prettier-ignore
|
|
215
209
|
case 'configTrustedPassports':
|
|
216
210
|
const trustedPassports = args.trustedPassports || [];
|
|
217
211
|
if (trustedPassports.length === 0) {
|
|
218
|
-
return
|
|
212
|
+
return 'removed all trusted passport issuers';
|
|
219
213
|
}
|
|
220
|
-
return `updated trusted passport issuers to following
|
|
214
|
+
return `updated trusted passport issuers to following: \n${trustedPassports.map(x => `- ${x.remark}: ${x.issuerDid}`).join('\n')}`; // prettier-ignore
|
|
221
215
|
case 'configTrustedFactories':
|
|
222
216
|
const trustedFactories = args.trustedFactories || [];
|
|
223
217
|
if (trustedFactories.length === 0) {
|
|
224
|
-
return
|
|
218
|
+
return 'removed all trusted factories';
|
|
225
219
|
}
|
|
226
|
-
return `updated trusted factories to following
|
|
220
|
+
return `updated trusted factories to following: \n${trustedFactories.map(x => `- ${x.remark}: ${x.factoryAddress}`).join('\n')}`; // prettier-ignore
|
|
227
221
|
case 'delegateTransferNFT':
|
|
228
222
|
return `${args.owner} ${args.reason}`;
|
|
229
223
|
case 'issuePassportToUser':
|
package/lib/states/blocklet.js
CHANGED
|
@@ -508,6 +508,7 @@ class BlockletState extends BaseState {
|
|
|
508
508
|
* }}
|
|
509
509
|
*/
|
|
510
510
|
async setBlockletStatus(did, status, { componentDids } = {}) {
|
|
511
|
+
logger.info('setBlockletStatus', { did, status, componentDids });
|
|
511
512
|
if (typeof status === 'undefined') {
|
|
512
513
|
throw new Error('Unsupported blocklet status');
|
|
513
514
|
}
|
|
@@ -23,7 +23,7 @@ class NotificationState extends BaseState {
|
|
|
23
23
|
}
|
|
24
24
|
|
|
25
25
|
async create(payload) {
|
|
26
|
-
['
|
|
26
|
+
['description'].forEach((x) => {
|
|
27
27
|
if (!payload[x]) {
|
|
28
28
|
throw new Error(`Invalid notification payload: ${x} is required`);
|
|
29
29
|
}
|
|
@@ -40,7 +40,7 @@ class NotificationState extends BaseState {
|
|
|
40
40
|
severity: payload.severity || 'info',
|
|
41
41
|
read: false,
|
|
42
42
|
});
|
|
43
|
-
this.emit(EVENTS.NOTIFICATION_CREATE, doc);
|
|
43
|
+
this.emit(EVENTS.NOTIFICATION_CREATE, { ...payload, ...doc });
|
|
44
44
|
return doc;
|
|
45
45
|
}
|
|
46
46
|
|
package/lib/util/blocklet.js
CHANGED
|
@@ -1811,6 +1811,16 @@ const ensureAppPortsNotOccupied = async ({
|
|
|
1811
1811
|
return newBlocklet;
|
|
1812
1812
|
};
|
|
1813
1813
|
|
|
1814
|
+
const getComponentNamesWithVersion = (app = {}, componentDids = []) => {
|
|
1815
|
+
const str = uniq(componentDids)
|
|
1816
|
+
.map((x) => {
|
|
1817
|
+
const component = (app.children || []).find((y) => y.meta.did === x);
|
|
1818
|
+
return `${component.meta.title}@${component.meta.version}`;
|
|
1819
|
+
})
|
|
1820
|
+
.join(', ');
|
|
1821
|
+
return str;
|
|
1822
|
+
};
|
|
1823
|
+
|
|
1814
1824
|
module.exports = {
|
|
1815
1825
|
updateBlockletFallbackLogo,
|
|
1816
1826
|
forEachBlocklet,
|
|
@@ -1873,4 +1883,5 @@ module.exports = {
|
|
|
1873
1883
|
getBlockletURLForLauncher,
|
|
1874
1884
|
exceedRedemptionPeriod,
|
|
1875
1885
|
ensureAppPortsNotOccupied,
|
|
1886
|
+
getComponentNamesWithVersion,
|
|
1876
1887
|
};
|