@abtnode/core 1.17.8-beta-20260109-075740-5f484e08 → 1.17.8-beta-20260111-112953-aed5ff39
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/access-key-manager.js +104 -0
- package/lib/api/team/invitation-manager.js +461 -0
- package/lib/api/team/notification-manager.js +189 -0
- package/lib/api/team/oauth-manager.js +60 -0
- package/lib/api/team/org-crud-manager.js +202 -0
- package/lib/api/team/org-manager.js +56 -0
- package/lib/api/team/org-member-manager.js +403 -0
- package/lib/api/team/org-query-manager.js +126 -0
- package/lib/api/team/org-resource-manager.js +186 -0
- package/lib/api/team/passport-manager.js +670 -0
- package/lib/api/team/rbac-manager.js +335 -0
- package/lib/api/team/session-manager.js +540 -0
- package/lib/api/team/store-manager.js +198 -0
- package/lib/api/team/tag-manager.js +230 -0
- package/lib/api/team/user-auth-manager.js +132 -0
- package/lib/api/team/user-manager.js +78 -0
- package/lib/api/team/user-query-manager.js +299 -0
- package/lib/api/team/user-social-manager.js +354 -0
- package/lib/api/team/user-update-manager.js +224 -0
- package/lib/api/team/verify-code-manager.js +161 -0
- package/lib/api/team.js +439 -3287
- package/lib/blocklet/manager/disk/auth-manager.js +68 -0
- package/lib/blocklet/manager/disk/backup-manager.js +288 -0
- package/lib/blocklet/manager/disk/cleanup-manager.js +157 -0
- package/lib/blocklet/manager/disk/component-manager.js +83 -0
- package/lib/blocklet/manager/disk/config-manager.js +191 -0
- package/lib/blocklet/manager/disk/controller-manager.js +64 -0
- package/lib/blocklet/manager/disk/delete-reset-manager.js +328 -0
- package/lib/blocklet/manager/disk/download-manager.js +96 -0
- package/lib/blocklet/manager/disk/env-config-manager.js +311 -0
- package/lib/blocklet/manager/disk/federated-manager.js +651 -0
- package/lib/blocklet/manager/disk/hook-manager.js +124 -0
- package/lib/blocklet/manager/disk/install-component-manager.js +95 -0
- package/lib/blocklet/manager/disk/install-core-manager.js +448 -0
- package/lib/blocklet/manager/disk/install-download-manager.js +313 -0
- package/lib/blocklet/manager/disk/install-manager.js +36 -0
- package/lib/blocklet/manager/disk/install-upgrade-manager.js +340 -0
- package/lib/blocklet/manager/disk/job-manager.js +467 -0
- package/lib/blocklet/manager/disk/lifecycle-manager.js +26 -0
- package/lib/blocklet/manager/disk/notification-manager.js +343 -0
- package/lib/blocklet/manager/disk/query-manager.js +562 -0
- package/lib/blocklet/manager/disk/settings-manager.js +507 -0
- package/lib/blocklet/manager/disk/start-manager.js +611 -0
- package/lib/blocklet/manager/disk/stop-restart-manager.js +292 -0
- package/lib/blocklet/manager/disk/update-manager.js +153 -0
- package/lib/blocklet/manager/disk.js +669 -5796
- package/lib/blocklet/manager/helper/blue-green-start-blocklet.js +5 -0
- package/lib/blocklet/manager/lock.js +18 -0
- package/lib/event/index.js +28 -24
- package/lib/util/blocklet/app-utils.js +192 -0
- package/lib/util/blocklet/blocklet-loader.js +258 -0
- package/lib/util/blocklet/config-manager.js +232 -0
- package/lib/util/blocklet/did-document.js +240 -0
- package/lib/util/blocklet/environment.js +555 -0
- package/lib/util/blocklet/health-check.js +449 -0
- package/lib/util/blocklet/install-utils.js +365 -0
- package/lib/util/blocklet/logo.js +57 -0
- package/lib/util/blocklet/meta-utils.js +269 -0
- package/lib/util/blocklet/port-manager.js +141 -0
- package/lib/util/blocklet/process-manager.js +504 -0
- package/lib/util/blocklet/runtime-info.js +105 -0
- package/lib/util/blocklet/validation.js +418 -0
- package/lib/util/blocklet.js +98 -3066
- package/lib/util/wallet-app-notification.js +40 -0
- package/package.json +22 -22
|
@@ -0,0 +1,232 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Configuration Manager Module
|
|
3
|
+
*
|
|
4
|
+
* Functions for managing blocklet configurations, preferences, and pack settings
|
|
5
|
+
* Extracted from blocklet.js for better modularity
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
const fs = require('fs-extra');
|
|
9
|
+
const path = require('node:path');
|
|
10
|
+
|
|
11
|
+
const {
|
|
12
|
+
BlockletGroup,
|
|
13
|
+
BLOCKLET_PREFERENCE_FILE,
|
|
14
|
+
BLOCKLET_PREFERENCE_PREFIX,
|
|
15
|
+
BLOCKLET_RESOURCE_DIR,
|
|
16
|
+
} = require('@blocklet/constant');
|
|
17
|
+
const { isEnvShareable } = require('@blocklet/meta/lib/util');
|
|
18
|
+
|
|
19
|
+
const { APP_CONFIG_IMAGE_KEYS } = require('../index');
|
|
20
|
+
|
|
21
|
+
/**
|
|
22
|
+
* Helper to convert preference schema properties to config format
|
|
23
|
+
* @param {object} properties - Schema properties
|
|
24
|
+
* @param {Array} result - Result array to populate
|
|
25
|
+
*/
|
|
26
|
+
const fromProperty2Config = (properties = {}, result) => {
|
|
27
|
+
Object.keys(properties).forEach((key) => {
|
|
28
|
+
const prop = properties[key];
|
|
29
|
+
if (prop.properties && ['ArrayTable', 'ArrayCards'].includes(prop['x-component']) === false) {
|
|
30
|
+
fromProperty2Config(prop.properties, result);
|
|
31
|
+
} else if (prop['x-decorator'] === 'FormItem') {
|
|
32
|
+
const secure = prop['x-component'] === 'Password';
|
|
33
|
+
result.push({
|
|
34
|
+
default: prop.default || '',
|
|
35
|
+
description: prop.title || key,
|
|
36
|
+
name: `${BLOCKLET_PREFERENCE_PREFIX}${key}`,
|
|
37
|
+
required: prop.required || false,
|
|
38
|
+
secure,
|
|
39
|
+
// eslint-disable-next-line no-nested-ternary
|
|
40
|
+
shared: secure ? false : typeof prop.shared === 'undefined' ? true : prop.shared,
|
|
41
|
+
});
|
|
42
|
+
}
|
|
43
|
+
});
|
|
44
|
+
};
|
|
45
|
+
|
|
46
|
+
/**
|
|
47
|
+
* Get config from blocklet preferences schema file
|
|
48
|
+
* @param {object} blocklet - Blocklet object with env.appDir
|
|
49
|
+
* @returns {Array} Array of config objects
|
|
50
|
+
*/
|
|
51
|
+
const getConfigFromPreferences = (blocklet) => {
|
|
52
|
+
const result = [];
|
|
53
|
+
const schemaFile = path.join(blocklet.env.appDir, BLOCKLET_PREFERENCE_FILE);
|
|
54
|
+
if (fs.existsSync(schemaFile)) {
|
|
55
|
+
try {
|
|
56
|
+
const schema = JSON.parse(fs.readFileSync(schemaFile, 'utf8'));
|
|
57
|
+
fromProperty2Config(schema.schema?.properties, result);
|
|
58
|
+
} catch {
|
|
59
|
+
// do nothing
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
return result;
|
|
64
|
+
};
|
|
65
|
+
|
|
66
|
+
/**
|
|
67
|
+
* Get app configs from component that should be shared
|
|
68
|
+
* @param {object} meta - Component meta
|
|
69
|
+
* @param {Array} configsInApp - Configs already in app
|
|
70
|
+
* @param {Array} configsInComponent - Configs in component
|
|
71
|
+
* @returns {Array} Array of shared config objects
|
|
72
|
+
*/
|
|
73
|
+
const getAppConfigsFromComponent = (meta, configsInApp = [], configsInComponent = []) => {
|
|
74
|
+
const configs = [];
|
|
75
|
+
for (const configInMeta of meta?.environments || []) {
|
|
76
|
+
if (isEnvShareable(configInMeta)) {
|
|
77
|
+
const configInApp = (configsInApp || []).find((x) => x.key === configInMeta.name);
|
|
78
|
+
if (!configInApp) {
|
|
79
|
+
const configInComponent = configsInComponent.find((y) => y.key === configInMeta.name);
|
|
80
|
+
if (configInComponent && isEnvShareable(configInComponent)) {
|
|
81
|
+
configs.push(configInComponent);
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
return configs;
|
|
87
|
+
};
|
|
88
|
+
|
|
89
|
+
/**
|
|
90
|
+
* Separate configs into shared and self configs
|
|
91
|
+
* @param {Array} configs - Input configs
|
|
92
|
+
* @param {Array} oldConfigs - Existing configs
|
|
93
|
+
* @returns {{ sharedConfigs: Array, selfConfigs: Array }}
|
|
94
|
+
*/
|
|
95
|
+
const getConfigsFromInput = (configs = [], oldConfigs = []) => {
|
|
96
|
+
const sharedConfigs = [];
|
|
97
|
+
const selfConfigs = [];
|
|
98
|
+
|
|
99
|
+
configs.forEach((config) => {
|
|
100
|
+
const oldConfig = oldConfigs.find((y) => y.key === config.key);
|
|
101
|
+
if (!config.key.startsWith(BLOCKLET_PREFERENCE_PREFIX) && (isEnvShareable(config) || isEnvShareable(oldConfig))) {
|
|
102
|
+
sharedConfigs.push(config);
|
|
103
|
+
} else {
|
|
104
|
+
selfConfigs.push(config);
|
|
105
|
+
}
|
|
106
|
+
});
|
|
107
|
+
|
|
108
|
+
return { sharedConfigs, selfConfigs };
|
|
109
|
+
};
|
|
110
|
+
|
|
111
|
+
/**
|
|
112
|
+
* Remove app configs if no component uses them
|
|
113
|
+
* @param {Array} componentConfigs - Configs from removed component
|
|
114
|
+
* @param {object} app - App blocklet
|
|
115
|
+
* @param {object} blockletExtraState - Blocklet extra state manager
|
|
116
|
+
*/
|
|
117
|
+
const removeAppConfigsFromComponent = async (componentConfigs, app, blockletExtraState) => {
|
|
118
|
+
const appConfigs = app.configs || [];
|
|
119
|
+
const remainedConfigs = [].concat(...(app.children || []).map((x) => x.configs || []));
|
|
120
|
+
const removedAppConfigs = [];
|
|
121
|
+
|
|
122
|
+
componentConfigs.forEach((config) => {
|
|
123
|
+
const appConfig = appConfigs.find((x) => x.key === config.key);
|
|
124
|
+
if (
|
|
125
|
+
appConfig &&
|
|
126
|
+
!appConfig.custom &&
|
|
127
|
+
!(app.meta.environments || []).find((x) => x.name === config.key) &&
|
|
128
|
+
!remainedConfigs.find((x) => x.key === config.key && isEnvShareable(x))
|
|
129
|
+
) {
|
|
130
|
+
removedAppConfigs.push({ key: appConfig.key, value: undefined });
|
|
131
|
+
}
|
|
132
|
+
});
|
|
133
|
+
|
|
134
|
+
if (removedAppConfigs.length) {
|
|
135
|
+
await blockletExtraState.setConfigs(app.meta.did, removedAppConfigs);
|
|
136
|
+
}
|
|
137
|
+
};
|
|
138
|
+
|
|
139
|
+
/**
|
|
140
|
+
* Get pack component from app children
|
|
141
|
+
* @param {object} app - App blocklet
|
|
142
|
+
* @returns {object|undefined} Pack component
|
|
143
|
+
*/
|
|
144
|
+
const getPackComponent = (app) => {
|
|
145
|
+
return (app?.children || []).find((x) => x.meta.group === BlockletGroup.pack);
|
|
146
|
+
};
|
|
147
|
+
|
|
148
|
+
/**
|
|
149
|
+
* Get pack config from pack component
|
|
150
|
+
* @param {object} app - App blocklet
|
|
151
|
+
* @returns {object|null} Pack config or null
|
|
152
|
+
*/
|
|
153
|
+
const getPackConfig = (app) => {
|
|
154
|
+
const packComponent = getPackComponent(app);
|
|
155
|
+
if (!packComponent) {
|
|
156
|
+
return null;
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
const resource = (packComponent.meta.resource?.bundles || []).find(
|
|
160
|
+
(x) => x.did === packComponent.meta.did && x.type === 'config'
|
|
161
|
+
);
|
|
162
|
+
|
|
163
|
+
if (!resource) {
|
|
164
|
+
return null;
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
const { appDir } = packComponent.env;
|
|
168
|
+
const configFile = path.join(appDir, BLOCKLET_RESOURCE_DIR, resource.did, resource.type, 'config.json');
|
|
169
|
+
|
|
170
|
+
if (!fs.existsSync(configFile)) {
|
|
171
|
+
return null;
|
|
172
|
+
}
|
|
173
|
+
|
|
174
|
+
return fs.readJSON(configFile);
|
|
175
|
+
};
|
|
176
|
+
|
|
177
|
+
/**
|
|
178
|
+
* Copy pack images from pack dir to app data dir
|
|
179
|
+
* @param {object} options - Options
|
|
180
|
+
* @param {string} options.appDataDir - App data directory
|
|
181
|
+
* @param {string} options.packDir - Pack directory
|
|
182
|
+
* @param {object} options.packConfig - Pack config with navigations and configObj
|
|
183
|
+
*/
|
|
184
|
+
const copyPackImages = async ({ appDataDir, packDir, packConfig = {} }) => {
|
|
185
|
+
const mediaDir = path.join(appDataDir, 'media', 'blocklet-service');
|
|
186
|
+
const { navigations = [], configObj = {} } = packConfig;
|
|
187
|
+
await fs.ensureDir(mediaDir);
|
|
188
|
+
|
|
189
|
+
// Filter bottom navigation items with icons
|
|
190
|
+
const bottomNavItems = navigations.filter((item) => {
|
|
191
|
+
const sections = Array.isArray(item.section) ? item.section : [item.section];
|
|
192
|
+
return sections.includes('bottomNavigation') && item.icon;
|
|
193
|
+
});
|
|
194
|
+
|
|
195
|
+
// Copy tabbar navigation icons
|
|
196
|
+
if (bottomNavItems.length > 0) {
|
|
197
|
+
await Promise.all(
|
|
198
|
+
bottomNavItems.map(async (item) => {
|
|
199
|
+
const iconFileName = path.basename(item.icon);
|
|
200
|
+
const iconInImages = path.join(packDir, 'images', iconFileName);
|
|
201
|
+
|
|
202
|
+
if (fs.existsSync(iconInImages)) {
|
|
203
|
+
await fs.copy(iconInImages, path.join(mediaDir, iconFileName));
|
|
204
|
+
}
|
|
205
|
+
})
|
|
206
|
+
);
|
|
207
|
+
}
|
|
208
|
+
|
|
209
|
+
// Copy brand-related images
|
|
210
|
+
await Promise.all(
|
|
211
|
+
APP_CONFIG_IMAGE_KEYS.map(async (key) => {
|
|
212
|
+
const value = configObj[key];
|
|
213
|
+
if (value) {
|
|
214
|
+
const imgFile = path.join(packDir, 'images', value);
|
|
215
|
+
if (fs.existsSync(imgFile)) {
|
|
216
|
+
await fs.copy(imgFile, path.join(appDataDir, value));
|
|
217
|
+
}
|
|
218
|
+
}
|
|
219
|
+
})
|
|
220
|
+
);
|
|
221
|
+
};
|
|
222
|
+
|
|
223
|
+
module.exports = {
|
|
224
|
+
fromProperty2Config,
|
|
225
|
+
getConfigFromPreferences,
|
|
226
|
+
getAppConfigsFromComponent,
|
|
227
|
+
getConfigsFromInput,
|
|
228
|
+
removeAppConfigsFromComponent,
|
|
229
|
+
getPackComponent,
|
|
230
|
+
getPackConfig,
|
|
231
|
+
copyPackImages,
|
|
232
|
+
};
|
|
@@ -0,0 +1,240 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* DID Document Module
|
|
3
|
+
*
|
|
4
|
+
* Functions for managing blocklet DID documents
|
|
5
|
+
* Extracted from blocklet.js for better modularity
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
const isEmpty = require('lodash/isEmpty');
|
|
9
|
+
|
|
10
|
+
const { toDid, toBuffer } = require('@ocap/util');
|
|
11
|
+
const { fromPublicKey } = require('@ocap/wallet');
|
|
12
|
+
const logger = require('@abtnode/logger')('@abtnode/core:util:blocklet:did-document');
|
|
13
|
+
const { isCustomDomain } = require('@abtnode/util/lib/url-evaluation');
|
|
14
|
+
const { isInServerlessMode } = require('@abtnode/util/lib/serverless');
|
|
15
|
+
const md5 = require('@abtnode/util/lib/md5');
|
|
16
|
+
const didDocument = require('@abtnode/util/lib/did-document');
|
|
17
|
+
const { SLOT_FOR_IP_DNS_SITE } = require('@abtnode/constant');
|
|
18
|
+
const { BLOCKLET_CONFIGURABLE_KEY, fromBlockletStatus } = require('@blocklet/constant');
|
|
19
|
+
const { getBlockletInfo } = require('@blocklet/meta/lib/info');
|
|
20
|
+
const { fixAvatar } = require('@blocklet/sdk/lib/util/user');
|
|
21
|
+
|
|
22
|
+
const { getServerDidDomain, replaceDomainSlot } = require('../index');
|
|
23
|
+
const { getFromCache: getAccessibleExternalNodeIp } = require('../get-accessible-external-node-ip');
|
|
24
|
+
|
|
25
|
+
/**
|
|
26
|
+
* Check if SLP domain should be enabled based on mode
|
|
27
|
+
* @param {string} mode - Node mode
|
|
28
|
+
* @returns {boolean}
|
|
29
|
+
*/
|
|
30
|
+
const shouldEnableSlpDomain = (mode) => {
|
|
31
|
+
if (process.env.ABT_NODE_ENABLE_SLP_DOMAIN === 'true') {
|
|
32
|
+
return true;
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
if (process.env.ABT_NODE_ENABLE_SLP_DOMAIN === 'false') {
|
|
36
|
+
return false;
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
return isInServerlessMode({ mode });
|
|
40
|
+
};
|
|
41
|
+
|
|
42
|
+
/**
|
|
43
|
+
* Get SLP DID from server DID and app permanent ID
|
|
44
|
+
* @param {string} serverDid - Server DID
|
|
45
|
+
* @param {string} appPid - App permanent ID
|
|
46
|
+
* @returns {string} SLP DID address
|
|
47
|
+
*/
|
|
48
|
+
const getSlpDid = (serverDid, appPid) => {
|
|
49
|
+
if (!serverDid || !appPid) {
|
|
50
|
+
throw new Error('serverDid and appPid is required');
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
const buffer = Buffer.concat([toBuffer(serverDid), toBuffer(appPid)]);
|
|
54
|
+
const md5Str = md5(buffer);
|
|
55
|
+
|
|
56
|
+
const wallet = fromPublicKey(md5Str);
|
|
57
|
+
return wallet.address;
|
|
58
|
+
};
|
|
59
|
+
|
|
60
|
+
/**
|
|
61
|
+
* Get blocklet known as (alias DIDs)
|
|
62
|
+
* @param {object} blocklet - Blocklet object
|
|
63
|
+
* @returns {string[]} Array of DIDs
|
|
64
|
+
*/
|
|
65
|
+
const getBlockletKnownAs = (blocklet) => {
|
|
66
|
+
const alsoKnownAs = [blocklet.appDid];
|
|
67
|
+
if (Array.isArray(blocklet.migratedFrom)) {
|
|
68
|
+
blocklet.migratedFrom.filter((x) => x.appDid !== blocklet.appPid).forEach((x) => alsoKnownAs.push(x.appDid));
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
return alsoKnownAs.filter(Boolean).map(toDid);
|
|
72
|
+
};
|
|
73
|
+
|
|
74
|
+
/**
|
|
75
|
+
* Publish DID document for a blocklet
|
|
76
|
+
* @param {object} options - Options
|
|
77
|
+
* @param {object} options.blocklet - Blocklet object
|
|
78
|
+
* @param {object} options.ownerInfo - Owner info
|
|
79
|
+
* @param {object} options.nodeInfo - Node info
|
|
80
|
+
*/
|
|
81
|
+
// eslint-disable-next-line require-await
|
|
82
|
+
const publishDidDocument = async ({ blocklet, ownerInfo, nodeInfo }) => {
|
|
83
|
+
const alsoKnownAs = getBlockletKnownAs(blocklet);
|
|
84
|
+
logger.debug('updateDidDocument blocklet info', { blocklet });
|
|
85
|
+
|
|
86
|
+
const { wallet } = getBlockletInfo(blocklet, nodeInfo.sk);
|
|
87
|
+
const { mode, did: serverDid } = nodeInfo;
|
|
88
|
+
|
|
89
|
+
let slpDid = null;
|
|
90
|
+
const enableSlpDomain = shouldEnableSlpDomain(mode);
|
|
91
|
+
if (enableSlpDomain) {
|
|
92
|
+
slpDid = getSlpDid(serverDid, blocklet.appPid);
|
|
93
|
+
|
|
94
|
+
if (alsoKnownAs.indexOf(slpDid) === -1) {
|
|
95
|
+
alsoKnownAs.push(toDid(slpDid));
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
logger.info('update did document', {
|
|
100
|
+
blockletDid: blocklet.meta.did,
|
|
101
|
+
alsoKnownAs,
|
|
102
|
+
slpDid,
|
|
103
|
+
daemonDidDomain: getServerDidDomain(nodeInfo),
|
|
104
|
+
didRegistryUrl: nodeInfo.didRegistry,
|
|
105
|
+
domain: nodeInfo.didDomain,
|
|
106
|
+
slpDomain: nodeInfo.slpDomain,
|
|
107
|
+
});
|
|
108
|
+
|
|
109
|
+
const name = blocklet.meta?.title || blocklet.meta?.name;
|
|
110
|
+
const state = fromBlockletStatus(blocklet.status);
|
|
111
|
+
|
|
112
|
+
let launcher;
|
|
113
|
+
if (!isEmpty(blocklet.controller)) {
|
|
114
|
+
launcher = {
|
|
115
|
+
did: toDid(blocklet.controller.did || nodeInfo.registerInfo.appPid), // 目前 controller 没有 launcher 的元信息, 默认在 nodeInfo 中存储
|
|
116
|
+
name: blocklet.controller.launcherName || nodeInfo.registerInfo.appName || '',
|
|
117
|
+
url: blocklet.controller.launcherUrl || nodeInfo.registerInfo.appUrl || '',
|
|
118
|
+
userDid: toDid(blocklet.controller.nftOwner),
|
|
119
|
+
};
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
const isPrimaryDomain = (d) => {
|
|
123
|
+
const appUrl = blocklet.environments.find((x) => x.key === BLOCKLET_CONFIGURABLE_KEY.BLOCKLET_APP_URL)?.value;
|
|
124
|
+
try {
|
|
125
|
+
const url = new URL(appUrl);
|
|
126
|
+
return url.hostname === d;
|
|
127
|
+
} catch (error) {
|
|
128
|
+
logger.error('failed to get primary domain', { error, domain: d, appUrl });
|
|
129
|
+
return false;
|
|
130
|
+
}
|
|
131
|
+
};
|
|
132
|
+
|
|
133
|
+
const domains = await Promise.all(
|
|
134
|
+
(blocklet.site?.domainAliases || []).map(async (item) => {
|
|
135
|
+
let type = isCustomDomain(item.value) ? 'custom' : 'internal';
|
|
136
|
+
// 如果域名是 appUrl,则设置为 primary
|
|
137
|
+
if (isPrimaryDomain(item.value)) {
|
|
138
|
+
type = 'primary';
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
if (item.value.includes(SLOT_FOR_IP_DNS_SITE)) {
|
|
142
|
+
const nodeIp = await getAccessibleExternalNodeIp();
|
|
143
|
+
item.value = replaceDomainSlot({ domain: item.value, nodeIp });
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
return {
|
|
147
|
+
type,
|
|
148
|
+
host: item.value,
|
|
149
|
+
url: `https://${item.value}`,
|
|
150
|
+
source: 'dnsRecords', // 固定为 dnsRecords
|
|
151
|
+
};
|
|
152
|
+
})
|
|
153
|
+
);
|
|
154
|
+
|
|
155
|
+
let owner;
|
|
156
|
+
if (ownerInfo) {
|
|
157
|
+
owner = {
|
|
158
|
+
did: toDid(ownerInfo.did),
|
|
159
|
+
name: ownerInfo.fullName,
|
|
160
|
+
avatar: fixAvatar(ownerInfo.avatar),
|
|
161
|
+
};
|
|
162
|
+
}
|
|
163
|
+
|
|
164
|
+
return didDocument.updateBlockletDocument({
|
|
165
|
+
blocklet,
|
|
166
|
+
wallet,
|
|
167
|
+
alsoKnownAs,
|
|
168
|
+
slpDid,
|
|
169
|
+
daemonDidDomain: getServerDidDomain(nodeInfo),
|
|
170
|
+
didRegistryUrl: nodeInfo.didRegistry,
|
|
171
|
+
domain: nodeInfo.didDomain,
|
|
172
|
+
slpDomain: nodeInfo.slpDomain,
|
|
173
|
+
serverDid,
|
|
174
|
+
blockletServerVersion: nodeInfo.version,
|
|
175
|
+
name,
|
|
176
|
+
state,
|
|
177
|
+
owner,
|
|
178
|
+
launcher,
|
|
179
|
+
domains,
|
|
180
|
+
});
|
|
181
|
+
};
|
|
182
|
+
|
|
183
|
+
/**
|
|
184
|
+
* Update DID document for a blocklet
|
|
185
|
+
* @param {object} options - Options
|
|
186
|
+
* @param {string} options.did - Blocklet DID
|
|
187
|
+
* @param {object} options.nodeInfo - Node info
|
|
188
|
+
* @param {object} options.teamManager - Team manager
|
|
189
|
+
* @param {object} options.states - State managers
|
|
190
|
+
*/
|
|
191
|
+
const updateDidDocument = async ({ did, nodeInfo, teamManager, states }) => {
|
|
192
|
+
const blocklet = await states.blocklet.getBlocklet(did);
|
|
193
|
+
const blockletExtra = await states.blockletExtras.findOne({ did });
|
|
194
|
+
|
|
195
|
+
blocklet.site = await states.site.findOneByBlocklet(did);
|
|
196
|
+
blocklet.settings = await states.blockletExtras.getSettings(did);
|
|
197
|
+
blocklet.controller = blockletExtra?.controller;
|
|
198
|
+
|
|
199
|
+
const ownerDid = blocklet.settings?.owner?.did;
|
|
200
|
+
let ownerInfo;
|
|
201
|
+
if (ownerDid) {
|
|
202
|
+
logger.info('get owner info', { ownerDid, teamDid: blocklet.appPid });
|
|
203
|
+
const userState = await teamManager.getUserState(blocklet.appPid);
|
|
204
|
+
ownerInfo = await userState.getUser(ownerDid);
|
|
205
|
+
}
|
|
206
|
+
|
|
207
|
+
return publishDidDocument({ blocklet, ownerInfo, nodeInfo });
|
|
208
|
+
};
|
|
209
|
+
|
|
210
|
+
/**
|
|
211
|
+
* Update DID document state only (e.g., to 'deleted') without fetching from database
|
|
212
|
+
* Used when blocklet is being removed and database data may not be available
|
|
213
|
+
* @param {object} options - Options
|
|
214
|
+
* @param {string} options.did - Blocklet DID
|
|
215
|
+
* @param {object} options.blocklet - Blocklet object
|
|
216
|
+
* @param {string} options.state - New state
|
|
217
|
+
* @param {object} options.nodeInfo - Node info
|
|
218
|
+
*/
|
|
219
|
+
const updateDidDocumentStateOnly = ({ did, blocklet, state, nodeInfo }) => {
|
|
220
|
+
logger.debug('update did document state only', { did, state });
|
|
221
|
+
|
|
222
|
+
const { wallet } = getBlockletInfo(blocklet, nodeInfo.sk);
|
|
223
|
+
|
|
224
|
+
return didDocument.updateBlockletStateOnly({
|
|
225
|
+
did,
|
|
226
|
+
state,
|
|
227
|
+
didRegistryUrl: nodeInfo.didRegistry,
|
|
228
|
+
wallet,
|
|
229
|
+
blockletServerVersion: nodeInfo.version,
|
|
230
|
+
});
|
|
231
|
+
};
|
|
232
|
+
|
|
233
|
+
module.exports = {
|
|
234
|
+
shouldEnableSlpDomain,
|
|
235
|
+
getSlpDid,
|
|
236
|
+
getBlockletKnownAs,
|
|
237
|
+
publishDidDocument,
|
|
238
|
+
updateDidDocument,
|
|
239
|
+
updateDidDocumentStateOnly,
|
|
240
|
+
};
|