@abtnode/blocklet-services 1.16.15-beta-e3a24907 → 1.16.15-beta-18951729

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/api/index.js CHANGED
@@ -19,6 +19,7 @@ const eventHub =
19
19
  process.env.NODE_ENV === 'test' ? require('@arcblock/event-hub/single') : require('@arcblock/event-hub');
20
20
  const logger = require('@abtnode/logger')(require('../package.json').name);
21
21
 
22
+ require('./libs/fetch');
22
23
  const cache = require('./cache');
23
24
  const { ensureProxyUrl } = require('./util');
24
25
  const { isProduction, isE2E } = require('./libs/env');
@@ -252,7 +253,7 @@ module.exports = function createServer(node, serverOptions = {}) {
252
253
  createFederatedRoutes.init(server, node, options);
253
254
  createUserRoutes.init(server, node, options);
254
255
  createEnvRoutes.init(server, node, options);
255
- createBlockletRoutes.init(server, node);
256
+ createBlockletRoutes.init(server, node, eventHub);
256
257
  createConnectSessionRoutes.init(server, node, options);
257
258
  createConnectRelayRoutes.init(server, node, options, wsRouter);
258
259
  authRoutes.attachDidAuthHandlers(server);
@@ -0,0 +1,11 @@
1
+ // This polyfill is required for open-graph generator to work
2
+ const fetch = require('node-fetch');
3
+
4
+ const { Headers, Request, Response } = fetch;
5
+
6
+ if (!global.fetch) {
7
+ global.fetch = fetch;
8
+ global.Headers = Headers;
9
+ global.Request = Request;
10
+ global.Response = Response;
11
+ }
@@ -0,0 +1,155 @@
1
+ // A simple open graph service based on satori and sharp
2
+ const fs = require('fs-extra');
3
+ const path = require('path');
4
+ const sharp = require('sharp');
5
+ const joinUrl = require('url-join');
6
+ const { Joi } = require('@arcblock/validator');
7
+ const stringify = require('json-stable-stringify');
8
+ const md5 = require('@abtnode/util/lib/md5');
9
+ const formatError = require('@abtnode/util/lib/format-error');
10
+ const { getPassportColor } = require('@abtnode/auth/lib/util/create-passport-svg');
11
+ const { WELLKNOWN_SERVICE_PATH_PREFIX } = require('@abtnode/constant');
12
+
13
+ const logger = require('@abtnode/logger')('@abtnode/blocklet-services/og');
14
+
15
+ const { getTemplate, getLogoSvg } = require('./template');
16
+
17
+ const TEMPLATES = ['default', 'section', 'cover'];
18
+
19
+ const schema = Joi.object({
20
+ template: Joi.string()
21
+ .lowercase()
22
+ .valid(...TEMPLATES)
23
+ .optional()
24
+ .default('default'),
25
+
26
+ title: Joi.string()
27
+ .max(128)
28
+ .when('template', {
29
+ is: 'default',
30
+ then: Joi.optional().default(''),
31
+ otherwise: Joi.required(),
32
+ }),
33
+
34
+ description: Joi.string()
35
+ .max(512)
36
+ .when('template', {
37
+ is: 'section',
38
+ then: Joi.required(),
39
+ otherwise: Joi.optional().default(''),
40
+ }),
41
+
42
+ section: Joi.string()
43
+ .max(64)
44
+ .when('template', {
45
+ is: 'section',
46
+ then: Joi.required(),
47
+ otherwise: Joi.optional().default(''),
48
+ }),
49
+
50
+ cover: Joi.string()
51
+ .uri({ scheme: ['https'] })
52
+ .when('template', {
53
+ is: 'cover',
54
+ then: Joi.required(),
55
+ otherwise: Joi.optional().default(''),
56
+ }),
57
+ }).options({ stripUnknown: true, allowUnknown: true, noDefaults: false });
58
+
59
+ const tasks = {};
60
+ const getOgImage = (input, info, dataDir, format) => {
61
+ if (fs.existsSync(dataDir) === false) {
62
+ fs.mkdirSync(dataDir, { recursive: true });
63
+ }
64
+
65
+ const color = getPassportColor(info.passportColor, info.did);
66
+ const logoUrl = joinUrl(info.appUrl, WELLKNOWN_SERVICE_PATH_PREFIX, '/blocklet/logo');
67
+ const { value, error } = schema.validate(input);
68
+ if (error) {
69
+ throw new Error(`open graph service params invalid: ${formatError(error)}`);
70
+ }
71
+ if (!value.title) {
72
+ value.title = info.name;
73
+ }
74
+ if (!value.description) {
75
+ value.description = info.description;
76
+ }
77
+ if (value.template === 'cover') {
78
+ value.description = value.title;
79
+ value.title = info.name;
80
+ }
81
+
82
+ const params = { ...value, width: 1200, height: 630, color, logoUrl, format };
83
+ const cacheKey = md5(stringify(params));
84
+ const nocache = input.nocache === '1';
85
+ const destPath = path.join(dataDir, `${cacheKey}.${format}`);
86
+ if (!nocache && fs.existsSync(destPath)) {
87
+ return destPath;
88
+ }
89
+
90
+ tasks[cacheKey] ??= generateOgImage(params).finally(() => {
91
+ setTimeout(() => {
92
+ delete tasks[cacheKey];
93
+ }, 1000);
94
+ });
95
+
96
+ return new Promise((resolve, reject) => {
97
+ tasks[cacheKey]
98
+ .then((buffer) => {
99
+ logger.info('open graph generate succeed', { params, destPath });
100
+ fs.writeFileSync(destPath, buffer);
101
+ resolve(destPath);
102
+ })
103
+ .catch((err) => {
104
+ logger.error('open graph generate failed', { error: err, params });
105
+ reject(err);
106
+ });
107
+ });
108
+ };
109
+
110
+ const fallbackFont = fs.readFile(path.resolve(__dirname, '../../fonts/noto-sans-sc-regular.otf'));
111
+ const generateOgImage = async (params) => {
112
+ const { default: satori } = await import('satori');
113
+ const raw = await getTemplate(params);
114
+ if (params.format === 'html') {
115
+ return raw;
116
+ }
117
+
118
+ const svg = await satori(raw, {
119
+ width: params.width,
120
+ height: params.height,
121
+ // debug: true,
122
+ fonts: [
123
+ {
124
+ name: 'Noto',
125
+ data: await fallbackFont,
126
+ weight: 400,
127
+ style: 'normal',
128
+ },
129
+ ],
130
+ });
131
+
132
+ if (params.format === 'svg') {
133
+ return svg;
134
+ }
135
+
136
+ if (['default', 'section'].includes(params.template)) {
137
+ return sharp(Buffer.from(getLogoSvg(params.color.start)))
138
+ .png()
139
+ .toBuffer()
140
+ .then((buffer) => {
141
+ return sharp(Buffer.from(svg))
142
+ .composite([{ input: buffer, top: 190, left: 816 }])
143
+ .png()
144
+ .toBuffer();
145
+ });
146
+ }
147
+
148
+ return sharp(Buffer.from(svg)).png().toBuffer();
149
+ };
150
+
151
+ module.exports = {
152
+ getOgImage,
153
+ generateOgImage,
154
+ TEMPLATES,
155
+ };
@@ -0,0 +1,212 @@
1
+ // Join the raw strings and values to reconstruct the original string
2
+ const join = (strings, ...values) => {
3
+ const original = strings.raw.reduce((result, str, i) => {
4
+ return result + str + (values[i] !== undefined ? values[i] : '');
5
+ }, '');
6
+
7
+ return original;
8
+ };
9
+
10
+ const getLogoSvg = (color) => {
11
+ return `<svg
12
+ xmlns="http://www.w3.org/2000/svg"
13
+ style="position: absolute; right: 24px; bottom: 24px; opacity: 0.1"
14
+ width="360"
15
+ height="416"
16
+ viewBox="0 0 45 52"
17
+ >
18
+ <g fill="none" fill-rule="evenodd" stroke="${color}">
19
+ <path
20
+ d="M.5 13.077L22.15.577l21.651 12.5v25l-21.65 12.5L.5 38.077zM22.15.577v50M.5 13.077l43.301 25m-43.301 0l43.301-25"
21
+ ></path>
22
+ <path d="M22.15 38.077l10.826-6.25-10.825-18.75-10.825 18.75z"></path>
23
+ </g>
24
+ </svg>`;
25
+ };
26
+
27
+ const getDefaultTemplate = ({ width, height, logoUrl, format, color, title, description }, fn) => {
28
+ return fn`<div
29
+ style="
30
+ width: ${width}px;
31
+ height: ${height}px;
32
+ background: linear-gradient(to bottom right, #000000 40%, ${color.start});
33
+ display: flex;
34
+ flex-direction: column;
35
+ justify-content: center;
36
+ align-items: flex-start;
37
+ position: relative;
38
+ "
39
+ >
40
+ <img
41
+ src="${logoUrl}"
42
+ height="120"
43
+ width="120"
44
+ style="margin-left: 96px; height: 120px; width: 120px; margin-bottom: 64px"
45
+ />
46
+ <h2
47
+ style="
48
+ font-size: 4.8rem;
49
+ letter-spacing: -2px;
50
+ margin: 32px 0;
51
+ color: #ddd;
52
+ font-weight: 400;
53
+ font-family: Arial, sans-serif;
54
+ text-align: left;
55
+ text-transform: capitalize;
56
+ padding: 0 96px;
57
+ "
58
+ >
59
+ ${title}
60
+ </h2>
61
+ <h3
62
+ style="
63
+ font-size: 2.4rem;
64
+ margin: 0;
65
+ color: #aaa;
66
+ font-weight: 400;
67
+ font-family: Arial, sans-serif;
68
+ text-align: left;
69
+ padding: 0 96px;
70
+ "
71
+ >
72
+ ${description}
73
+ </h3>
74
+ ${format !== 'png' ? getLogoSvg(color.start) : ''}
75
+ </div>`;
76
+ };
77
+
78
+ const getSectionTemplate = ({ width, height, logoUrl, color, format, title, description, section }, fn) => {
79
+ return fn` <div
80
+ style="
81
+ width: ${width};
82
+ height: ${height}px;
83
+ background: radial-gradient(circle at 83% 63%, ${color.start}, #000000 50%);
84
+ display: flex;
85
+ flex-direction: column;
86
+ justify-content: center;
87
+ align-items: flex-start;
88
+ position: relative;
89
+ "
90
+ >
91
+ <img
92
+ src="${logoUrl}"
93
+ height="90"
94
+ width="90"
95
+ style="margin-left: 96px; height: 90px; width: 90px; margin-bottom: 96px"
96
+ />
97
+ <p
98
+ style="
99
+ font-size: 1.8rem;
100
+ margin: 0;
101
+ color: ${color.start};
102
+ font-weight: 400;
103
+ font-family: Arial, sans-serif;
104
+ text-align: left;
105
+ padding: 0 96px;
106
+ "
107
+ >
108
+ ${section}
109
+ </p>
110
+ <h2
111
+ style="
112
+ font-size: 4.8rem;
113
+ margin: 32px 0;
114
+ color: #eee;
115
+ letter-spacing: -2px;
116
+ font-weight: 400;
117
+ font-family: Arial, sans-serif;
118
+ text-align: center;
119
+ text-transform: capitalize;
120
+ padding: 0 96px;
121
+ "
122
+ >
123
+ ${title}
124
+ </h2>
125
+ <h3
126
+ style="
127
+ font-size: 2.4rem;
128
+ margin: 0;
129
+ color: #bbb;
130
+ font-weight: 400;
131
+ font-family: Arial, sans-serif;
132
+ text-align: left;
133
+ padding: 0 96px;
134
+ "
135
+ >
136
+ ${description}
137
+ </h3>
138
+ ${format !== 'png' ? getLogoSvg(color.start) : ''}
139
+ </div>`;
140
+ };
141
+
142
+ const getCoverTemplate = ({ width, height, logoUrl, color, title, description, cover }, fn) => {
143
+ return fn`<div style="width: ${width}px; height: ${height}px; display: flex; background: ${color.start};">
144
+ <div style="display: flex; height: ${height}px; background: ${color.start}; width: 45%">
145
+ <div style="margin-left: 32px; display: flex; flex-direction: column; align-items: flex-start; justify-content: space-around;">
146
+ <h2
147
+ style="
148
+ font-size: 3.6rem;
149
+ color: #ddd;
150
+ font-weight: 400;
151
+ font-family: Arial, sans-serif;
152
+ margin: 32px 0 0;
153
+ text-align: left;
154
+ "
155
+ >
156
+ ${description}
157
+ </h2>
158
+ <div style="display: flex; justify-content: flex-start; align-items: center">
159
+ <img src="${logoUrl}" height="60" width="60" style="height: 60px; width: 60px" />
160
+ <h3
161
+ style="
162
+ font-size: 2rem;
163
+ margin: 0 0 0 16px;
164
+ color: #ddd;
165
+ font-weight: 400;
166
+ font-family: Arial, sans-serif;
167
+ text-align: left;
168
+ text-transform: capitalize;
169
+ "
170
+ >
171
+ ${title}
172
+ </h3>
173
+ </div>
174
+ </div>
175
+ </div>
176
+ <div style="display: flex; height: 630px; width: 55%; background-color: ${color.start}">
177
+ <img src="${cover}" height="630" width="100%" style="height: 630px; width: 100%; object-fit: cover" />
178
+ <div style="
179
+ display: flex;
180
+ background: ${color.start};
181
+ height: ${height * 2}px;
182
+ width: 125px;
183
+ position: absolute;
184
+ transform: rotate(10deg);
185
+ left: -120px;
186
+ top: -25px;"></div>
187
+ </div>
188
+ </div>`;
189
+ };
190
+
191
+ const getTemplate = async (params) => {
192
+ // eslint-disable-next-line import/no-unresolved
193
+ const { html } = await import('satori-html');
194
+ const fn = params.format === 'html' ? join : html;
195
+
196
+ if (params.template === 'default') {
197
+ return getDefaultTemplate(params, fn);
198
+ }
199
+ if (params.template === 'section') {
200
+ return getSectionTemplate(params, fn);
201
+ }
202
+ if (params.template === 'cover') {
203
+ return getCoverTemplate(params, fn);
204
+ }
205
+
206
+ throw new Error('Invalid open graph template');
207
+ };
208
+
209
+ module.exports = {
210
+ getTemplate,
211
+ getLogoSvg,
212
+ };
@@ -1,5 +1,5 @@
1
1
  /* eslint-disable no-console */
2
- const fs = require('fs');
2
+ const fs = require('fs-extra');
3
3
  const path = require('path');
4
4
  const cloneDeep = require('lodash/cloneDeep');
5
5
  const dayjs = require('@abtnode/util/lib/dayjs');
@@ -34,15 +34,17 @@ const {
34
34
  USER_AVATAR_PATH_PREFIX,
35
35
  ROLES,
36
36
  USER_AVATAR_URL_PREFIX,
37
+ OPEN_GRAPH_DIR,
37
38
  } = require('@abtnode/constant');
38
39
  const logger = require('@abtnode/logger')(require('../../package.json').name);
39
40
 
40
41
  const { createDownloadLogStream } = require('@abtnode/core/lib/util/log');
41
42
 
42
- const { BlockletStatus } = require('@blocklet/constant');
43
+ const { BlockletStatus, BlockletInternalEvents } = require('@blocklet/constant');
43
44
 
44
45
  const { checkAdminPermission } = require('../middlewares/check-permission');
45
46
  const { isImageAccepted, isImageRequest, processAndRespond } = require('../libs/image');
47
+ const { getOgImage } = require('../libs/open-graph');
46
48
 
47
49
  const polishBlocklet = (doc) => {
48
50
  const res = cloneDeep(doc);
@@ -53,7 +55,7 @@ const polishBlocklet = (doc) => {
53
55
  const prefix = WELLKNOWN_SERVICE_PATH_PREFIX;
54
56
 
55
57
  module.exports = {
56
- init(server, node) {
58
+ init(server, node, events) {
57
59
  const onSendFallbackLogo = ({ res, sendOptions }) => {
58
60
  res.sendStaticFile('/images/blocklet.png', sendOptions);
59
61
  };
@@ -114,8 +116,6 @@ module.exports = {
114
116
 
115
117
  const cacheDir = path.join(node.dataDirs.cache, 'services', 'image');
116
118
  server.get(`${prefix}${USER_AVATAR_PATH_PREFIX}/:fileName`, async (req, res) => {
117
- const sendOptions = { maxAge: '1y' };
118
-
119
119
  try {
120
120
  const blocklet = await req.getBlocklet();
121
121
  let { fileName } = req.params;
@@ -140,7 +140,7 @@ module.exports = {
140
140
  Promise.resolve([fs.createReadStream(avatarFile), path.extname(avatarFile).slice(1)])
141
141
  );
142
142
  } else {
143
- res.sendFile(avatarFile, sendOptions);
143
+ res.sendFile(avatarFile, { maxAge: '365d', immutable: true });
144
144
  }
145
145
  } catch (err) {
146
146
  logger.error('failed to send user avatar', { fileName: req.params.fileName, error: err });
@@ -465,5 +465,45 @@ module.exports = {
465
465
  ],
466
466
  });
467
467
  });
468
+
469
+ server.get(`${prefix}/blocklet/og.(png|html)`, async (req, res) => {
470
+ try {
471
+ const format = req.path.split('.').pop();
472
+ const info = await req.getBlockletInfo();
473
+ const blocklet = await req.getBlocklet();
474
+ const cache = req.query.nocache !== '1';
475
+
476
+ const dataDir = path.join(blocklet.env.dataDir, OPEN_GRAPH_DIR);
477
+ const sourceFile = await getOgImage(req.query, info, dataDir, format);
478
+ if (format === 'png' && isImageAccepted(req) && isImageRequest(req)) {
479
+ const appDir = path.join(cacheDir, blocklet.appPid);
480
+ processAndRespond(req, res, appDir, () =>
481
+ Promise.resolve([fs.createReadStream(sourceFile), path.extname(sourceFile).slice(1)])
482
+ );
483
+ } else {
484
+ res.sendFile(sourceFile, cache ? { maxAge: '365d', immutable: true } : { maxAge: 0 });
485
+ }
486
+ } catch (err) {
487
+ logger.error('failed to send open graph', { fileName: req.params.fileName, error: err });
488
+ res.status(500).send(err.message);
489
+ }
490
+ });
491
+ // Bust cache on blocklet config change
492
+ if (events) {
493
+ events.on(BlockletInternalEvents.appConfigChanged, ({ appDid }) => {
494
+ ['png', 'html'].forEach((format) => {
495
+ const cached = path.join(node.dataDirs.data, appDid, `og.${format}`);
496
+ if (fs.existsSync(cached)) {
497
+ logger.info('bust og cache on blocklet config change', { appDid, cached });
498
+ try {
499
+ fs.unlinkSync(cached);
500
+ logger.info('bust og cache on blocklet config change', { appDid, format });
501
+ } catch (err) {
502
+ logger.error('bust og cache on blocklet config change', { appDid, format, error: err });
503
+ }
504
+ }
505
+ });
506
+ });
507
+ }
468
508
  },
469
509
  };
@@ -1,16 +1,16 @@
1
1
  {
2
2
  "files": {
3
3
  "main.css": "/.well-known/service/static/static/css/main.7ea79dc8.css",
4
- "main.js": "/.well-known/service/static/static/js/main.1b821566.js",
4
+ "main.js": "/.well-known/service/static/static/js/main.e29a7133.js",
5
5
  "static/js/4716.58477c5c.chunk.js": "/.well-known/service/static/static/js/4716.58477c5c.chunk.js",
6
6
  "static/js/6856.163537c7.chunk.js": "/.well-known/service/static/static/js/6856.163537c7.chunk.js",
7
7
  "static/js/1660.e2ff5a21.chunk.js": "/.well-known/service/static/static/js/1660.e2ff5a21.chunk.js",
8
8
  "static/js/9899.18509ac9.chunk.js": "/.well-known/service/static/static/js/9899.18509ac9.chunk.js",
9
- "static/js/6737.5aef67e7.chunk.js": "/.well-known/service/static/static/js/6737.5aef67e7.chunk.js",
9
+ "static/js/6737.6432760e.chunk.js": "/.well-known/service/static/static/js/6737.6432760e.chunk.js",
10
10
  "static/js/1760.3318c7ca.chunk.js": "/.well-known/service/static/static/js/1760.3318c7ca.chunk.js",
11
11
  "static/js/9620.4b7c9e8b.chunk.js": "/.well-known/service/static/static/js/9620.4b7c9e8b.chunk.js",
12
12
  "static/js/1480.f89236fc.chunk.js": "/.well-known/service/static/static/js/1480.f89236fc.chunk.js",
13
- "static/js/6186.2a5f97da.chunk.js": "/.well-known/service/static/static/js/6186.2a5f97da.chunk.js",
13
+ "static/js/6186.e711ab85.chunk.js": "/.well-known/service/static/static/js/6186.e711ab85.chunk.js",
14
14
  "static/js/4682.23dd054e.chunk.js": "/.well-known/service/static/static/js/4682.23dd054e.chunk.js",
15
15
  "static/js/6711.38948be4.chunk.js": "/.well-known/service/static/static/js/6711.38948be4.chunk.js",
16
16
  "static/js/8437.0d88b9db.chunk.js": "/.well-known/service/static/static/js/8437.0d88b9db.chunk.js",
@@ -27,7 +27,7 @@
27
27
  "static/js/2653.58a5430b.chunk.js": "/.well-known/service/static/static/js/2653.58a5430b.chunk.js",
28
28
  "static/js/3593.98d9341a.chunk.js": "/.well-known/service/static/static/js/3593.98d9341a.chunk.js",
29
29
  "static/css/5355.c4fb5c4a.chunk.css": "/.well-known/service/static/static/css/5355.c4fb5c4a.chunk.css",
30
- "static/js/5355.4b07ad55.chunk.js": "/.well-known/service/static/static/js/5355.4b07ad55.chunk.js",
30
+ "static/js/5355.2eaad302.chunk.js": "/.well-known/service/static/static/js/5355.2eaad302.chunk.js",
31
31
  "static/js/6771.583c16c9.chunk.js": "/.well-known/service/static/static/js/6771.583c16c9.chunk.js",
32
32
  "static/css/5982.ac464505.chunk.css": "/.well-known/service/static/static/css/5982.ac464505.chunk.css",
33
33
  "static/js/5982.19c5663f.chunk.js": "/.well-known/service/static/static/js/5982.19c5663f.chunk.js",
@@ -73,7 +73,7 @@
73
73
  "static/js/9107.967c2ac1.chunk.js": "/.well-known/service/static/static/js/9107.967c2ac1.chunk.js",
74
74
  "static/css/3154.e954fcda.chunk.css": "/.well-known/service/static/static/css/3154.e954fcda.chunk.css",
75
75
  "static/js/9657.e974d577.chunk.js": "/.well-known/service/static/static/js/9657.e974d577.chunk.js",
76
- "static/js/5541.1d065ac6.chunk.js": "/.well-known/service/static/static/js/5541.1d065ac6.chunk.js",
76
+ "static/js/5541.581f1db7.chunk.js": "/.well-known/service/static/static/js/5541.581f1db7.chunk.js",
77
77
  "static/media/ubuntu-mono-all-400-normal.woff": "/.well-known/service/static/static/media/ubuntu-mono-all-400-normal.c879328bc62e9c68268f.woff",
78
78
  "service-worker.js": "/.well-known/service/static/service-worker.js",
79
79
  "static/media/lato-all-400-normal.woff": "/.well-known/service/static/static/media/lato-all-400-normal.3dc1eff492ab1f598560.woff",
@@ -98,16 +98,16 @@
98
98
  "index.html": "/.well-known/service/static/index.html",
99
99
  "static/media/space-connected.svg": "/.well-known/service/static/static/media/space-connected.9a4e18fd2bc7d065191b0d241a131c28.svg",
100
100
  "main.7ea79dc8.css.map": "/.well-known/service/static/static/css/main.7ea79dc8.css.map",
101
- "main.1b821566.js.map": "/.well-known/service/static/static/js/main.1b821566.js.map",
101
+ "main.e29a7133.js.map": "/.well-known/service/static/static/js/main.e29a7133.js.map",
102
102
  "4716.58477c5c.chunk.js.map": "/.well-known/service/static/static/js/4716.58477c5c.chunk.js.map",
103
103
  "6856.163537c7.chunk.js.map": "/.well-known/service/static/static/js/6856.163537c7.chunk.js.map",
104
104
  "1660.e2ff5a21.chunk.js.map": "/.well-known/service/static/static/js/1660.e2ff5a21.chunk.js.map",
105
105
  "9899.18509ac9.chunk.js.map": "/.well-known/service/static/static/js/9899.18509ac9.chunk.js.map",
106
- "6737.5aef67e7.chunk.js.map": "/.well-known/service/static/static/js/6737.5aef67e7.chunk.js.map",
106
+ "6737.6432760e.chunk.js.map": "/.well-known/service/static/static/js/6737.6432760e.chunk.js.map",
107
107
  "1760.3318c7ca.chunk.js.map": "/.well-known/service/static/static/js/1760.3318c7ca.chunk.js.map",
108
108
  "9620.4b7c9e8b.chunk.js.map": "/.well-known/service/static/static/js/9620.4b7c9e8b.chunk.js.map",
109
109
  "1480.f89236fc.chunk.js.map": "/.well-known/service/static/static/js/1480.f89236fc.chunk.js.map",
110
- "6186.2a5f97da.chunk.js.map": "/.well-known/service/static/static/js/6186.2a5f97da.chunk.js.map",
110
+ "6186.e711ab85.chunk.js.map": "/.well-known/service/static/static/js/6186.e711ab85.chunk.js.map",
111
111
  "4682.23dd054e.chunk.js.map": "/.well-known/service/static/static/js/4682.23dd054e.chunk.js.map",
112
112
  "6711.38948be4.chunk.js.map": "/.well-known/service/static/static/js/6711.38948be4.chunk.js.map",
113
113
  "8437.0d88b9db.chunk.js.map": "/.well-known/service/static/static/js/8437.0d88b9db.chunk.js.map",
@@ -124,7 +124,7 @@
124
124
  "2653.58a5430b.chunk.js.map": "/.well-known/service/static/static/js/2653.58a5430b.chunk.js.map",
125
125
  "3593.98d9341a.chunk.js.map": "/.well-known/service/static/static/js/3593.98d9341a.chunk.js.map",
126
126
  "5355.c4fb5c4a.chunk.css.map": "/.well-known/service/static/static/css/5355.c4fb5c4a.chunk.css.map",
127
- "5355.4b07ad55.chunk.js.map": "/.well-known/service/static/static/js/5355.4b07ad55.chunk.js.map",
127
+ "5355.2eaad302.chunk.js.map": "/.well-known/service/static/static/js/5355.2eaad302.chunk.js.map",
128
128
  "6771.583c16c9.chunk.js.map": "/.well-known/service/static/static/js/6771.583c16c9.chunk.js.map",
129
129
  "5982.ac464505.chunk.css.map": "/.well-known/service/static/static/css/5982.ac464505.chunk.css.map",
130
130
  "5982.19c5663f.chunk.js.map": "/.well-known/service/static/static/js/5982.19c5663f.chunk.js.map",
@@ -170,10 +170,10 @@
170
170
  "9107.967c2ac1.chunk.js.map": "/.well-known/service/static/static/js/9107.967c2ac1.chunk.js.map",
171
171
  "3154.e954fcda.chunk.css.map": "/.well-known/service/static/static/css/3154.e954fcda.chunk.css.map",
172
172
  "9657.e974d577.chunk.js.map": "/.well-known/service/static/static/js/9657.e974d577.chunk.js.map",
173
- "5541.1d065ac6.chunk.js.map": "/.well-known/service/static/static/js/5541.1d065ac6.chunk.js.map"
173
+ "5541.581f1db7.chunk.js.map": "/.well-known/service/static/static/js/5541.581f1db7.chunk.js.map"
174
174
  },
175
175
  "entrypoints": [
176
176
  "static/css/main.7ea79dc8.css",
177
- "static/js/main.1b821566.js"
177
+ "static/js/main.e29a7133.js"
178
178
  ]
179
179
  }
package/build/index.html CHANGED
@@ -1 +1 @@
1
- <!doctype html><html lang="en"><head><meta charset="utf-8"/><link rel="icon" href="/favicon.ico"/><meta name="viewport" content="width=device-width,initial-scale=1,maximum-scale=1,user-scalable=0"/><meta name="theme-color" content="#000000"/><title>Blocklet Service</title><link rel="manifest" href="/.well-known/service/manifest.json"/><script src="/.well-known/service/api/env"></script><script src="/__blocklet__.js"></script><script defer="defer" src="/.well-known/service/static/static/js/main.1b821566.js"></script><link href="/.well-known/service/static/static/css/main.7ea79dc8.css" rel="stylesheet"></head><body><noscript>You need to enable JavaScript to run this app.</noscript><div id="root"></div></body></html>
1
+ <!doctype html><html lang="en"><head><meta charset="utf-8"/><link rel="icon" href="/favicon.ico"/><meta name="viewport" content="width=device-width,initial-scale=1,maximum-scale=1,user-scalable=0"/><meta name="theme-color" content="#000000"/><title>Blocklet Service</title><link rel="manifest" href="/.well-known/service/manifest.json"/><script src="/.well-known/service/api/env"></script><script src="/__blocklet__.js"></script><script defer="defer" src="/.well-known/service/static/static/js/main.e29a7133.js"></script><link href="/.well-known/service/static/static/css/main.7ea79dc8.css" rel="stylesheet"></head><body><noscript>You need to enable JavaScript to run this app.</noscript><div id="root"></div></body></html>