blogger-plugin 0.0.2 → 0.0.4

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/dist/vite.cjs CHANGED
@@ -1,15 +1,78 @@
1
- "use strict";Object.defineProperty(exports, "__esModule", {value: true}); function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }// src/vite.ts
2
- var _fs = require('fs'); var _fs2 = _interopRequireDefault(_fs);
3
- var _path = require('path'); var _path2 = _interopRequireDefault(_path);
1
+ "use strict";Object.defineProperty(exports, "__esModule", {value: true}); function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) { newObj[key] = obj[key]; } } } newObj.default = obj; return newObj; } }// src/vite.ts
2
+ var _fs = require('fs'); var fs2 = _interopRequireWildcard(_fs); var fs = _interopRequireWildcard(_fs);
3
+ var _path = require('path'); var path2 = _interopRequireWildcard(_path); var path = _interopRequireWildcard(_path);
4
4
  var _stream = require('stream');
5
5
 
6
- // src/schema.ts
7
- var _zod = require('zod');
8
- var BloggerPluginOptionsSchema = _zod.z.object({
9
- entry: _zod.z.string().optional(),
10
- template: _zod.z.string().optional(),
11
- proxyBlog: _zod.z.url()
12
- }).strict();
6
+
7
+ var _vite = require('vite');
8
+
9
+ // src/cache.ts
10
+
11
+
12
+ var _tailwindcssiso = require('tailwindcss-iso');
13
+ var TAILWIND_CACHE_FILE = ".tailwind-classes.json";
14
+ function readFileContent(file) {
15
+ if (!fs.existsSync(file)) {
16
+ return null;
17
+ }
18
+ return fs.readFileSync(file, "utf-8");
19
+ }
20
+ function writeFileContent(file, content) {
21
+ const dirname2 = path.dirname(file);
22
+ if (!fs.existsSync(dirname2)) {
23
+ fs.mkdirSync(dirname2, { recursive: true });
24
+ }
25
+ const current = readFileContent(file);
26
+ if (current === null || content !== current) {
27
+ fs.writeFileSync(file, content, "utf8");
28
+ return true;
29
+ }
30
+ return false;
31
+ }
32
+ function removeFile(file) {
33
+ if (!fs.existsSync(file)) {
34
+ return false;
35
+ }
36
+ fs.rmSync(file);
37
+ return true;
38
+ }
39
+ function getTailwindCacheFile(root) {
40
+ return path.resolve(root, TAILWIND_CACHE_FILE);
41
+ }
42
+ function readTailwindCache(root) {
43
+ const content = readFileContent(getTailwindCacheFile(root));
44
+ if (!content) {
45
+ return null;
46
+ }
47
+ try {
48
+ return JSON.parse(content);
49
+ } catch (e) {
50
+ return null;
51
+ }
52
+ }
53
+ function writeTailwindCache(root, classes) {
54
+ const file = getTailwindCacheFile(root);
55
+ const content = JSON.stringify(classes, null, 2);
56
+ const updated = writeFileContent(file, content);
57
+ return { updated, content };
58
+ }
59
+ function clearTailwindCache(root) {
60
+ writeTailwindCache(root, []);
61
+ }
62
+ function removeTailwindCache(root) {
63
+ removeFile(getTailwindCacheFile(root));
64
+ }
65
+ async function updateTailwindCache(root, content) {
66
+ var _a;
67
+ const classes = await _tailwindcssiso.getTailwindClasses.call(void 0, {
68
+ content
69
+ });
70
+ writeTailwindCache(root, [.../* @__PURE__ */ new Set([...(_a = readTailwindCache(root)) != null ? _a : [], ...classes])]);
71
+ }
72
+
73
+ // src/constants.ts
74
+ var DEFAULT_ENTRIES = ["index.tsx", "index.ts", "index.jsx", "index.js", "main.tsx", "main.ts", "main.jsx", "main.js"];
75
+ var DEFAULT_TEMPLATES = ["template.xml", "theme.xml"];
13
76
 
14
77
  // src/utils.ts
15
78
  function escapeHtml(str) {
@@ -49,24 +112,20 @@ function toWebHeaders(httpHeaders) {
49
112
  }
50
113
  return headers;
51
114
  }
115
+ var BLOGGER_PLUGIN_HEAD_COMMENT_REGEX = /(<!--blogger-plugin:head:begin-->)([\s\S]*?)(<!--blogger-plugin:head:end-->)/;
116
+ var BLOGGER_PLUGIN_HEAD_BCOMMENT_REGEX = /(<b:comment><!--blogger-plugin:head:begin--><\/b:comment>)([\s\S]*?)(<b:comment><!--blogger-plugin:head:end--><\/b:comment>)/;
52
117
  function replaceBloggerPluginHeadComment(input, replacement, bcomment = false) {
53
118
  if (bcomment) {
54
- return input.replace(
55
- /<b:comment><!--blogger-plugin:head:begin--><\/b:comment>[\s\S]*?<b:comment><!--blogger-plugin:head:end--><\/b:comment>/,
56
- `<b:comment><!--blogger-plugin:head:begin--></b:comment>${replacement}<b:comment><!--blogger-plugin:head:end--></b:comment>`
57
- );
119
+ return input.replace(BLOGGER_PLUGIN_HEAD_BCOMMENT_REGEX, (_, start, _content, end) => `${start}${replacement}${end}`);
58
120
  }
59
- return input.replace(
60
- /<!--blogger-plugin:head:begin-->[\s\S]*?<!--blogger-plugin:head:end-->/,
61
- `<!--blogger-plugin:head:begin-->${replacement}<!--blogger-plugin:head:end-->`
62
- );
121
+ return input.replace(BLOGGER_PLUGIN_HEAD_COMMENT_REGEX, (_, start, _content, end) => `${start}${replacement}${end}`);
63
122
  }
64
123
  function getBloggerPluginHeadComment(input, bcomment = false) {
65
124
  var _a, _b, _c, _d;
66
125
  if (bcomment) {
67
- return (_b = (_a = input.match(/<b:comment><!--blogger-plugin:head:begin--><\/b:comment>([\s\S]*?)<b:comment><!--blogger-plugin:head:end--><\/b:comment>/)) == null ? void 0 : _a[1]) != null ? _b : null;
126
+ return (_b = (_a = input.match(BLOGGER_PLUGIN_HEAD_BCOMMENT_REGEX)) == null ? void 0 : _a[2]) != null ? _b : null;
68
127
  }
69
- return (_d = (_c = input.match(/<!--blogger-plugin:head:begin-->([\s\S]*?)<!--blogger-plugin:head:end-->/)) == null ? void 0 : _c[1]) != null ? _d : null;
128
+ return (_d = (_c = input.match(BLOGGER_PLUGIN_HEAD_COMMENT_REGEX)) == null ? void 0 : _c[2]) != null ? _d : null;
70
129
  }
71
130
  function replaceHost(input, oldHost, newHost, newProtocol) {
72
131
  return input.replace(
@@ -74,6 +133,21 @@ function replaceHost(input, oldHost, newHost, newProtocol) {
74
133
  (_, protocol, slash) => `${protocol ? newProtocol != null ? newProtocol : protocol : ""}${slash != null ? slash : ""}${newHost}`
75
134
  );
76
135
  }
136
+ function getRequestUrl(req) {
137
+ const xForwardedProtoHeader = req.headers["x-forwarded-proto"];
138
+ const xForwardedHostHeader = req.headers["x-forwarded-host"];
139
+ const hostHeader = req.headers.host;
140
+ const protocol = Array.isArray(xForwardedProtoHeader) ? xForwardedProtoHeader[0] : xForwardedProtoHeader != null ? xForwardedProtoHeader : req.socket && "encrypted" in req.socket && req.socket.encrypted ? "https" : "http";
141
+ const host = Array.isArray(xForwardedHostHeader) ? xForwardedHostHeader[0] : xForwardedHostHeader != null ? xForwardedHostHeader : hostHeader;
142
+ if (host && req.url) {
143
+ return new URL(`${protocol}://${host}${req.url}`);
144
+ }
145
+ return null;
146
+ }
147
+ var TAILWIND_PLUGIN_NAMES = /* @__PURE__ */ new Set(["@tailwindcss/vite:scan"]);
148
+ function isTailwindPlugin(plugin) {
149
+ return TAILWIND_PLUGIN_NAMES.has(plugin.name);
150
+ }
77
151
  function errorHtml(reqUrl) {
78
152
  return `<!DOCTYPE html>
79
153
  <html>
@@ -179,14 +253,94 @@ function errorHtml(reqUrl) {
179
253
  }
180
254
 
181
255
  // src/vite.ts
182
- var DEFAULT_ENTRIES = ["index.tsx", "index.ts", "index.jsx", "index.js", "main.tsx", "main.ts", "main.jsx", "main.js"];
183
- var DEFAULT_TEMPLATES = ["template.xml", "theme.xml"];
184
- function createPluginContext(userOptions) {
256
+ function createBloggerPluginContext(userOptions) {
257
+ if (typeof userOptions.entry !== "undefined" && typeof userOptions.entry !== "string") {
258
+ throw new Error("Option 'entry' must be a string");
259
+ }
260
+ if (typeof userOptions.template !== "undefined" && typeof userOptions.template !== "string") {
261
+ throw new Error("Option 'template' must be a string");
262
+ }
263
+ if (typeof userOptions.proxyBlog !== "string") {
264
+ throw new Error("Option 'proxyBlog' must be a string");
265
+ }
266
+ let proxyBlog;
267
+ try {
268
+ proxyBlog = new URL(userOptions.proxyBlog);
269
+ } catch (e) {
270
+ throw new Error("Option 'proxyBlog' must be a valid url");
271
+ }
185
272
  return {
186
- viteConfig: void 0,
273
+ root: process.cwd(),
187
274
  entry: void 0,
188
275
  template: void 0,
189
- options: BloggerPluginOptionsSchema.parse(userOptions)
276
+ proxyBlog,
277
+ viteConfig: void 0,
278
+ tailwind: false,
279
+ input: void 0,
280
+ html: void 0,
281
+ resolve(config) {
282
+ this.root = config.root ? path2.resolve(config.root) : this.root;
283
+ if (userOptions.entry) {
284
+ const providedPath = path2.resolve(this.root, userOptions.entry);
285
+ if (fs2.existsSync(providedPath)) {
286
+ this.entry = providedPath;
287
+ } else {
288
+ throw new Error(`Provided entry file does not exist: ${providedPath}`);
289
+ }
290
+ } else {
291
+ for (const file of DEFAULT_ENTRIES) {
292
+ const fullPath = path2.resolve(this.root, "src", file);
293
+ if (fs2.existsSync(fullPath)) {
294
+ this.entry = fullPath;
295
+ break;
296
+ }
297
+ }
298
+ if (!this.entry) {
299
+ throw new Error(
300
+ `No entry file found in "src".
301
+ Tried: ${DEFAULT_ENTRIES.map((c) => path2.join("src", c)).join(", ")}
302
+ \u{1F449} Tip: You can pass a custom entry like:
303
+ blogger({ entry: "src/my-entry.ts" })`
304
+ );
305
+ }
306
+ }
307
+ if (userOptions.template) {
308
+ const providedPath = path2.resolve(this.root, userOptions.template);
309
+ if (fs2.existsSync(providedPath)) {
310
+ this.template = providedPath;
311
+ } else {
312
+ throw new Error(`Provided template file does not exist: ${providedPath}`);
313
+ }
314
+ } else {
315
+ for (const file of DEFAULT_TEMPLATES) {
316
+ const fullPath = path2.resolve(this.root, "src", file);
317
+ if (fs2.existsSync(fullPath)) {
318
+ this.template = fullPath;
319
+ break;
320
+ }
321
+ }
322
+ if (!this.template) {
323
+ throw new Error(
324
+ `No template file found in "src".
325
+ Tried: ${DEFAULT_TEMPLATES.map((c) => path2.join("src", c)).join(", ")}
326
+ \u{1F449} Tip: You can pass a custom template like:
327
+ blogger({ template: "src/my-template.xml" })`
328
+ );
329
+ }
330
+ }
331
+ const name = path2.basename(this.entry, path2.extname(this.entry));
332
+ this.input = `virtual:blogger-plugin/${name}.html`;
333
+ this.html = `<!DOCTYPE html>
334
+ <html>
335
+ <head>
336
+ <!--head-->
337
+ <script type="module" src="/${path2.relative(this.root, this.entry).replace("\\", "/")}"></script>
338
+ </head>
339
+ <body>
340
+ <!--body-->
341
+ </body>
342
+ </html>`;
343
+ }
190
344
  };
191
345
  }
192
346
  function isViteDevServer(server) {
@@ -197,17 +351,18 @@ function useServerMiddleware(server, ctx, _this) {
197
351
  var _a;
198
352
  (_a = server.httpServer) == null ? void 0 : _a.once("listening", () => {
199
353
  setTimeout(() => {
200
- _this.info(`Unhandled requests will be proxied to ${ctx.options.proxyBlog}`);
354
+ _this.info(`Unhandled requests will be proxied to ${ctx.proxyBlog.origin}`);
201
355
  }, 0);
202
356
  });
203
357
  server.middlewares.use(async (req, res, next) => {
204
358
  var _a2;
205
- if (!req.url || !req.originalUrl) {
359
+ const url = getRequestUrl(req);
360
+ if (!req.url || !req.originalUrl || !url) {
206
361
  next();
207
362
  return;
208
363
  }
209
364
  const start = Date.now();
210
- const proxyUrl = new URL(req.originalUrl, ctx.options.proxyBlog);
365
+ const proxyUrl = new URL(`${ctx.proxyBlog.origin}${req.originalUrl}`);
211
366
  const viewParam = proxyUrl.searchParams.get("view");
212
367
  proxyUrl.searchParams.set("view", `${isViteDevServer(server) ? "-DevServer" : "-PreviewServer"}${(viewParam == null ? void 0 : viewParam.startsWith("-")) ? viewParam : ""}`);
213
368
  const proxyRequest = new Request(proxyUrl, {
@@ -229,28 +384,24 @@ function useServerMiddleware(server, ctx, _this) {
229
384
  return null;
230
385
  });
231
386
  if (proxyResponse) {
232
- const requestProtocol = `${req.headers["x-forwarded-proto"] || (req.socket && "encrypted" in req.socket && req.socket.encrypted ? "https" : "http")}:`;
233
- const requestHost = req.headers["x-forwarded-host"] || req.headers.host;
234
387
  res.statusCode = proxyResponse.status;
235
388
  res.statusMessage = proxyResponse.statusText;
236
389
  proxyResponse.headers.forEach((value, key) => {
237
390
  var _a3;
238
391
  if (key === "location") {
239
- const redirectUrl = new URL(value, requestHost ? `${requestProtocol}//${requestHost}${req.originalUrl}` : proxyUrl.href);
240
- if (requestHost && redirectUrl.host === requestHost || redirectUrl.host === proxyUrl.host) {
241
- if (requestHost && requestProtocol) {
242
- redirectUrl.host = requestHost;
243
- redirectUrl.protocol = requestProtocol;
244
- }
392
+ const redirectUrl = new URL(value, proxyUrl);
393
+ if (redirectUrl.host === url.host || redirectUrl.host === proxyUrl.host) {
394
+ redirectUrl.host = url.host;
395
+ redirectUrl.protocol = url.protocol;
245
396
  const viewParam2 = (_a3 = redirectUrl.searchParams.get("view")) == null ? void 0 : _a3.replaceAll("-DevServer", "").replaceAll("-PreviewServer", "");
246
397
  if (viewParam2) {
247
398
  redirectUrl.searchParams.set("view", viewParam2);
248
399
  } else {
249
400
  redirectUrl.searchParams.delete("view");
250
401
  }
251
- res.setHeader(key, redirectUrl.pathname + redirectUrl.search + redirectUrl.hash);
402
+ res.setHeader("location", redirectUrl.pathname + redirectUrl.search + redirectUrl.hash);
252
403
  } else {
253
- res.setHeader(key, redirectUrl.href);
404
+ res.setHeader("location", redirectUrl.href);
254
405
  }
255
406
  } else if (["content-type", "x-robots-tag", "date", "location"].includes(key)) {
256
407
  res.setHeader(key, value);
@@ -259,12 +410,13 @@ function useServerMiddleware(server, ctx, _this) {
259
410
  const contentType = proxyResponse.headers.get("content-type");
260
411
  if (contentType == null ? void 0 : contentType.startsWith("text/html")) {
261
412
  let htmlTemplateContent = await proxyResponse.text();
262
- if (requestHost && requestProtocol) {
263
- htmlTemplateContent = replaceHost(htmlTemplateContent, proxyUrl.host, requestHost, requestProtocol);
413
+ if (ctx.tailwind && isViteDevServer(server)) {
414
+ await updateTailwindCache(ctx.root, htmlTemplateContent);
264
415
  }
416
+ htmlTemplateContent = replaceHost(htmlTemplateContent, proxyUrl.host, url.host, url.protocol);
265
417
  if (isViteDevServer(server)) {
266
418
  const htmlTags = [];
267
- htmlTags.push(`<script src='/${escapeHtml(_path2.default.relative(ctx.viteConfig.root, ctx.entry))}' type='module'></script>`);
419
+ htmlTags.push(`<script type='module' src='/${escapeHtml(path2.relative(ctx.root, ctx.entry).replace("\\", "/"))}'></script>`);
268
420
  const template = await server.transformIndexHtml(
269
421
  req.url,
270
422
  replaceBloggerPluginHeadComment(htmlTemplateContent, htmlTags.join("")),
@@ -272,14 +424,14 @@ function useServerMiddleware(server, ctx, _this) {
272
424
  );
273
425
  res.end(template);
274
426
  } else {
275
- const xmlTemplateContent = _fs2.default.readFileSync(_path2.default.resolve(ctx.viteConfig.build.outDir, "template.xml"), "utf8");
427
+ const xmlTemplateContent = fs2.readFileSync(path2.resolve(ctx.viteConfig.build.outDir, "template.xml"), "utf8");
276
428
  const htmlTagsStr = getBloggerPluginHeadComment(xmlTemplateContent, true);
277
429
  const template = replaceBloggerPluginHeadComment(htmlTemplateContent, htmlTagsStr != null ? htmlTagsStr : "");
278
430
  res.end(template);
279
431
  }
280
- } else if (requestHost && requestProtocol && contentType && /^(text\/)|(application\/(.*\+)?(xml|json))/.test(contentType)) {
432
+ } else if (contentType && /^(text\/)|(application\/(.*\+)?(xml|json))/.test(contentType)) {
281
433
  const content = await proxyResponse.text();
282
- res.end(replaceHost(content, proxyUrl.host, requestHost, requestProtocol));
434
+ res.end(replaceHost(content, proxyUrl.host, url.host, url.protocol));
283
435
  } else {
284
436
  res.end(new Uint8Array(await proxyResponse.arrayBuffer()));
285
437
  }
@@ -295,94 +447,103 @@ function useServerMiddleware(server, ctx, _this) {
295
447
  };
296
448
  }
297
449
  function blogger(userOptions) {
298
- const ctx = createPluginContext(userOptions);
450
+ const ctx = createBloggerPluginContext(userOptions);
299
451
  return {
300
452
  name: "vite-plugin-blogger",
301
453
  config(config) {
302
- var _a, _b, _c;
303
- const root = config.root || process.cwd();
304
- let entry;
305
- let template;
306
- if (ctx.options.entry) {
307
- const providedPath = _path2.default.resolve(root, ctx.options.entry);
308
- if (_fs2.default.existsSync(providedPath)) {
309
- entry = providedPath;
310
- } else {
311
- this.error(`Provided entry file does not exist: ${providedPath}`);
312
- }
454
+ var _a;
455
+ ctx.resolve(config);
456
+ config.build || (config.build = {});
457
+ const major = Number(_vite.version.split(".")[0]);
458
+ const bundlerKey = major >= 8 ? "rolldownOptions" : "rollupOptions";
459
+ (_a = config.build)[bundlerKey] || (_a[bundlerKey] = {});
460
+ const bundlerOptions = config.build[bundlerKey];
461
+ if (Array.isArray(bundlerOptions.input)) {
462
+ bundlerOptions.input = [...bundlerOptions.input, ctx.input];
463
+ } else if (typeof bundlerOptions.input === "object" && bundlerOptions.input !== null) {
464
+ bundlerOptions.input[ctx.input] = ctx.input;
313
465
  } else {
314
- for (const file of DEFAULT_ENTRIES) {
315
- const fullPath = _path2.default.resolve(root, "src", file);
316
- if (_fs2.default.existsSync(fullPath)) {
317
- entry = fullPath;
318
- break;
319
- }
320
- }
321
- if (!entry) {
322
- this.error(
323
- `No entry file found in "src".
324
- Tried: ${DEFAULT_ENTRIES.map((c) => _path2.default.join("src", c)).join(", ")}
325
- \u{1F449} Tip: You can pass a custom entry like:
326
- blogger({ entry: "src/my-entry.ts" })`
327
- );
328
- }
466
+ bundlerOptions.input = ctx.input;
329
467
  }
330
- if (ctx.options.template) {
331
- const providedPath = _path2.default.resolve(root, ctx.options.template);
332
- if (_fs2.default.existsSync(providedPath)) {
333
- template = providedPath;
334
- } else {
335
- this.error(`Provided template file does not exist: ${providedPath}`);
468
+ const originalTemplateXmlContent = fs2.readFileSync(ctx.template, "utf8");
469
+ const modifiedTemplateXmlContent = replaceBloggerPluginHeadComment(replaceBloggerPluginHeadComment(originalTemplateXmlContent, ""), "", true);
470
+ fs2.writeFileSync(ctx.template, modifiedTemplateXmlContent, "utf-8");
471
+ },
472
+ configResolved(config) {
473
+ ctx.viteConfig = config;
474
+ ctx.tailwind = config.plugins.flat(Number.POSITIVE_INFINITY).some((plugin) => isTailwindPlugin(plugin));
475
+ if (ctx.tailwind) {
476
+ clearTailwindCache(ctx.root);
477
+ if (config.command === "build") {
478
+ updateTailwindCache(ctx.root, fs2.readFileSync(ctx.template, "utf-8"));
336
479
  }
337
480
  } else {
338
- for (const file of DEFAULT_TEMPLATES) {
339
- const fullPath = _path2.default.resolve(root, "src", file);
340
- if (_fs2.default.existsSync(fullPath)) {
341
- template = fullPath;
342
- break;
343
- }
344
- }
345
- if (!template) {
346
- this.error(
347
- `No template file found in "src".
348
- Tried: ${DEFAULT_TEMPLATES.map((c) => _path2.default.join("src", c)).join(", ")}
349
- \u{1F449} Tip: You can pass a custom template like:
350
- blogger({ template: "src/my-template.xml" })`
351
- );
352
- }
481
+ removeTailwindCache(ctx.root);
353
482
  }
354
- ctx.entry = entry;
355
- ctx.template = template;
356
- (_a = config.build) != null ? _a : config.build = {};
357
- (_c = (_b = config.build).rollupOptions) != null ? _c : _b.rollupOptions = {};
358
- config.build.rollupOptions.input = entry;
359
- const xmlTemplateContent = _fs2.default.readFileSync(ctx.template, "utf8");
360
- _fs2.default.writeFileSync(ctx.template, replaceBloggerPluginHeadComment(replaceBloggerPluginHeadComment(xmlTemplateContent, ""), "", true), {
361
- encoding: "utf8"
362
- });
363
483
  },
364
- configResolved(config) {
365
- ctx.viteConfig = config;
484
+ resolveId(source) {
485
+ if (source === ctx.input) {
486
+ return ctx.input;
487
+ }
366
488
  },
367
- generateBundle(_options, bundle) {
368
- var _a;
369
- for (const output of Object.values(bundle)) {
370
- if (output.type !== "chunk" || !output.isEntry) {
371
- continue;
372
- }
373
- const xmlTemplateContent = _fs2.default.readFileSync(ctx.template, "utf8");
374
- const htmlTags = [];
375
- (_a = output.viteMetadata) == null ? void 0 : _a.importedCss.forEach((value) => {
376
- htmlTags.push(`<link crossorigin='anonymous' href='${escapeHtml(ctx.viteConfig.base + value)}' rel='stylesheet'/>`);
377
- });
378
- htmlTags.push(`<script crossorigin='anonymous' src='${escapeHtml(ctx.viteConfig.base + output.fileName)}' type='module'></script>`);
379
- const template = replaceBloggerPluginHeadComment(xmlTemplateContent, htmlTags.join(""), true);
380
- this.emitFile({
381
- type: "asset",
382
- fileName: "template.xml",
383
- source: template
384
- });
385
- break;
489
+ load(id) {
490
+ if (id === ctx.input) {
491
+ return ctx.html;
492
+ }
493
+ },
494
+ writeBundle(_, bundle) {
495
+ if (!(ctx.input in bundle)) {
496
+ return;
497
+ }
498
+ const asset = bundle[ctx.input];
499
+ delete bundle[ctx.input];
500
+ if (asset.type !== "asset" || typeof asset.source !== "string") {
501
+ return;
502
+ }
503
+ const regex = /<!DOCTYPE html>\s*<html[^>]*>\s*<head>([\s\S]*?)<!--head-->([\s\S]*?)<\/head>\s*<body>([\s\S]*?)<!--body-->([\s\S]*?)<\/body>\s*<\/html>/i;
504
+ const match = asset.source.match(regex);
505
+ if (!match) {
506
+ return;
507
+ }
508
+ const afterHeadBegin = match[1];
509
+ const beforeHeadEnd = match[2];
510
+ const afterBodyBegin = match[3];
511
+ const beforeBodyEnd = match[4];
512
+ const headContent = (afterHeadBegin + beforeHeadEnd).replace(/\b(crossorigin|defer|async|disabled|checked)\b(?!=)/g, (_2, $1) => `${$1}=""`).replace(/(\w+)=(".*?"|'.*?')/g, (_2, $1, $2) => {
513
+ const v = $2.slice(1, -1).replace(/&/g, "&amp;").replace(/'/g, "&apos;").replace(/"/g, "&quot;").replace(/</g, "&lt;").replace(/>/g, "&gt;");
514
+ return `${$1}='${v}'`;
515
+ }).replace(/<(link|meta|img|br|hr|input)([^>]*?)>/gi, (_2, $1, $2) => `<${$1}${$2} />`).replace(/>\s+</g, "><").trim();
516
+ const originalTemplateXmlContent = fs2.readFileSync(ctx.template, "utf8");
517
+ const modifiedTemplateXmlContent = replaceBloggerPluginHeadComment(originalTemplateXmlContent, headContent, true);
518
+ const templateTagsXmlContent = `<?xml version="1.0" encoding="UTF-8" ?>
519
+ <!DOCTYPE html>
520
+ <html>
521
+ <head>
522
+ <!--head:afterbegin:begin-->
523
+
524
+ <!--head:afterbegin:end-->
525
+
526
+ <!--head:beforeend:begin-->
527
+ ${headContent}
528
+ <!--head:beforeend:end-->
529
+ </head>
530
+ <body>
531
+ <!--body:afterbegin:begin-->
532
+ ${afterBodyBegin.trim()}
533
+ <!--body:afterbegin:end-->
534
+
535
+ <!--body:beforeend:begin-->
536
+ ${beforeBodyEnd.trim()}
537
+ <!--body:beforeend:end-->
538
+ </body>
539
+ </html>`;
540
+ fs2.writeFileSync(path2.resolve(ctx.viteConfig.build.outDir, "template.xml"), modifiedTemplateXmlContent);
541
+ fs2.writeFileSync(path2.resolve(ctx.viteConfig.build.outDir, "template-tags.xml"), templateTagsXmlContent);
542
+ },
543
+ closeBundle() {
544
+ const htmlDir = path2.resolve(ctx.viteConfig.build.outDir, "virtual:blogger-plugin");
545
+ if (fs2.existsSync(htmlDir)) {
546
+ fs2.rmSync(htmlDir, { recursive: true });
386
547
  }
387
548
  },
388
549
  configureServer(server) {