@skrillex1224/chrome-article-publish-extension 1.0.0
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/README.md +226 -0
- package/dist/adapters/index.d.ts +1125 -0
- package/dist/adapters/index.js +1900 -0
- package/dist/adapters/index.js.map +1 -0
- package/dist/chunk-7Q3KKWUB.js +602 -0
- package/dist/chunk-7Q3KKWUB.js.map +1 -0
- package/dist/chunk-IUAZAMKF.js +123 -0
- package/dist/chunk-IUAZAMKF.js.map +1 -0
- package/dist/chunk-QM2T4VGM.js +6688 -0
- package/dist/chunk-QM2T4VGM.js.map +1 -0
- package/dist/chunk-UO6CDRC5.js +322 -0
- package/dist/chunk-UO6CDRC5.js.map +1 -0
- package/dist/converter/index.d.ts +2 -0
- package/dist/converter/index.html +10 -0
- package/dist/converter/index.js +432 -0
- package/dist/converter/index.js.map +1 -0
- package/dist/index.d.ts +43 -0
- package/dist/index.js +192 -0
- package/dist/index.js.map +1 -0
- package/dist/interface-BlLeWXzS.d.ts +265 -0
- package/dist/preprocessor/index.html +10 -0
- package/dist/runtime/index.d.ts +90 -0
- package/dist/runtime/index.js +9 -0
- package/dist/runtime/index.js.map +1 -0
- package/dist/types-BAnNlLpy.d.ts +140 -0
- package/package.json +54 -0
|
@@ -0,0 +1,602 @@
|
|
|
1
|
+
// src/lib/logger.ts
|
|
2
|
+
var LOG_LEVELS = {
|
|
3
|
+
debug: 0,
|
|
4
|
+
info: 1,
|
|
5
|
+
warn: 2,
|
|
6
|
+
error: 3
|
|
7
|
+
};
|
|
8
|
+
var isProd = typeof import.meta !== "undefined" && import.meta.env?.PROD || typeof process !== "undefined" && process.env?.NODE_ENV === "production";
|
|
9
|
+
var globalConfig = {
|
|
10
|
+
enabled: true,
|
|
11
|
+
level: isProd ? "warn" : "debug"
|
|
12
|
+
};
|
|
13
|
+
function createLogger(prefix) {
|
|
14
|
+
const shouldLog = (level) => {
|
|
15
|
+
if (!globalConfig.enabled) return false;
|
|
16
|
+
return LOG_LEVELS[level] >= LOG_LEVELS[globalConfig.level];
|
|
17
|
+
};
|
|
18
|
+
return {
|
|
19
|
+
debug: (...args) => {
|
|
20
|
+
if (shouldLog("debug")) {
|
|
21
|
+
console.log(`[${prefix}]`, ...args);
|
|
22
|
+
}
|
|
23
|
+
},
|
|
24
|
+
info: (...args) => {
|
|
25
|
+
if (shouldLog("info")) {
|
|
26
|
+
console.log(`[${prefix}]`, ...args);
|
|
27
|
+
}
|
|
28
|
+
},
|
|
29
|
+
warn: (...args) => {
|
|
30
|
+
if (shouldLog("warn")) {
|
|
31
|
+
console.warn(`[${prefix}]`, ...args);
|
|
32
|
+
}
|
|
33
|
+
},
|
|
34
|
+
error: (...args) => {
|
|
35
|
+
if (shouldLog("error")) {
|
|
36
|
+
console.error(`[${prefix}]`, ...args);
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
};
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
// src/lib/markdown-images.ts
|
|
43
|
+
function parseMarkdownImages(markdown) {
|
|
44
|
+
const results = [];
|
|
45
|
+
const len = markdown.length;
|
|
46
|
+
let i = 0;
|
|
47
|
+
const findClosingBracket = (start) => {
|
|
48
|
+
for (let j = start; j < len; j++) {
|
|
49
|
+
const ch = markdown[j];
|
|
50
|
+
if (ch === "\\") {
|
|
51
|
+
j++;
|
|
52
|
+
continue;
|
|
53
|
+
}
|
|
54
|
+
if (ch === "]") return j;
|
|
55
|
+
}
|
|
56
|
+
return -1;
|
|
57
|
+
};
|
|
58
|
+
while (i < len) {
|
|
59
|
+
const start = markdown.indexOf("![", i);
|
|
60
|
+
if (start === -1) break;
|
|
61
|
+
const altStart = start + 2;
|
|
62
|
+
const altEnd = findClosingBracket(altStart);
|
|
63
|
+
if (altEnd === -1 || markdown[altEnd + 1] !== "(") {
|
|
64
|
+
i = altStart;
|
|
65
|
+
continue;
|
|
66
|
+
}
|
|
67
|
+
let k = altEnd + 2;
|
|
68
|
+
while (k < len && /\s/.test(markdown[k])) k++;
|
|
69
|
+
let url = "";
|
|
70
|
+
if (markdown[k] === "<") {
|
|
71
|
+
const close = markdown.indexOf(">", k + 1);
|
|
72
|
+
if (close === -1) {
|
|
73
|
+
i = altEnd + 1;
|
|
74
|
+
continue;
|
|
75
|
+
}
|
|
76
|
+
url = markdown.slice(k + 1, close);
|
|
77
|
+
k = close + 1;
|
|
78
|
+
} else {
|
|
79
|
+
const urlStart = k;
|
|
80
|
+
let depth = 0;
|
|
81
|
+
while (k < len) {
|
|
82
|
+
const ch = markdown[k];
|
|
83
|
+
if (ch === "\\") {
|
|
84
|
+
k += 2;
|
|
85
|
+
continue;
|
|
86
|
+
}
|
|
87
|
+
if (ch === "(") {
|
|
88
|
+
depth++;
|
|
89
|
+
} else if (ch === ")") {
|
|
90
|
+
if (depth === 0) break;
|
|
91
|
+
depth--;
|
|
92
|
+
} else if (/\s/.test(ch) && depth === 0) {
|
|
93
|
+
break;
|
|
94
|
+
}
|
|
95
|
+
k++;
|
|
96
|
+
}
|
|
97
|
+
url = markdown.slice(urlStart, k);
|
|
98
|
+
}
|
|
99
|
+
if (!url) {
|
|
100
|
+
i = altEnd + 1;
|
|
101
|
+
continue;
|
|
102
|
+
}
|
|
103
|
+
while (k < len && /\s/.test(markdown[k])) k++;
|
|
104
|
+
if (k < len && (markdown[k] === '"' || markdown[k] === "'")) {
|
|
105
|
+
const quote = markdown[k];
|
|
106
|
+
k++;
|
|
107
|
+
while (k < len) {
|
|
108
|
+
const ch = markdown[k];
|
|
109
|
+
if (ch === "\\") {
|
|
110
|
+
k += 2;
|
|
111
|
+
continue;
|
|
112
|
+
}
|
|
113
|
+
if (ch === quote) {
|
|
114
|
+
k++;
|
|
115
|
+
break;
|
|
116
|
+
}
|
|
117
|
+
k++;
|
|
118
|
+
}
|
|
119
|
+
while (k < len && /\s/.test(markdown[k])) k++;
|
|
120
|
+
} else if (k < len && markdown[k] === "(") {
|
|
121
|
+
k++;
|
|
122
|
+
while (k < len) {
|
|
123
|
+
const ch = markdown[k];
|
|
124
|
+
if (ch === "\\") {
|
|
125
|
+
k += 2;
|
|
126
|
+
continue;
|
|
127
|
+
}
|
|
128
|
+
if (ch === ")") {
|
|
129
|
+
k++;
|
|
130
|
+
break;
|
|
131
|
+
}
|
|
132
|
+
k++;
|
|
133
|
+
}
|
|
134
|
+
while (k < len && /\s/.test(markdown[k])) k++;
|
|
135
|
+
}
|
|
136
|
+
if (markdown[k] !== ")") {
|
|
137
|
+
i = altEnd + 1;
|
|
138
|
+
continue;
|
|
139
|
+
}
|
|
140
|
+
const full = markdown.slice(start, k + 1);
|
|
141
|
+
const alt = markdown.slice(altStart, altEnd);
|
|
142
|
+
results.push({ full, alt, src: url });
|
|
143
|
+
i = k + 1;
|
|
144
|
+
}
|
|
145
|
+
return results;
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
// src/lib/turndown.ts
|
|
149
|
+
import TurndownService from "turndown";
|
|
150
|
+
import { marked } from "marked";
|
|
151
|
+
var logger = createLogger("Turndown");
|
|
152
|
+
function decodeHtmlEntities(text) {
|
|
153
|
+
let result = text;
|
|
154
|
+
for (let i = 0; i < 3; i++) {
|
|
155
|
+
const prev = result;
|
|
156
|
+
result = result.replace(/&/g, "&");
|
|
157
|
+
if (prev === result) break;
|
|
158
|
+
}
|
|
159
|
+
result = result.replace(/&#[xX]([0-9a-fA-F]+);/g, (_, hex) => {
|
|
160
|
+
return String.fromCharCode(parseInt(hex, 16));
|
|
161
|
+
});
|
|
162
|
+
result = result.replace(/&#(\d+);/g, (_, dec) => {
|
|
163
|
+
return String.fromCharCode(parseInt(dec, 10));
|
|
164
|
+
});
|
|
165
|
+
const namedEntities = {
|
|
166
|
+
"<": "<",
|
|
167
|
+
">": ">",
|
|
168
|
+
"&": "&",
|
|
169
|
+
""": '"',
|
|
170
|
+
"'": "'",
|
|
171
|
+
"'": "'",
|
|
172
|
+
" ": " ",
|
|
173
|
+
"–": "\u2013",
|
|
174
|
+
"—": "\u2014",
|
|
175
|
+
"‘": "\u2018",
|
|
176
|
+
"’": "\u2019",
|
|
177
|
+
"“": "\u201C",
|
|
178
|
+
"”": "\u201D",
|
|
179
|
+
"©": "\xA9",
|
|
180
|
+
"®": "\xAE",
|
|
181
|
+
"™": "\u2122",
|
|
182
|
+
"…": "\u2026"
|
|
183
|
+
};
|
|
184
|
+
for (const [entity, char] of Object.entries(namedEntities)) {
|
|
185
|
+
result = result.split(entity).join(char);
|
|
186
|
+
}
|
|
187
|
+
return result;
|
|
188
|
+
}
|
|
189
|
+
var KNOWN_HTML_TAGS = [
|
|
190
|
+
// 文本格式化
|
|
191
|
+
"span",
|
|
192
|
+
"em",
|
|
193
|
+
"strong",
|
|
194
|
+
"b",
|
|
195
|
+
"i",
|
|
196
|
+
"u",
|
|
197
|
+
"s",
|
|
198
|
+
"strike",
|
|
199
|
+
"del",
|
|
200
|
+
"ins",
|
|
201
|
+
"mark",
|
|
202
|
+
"sub",
|
|
203
|
+
"sup",
|
|
204
|
+
"small",
|
|
205
|
+
"big",
|
|
206
|
+
"font",
|
|
207
|
+
"a",
|
|
208
|
+
// 代码相关
|
|
209
|
+
"code",
|
|
210
|
+
"pre",
|
|
211
|
+
"kbd",
|
|
212
|
+
"samp",
|
|
213
|
+
"var",
|
|
214
|
+
"tt",
|
|
215
|
+
// 块级元素
|
|
216
|
+
"div",
|
|
217
|
+
"p",
|
|
218
|
+
"section",
|
|
219
|
+
"article",
|
|
220
|
+
"header",
|
|
221
|
+
"footer",
|
|
222
|
+
"aside",
|
|
223
|
+
"nav",
|
|
224
|
+
"main",
|
|
225
|
+
"figure",
|
|
226
|
+
"figcaption",
|
|
227
|
+
"blockquote",
|
|
228
|
+
"address",
|
|
229
|
+
// 列表
|
|
230
|
+
"ul",
|
|
231
|
+
"ol",
|
|
232
|
+
"li",
|
|
233
|
+
"dl",
|
|
234
|
+
"dt",
|
|
235
|
+
"dd",
|
|
236
|
+
// 表格
|
|
237
|
+
"table",
|
|
238
|
+
"thead",
|
|
239
|
+
"tbody",
|
|
240
|
+
"tfoot",
|
|
241
|
+
"tr",
|
|
242
|
+
"th",
|
|
243
|
+
"td",
|
|
244
|
+
"caption",
|
|
245
|
+
"colgroup",
|
|
246
|
+
"col",
|
|
247
|
+
// 换行/分隔
|
|
248
|
+
"br",
|
|
249
|
+
"hr",
|
|
250
|
+
"wbr",
|
|
251
|
+
// 其他
|
|
252
|
+
"abbr",
|
|
253
|
+
"acronym",
|
|
254
|
+
"cite",
|
|
255
|
+
"dfn",
|
|
256
|
+
"q",
|
|
257
|
+
"time",
|
|
258
|
+
"ruby",
|
|
259
|
+
"rt",
|
|
260
|
+
"rp",
|
|
261
|
+
"bdi",
|
|
262
|
+
"bdo",
|
|
263
|
+
"data",
|
|
264
|
+
"meter",
|
|
265
|
+
"progress",
|
|
266
|
+
"output",
|
|
267
|
+
"details",
|
|
268
|
+
"summary",
|
|
269
|
+
// 微信特殊标签
|
|
270
|
+
"mpvoice",
|
|
271
|
+
"mpprofile",
|
|
272
|
+
"qqmusic",
|
|
273
|
+
"mpcps"
|
|
274
|
+
];
|
|
275
|
+
function extractCodeText(html) {
|
|
276
|
+
const LT_PLACEHOLDER = "\0__CODE_LT__\0";
|
|
277
|
+
const GT_PLACEHOLDER = "\0__CODE_GT__\0";
|
|
278
|
+
let text = html;
|
|
279
|
+
text = text.replace(/</gi, LT_PLACEHOLDER);
|
|
280
|
+
text = text.replace(/>/gi, GT_PLACEHOLDER);
|
|
281
|
+
text = text.replace(/�*60;/gi, LT_PLACEHOLDER);
|
|
282
|
+
text = text.replace(/�*62;/gi, GT_PLACEHOLDER);
|
|
283
|
+
text = text.replace(/�*3[cC];/gi, LT_PLACEHOLDER);
|
|
284
|
+
text = text.replace(/�*3[eE];/gi, GT_PLACEHOLDER);
|
|
285
|
+
const tagPattern = KNOWN_HTML_TAGS.join("|");
|
|
286
|
+
text = text.replace(new RegExp(`<(${tagPattern})\\b[^>]*\\/?>`, "gi"), "");
|
|
287
|
+
text = text.replace(new RegExp(`<\\/(${tagPattern})>`, "gi"), "");
|
|
288
|
+
text = text.replace(new RegExp(LT_PLACEHOLDER.replace(/[.*+?^${}()|[\]\\]/g, "\\$&"), "g"), "<");
|
|
289
|
+
text = text.replace(new RegExp(GT_PLACEHOLDER.replace(/[.*+?^${}()|[\]\\]/g, "\\$&"), "g"), ">");
|
|
290
|
+
text = decodeHtmlEntities(text);
|
|
291
|
+
return text;
|
|
292
|
+
}
|
|
293
|
+
function extractCodeFromHtml(html) {
|
|
294
|
+
let text = html.replace(/<br\s*\/?>/gi, "\n").replace(/<\/div>/gi, "\n").replace(/<\/p>/gi, "\n").replace(/<\/li>/gi, "\n").replace(/<\/?code[^>]*>/gi, "");
|
|
295
|
+
text = extractCodeText(text);
|
|
296
|
+
return text.trim();
|
|
297
|
+
}
|
|
298
|
+
function htmlToMarkdown(html, _options = {}) {
|
|
299
|
+
return htmlToMarkdownSimple(html);
|
|
300
|
+
}
|
|
301
|
+
function extractLangFromClass(className) {
|
|
302
|
+
if (!className) return "";
|
|
303
|
+
const patterns = [
|
|
304
|
+
/language-(\w+)/i,
|
|
305
|
+
// language-javascript
|
|
306
|
+
/lang-(\w+)/i,
|
|
307
|
+
// lang-js
|
|
308
|
+
/\bhljs\s+(\w+)/i,
|
|
309
|
+
// hljs javascript
|
|
310
|
+
/\b(javascript|typescript|python|java|cpp|c|csharp|go|rust|ruby|php|swift|kotlin|scala|sql|html|css|json|xml|yaml|markdown|bash|shell|powershell)\b/i
|
|
311
|
+
];
|
|
312
|
+
for (const pattern of patterns) {
|
|
313
|
+
const match = className.match(pattern);
|
|
314
|
+
if (match) {
|
|
315
|
+
return match[1].toLowerCase();
|
|
316
|
+
}
|
|
317
|
+
}
|
|
318
|
+
return "";
|
|
319
|
+
}
|
|
320
|
+
function htmlToMarkdownSimple(html) {
|
|
321
|
+
let md = html;
|
|
322
|
+
md = md.replace(
|
|
323
|
+
/<ul[^>]*class=["'][^"']*code-snippet__line-index[^"']*["'][^>]*>[\s\S]*?<\/ul>/gi,
|
|
324
|
+
""
|
|
325
|
+
);
|
|
326
|
+
md = convertTables(md);
|
|
327
|
+
md = md.replace(/<h1[^>]*>([\s\S]*?)<\/h1>/gi, "\n# $1\n");
|
|
328
|
+
md = md.replace(/<h2[^>]*>([\s\S]*?)<\/h2>/gi, "\n## $1\n");
|
|
329
|
+
md = md.replace(/<h3[^>]*>([\s\S]*?)<\/h3>/gi, "\n### $1\n");
|
|
330
|
+
md = md.replace(/<h4[^>]*>([\s\S]*?)<\/h4>/gi, "\n#### $1\n");
|
|
331
|
+
md = md.replace(/<h5[^>]*>([\s\S]*?)<\/h5>/gi, "\n##### $1\n");
|
|
332
|
+
md = md.replace(/<h6[^>]*>([\s\S]*?)<\/h6>/gi, "\n###### $1\n");
|
|
333
|
+
md = md.replace(/<(strong|b)[^>]*>([\s\S]*?)<\/\1>/gi, "**$2**");
|
|
334
|
+
md = md.replace(/<(em|i)[^>]*>([\s\S]*?)<\/\1>/gi, "*$2*");
|
|
335
|
+
md = md.replace(/<a[^>]*href="([^"]*)"[^>]*>([\s\S]*?)<\/a>/gi, "[$2]($1)");
|
|
336
|
+
md = md.replace(/<img[^>]*src="([^"]*)"[^>]*alt="([^"]*)"[^>]*\/?>/gi, "");
|
|
337
|
+
md = md.replace(/<img[^>]*src="([^"]*)"[^>]*\/?>/gi, "");
|
|
338
|
+
md = md.replace(/<pre[^>]*>([\s\S]*?)<\/pre>/gi, (match, content) => {
|
|
339
|
+
let language = "";
|
|
340
|
+
const preLangMatch = match.match(/<pre[^>]*data-lang(?:uage)?=["'](\w+)["']/);
|
|
341
|
+
const preClassMatch = match.match(/<pre[^>]*class="([^"]*)"/);
|
|
342
|
+
if (preLangMatch) {
|
|
343
|
+
language = preLangMatch[1];
|
|
344
|
+
} else if (preClassMatch) {
|
|
345
|
+
language = extractLangFromClass(preClassMatch[1]);
|
|
346
|
+
}
|
|
347
|
+
const codeLangMatch = content.match(/<code[^>]*data-lang(?:uage)?=["'](\w+)["']/);
|
|
348
|
+
const codeClassMatch = content.match(/<code[^>]*class="([^"]*)"/);
|
|
349
|
+
if (!language) {
|
|
350
|
+
if (codeLangMatch) {
|
|
351
|
+
language = codeLangMatch[1];
|
|
352
|
+
} else if (codeClassMatch) {
|
|
353
|
+
language = extractLangFromClass(codeClassMatch[1]);
|
|
354
|
+
}
|
|
355
|
+
}
|
|
356
|
+
const text = extractCodeFromHtml(content);
|
|
357
|
+
return "\n```" + language + "\n" + text + "\n```\n";
|
|
358
|
+
});
|
|
359
|
+
md = md.replace(/<code[^>]*>([\s\S]*?)<\/code>/gi, "`$1`");
|
|
360
|
+
md = md.replace(/<ul[^>]*>([\s\S]*?)<\/ul>/gi, "$1\n");
|
|
361
|
+
md = md.replace(/<ol[^>]*>([\s\S]*?)<\/ol>/gi, "$1\n");
|
|
362
|
+
md = md.replace(/<li[^>]*>([\s\S]*?)<\/li>/gi, "- $1\n");
|
|
363
|
+
md = md.replace(/<p[^>]*>([\s\S]*?)<\/p>/gi, "\n$1\n");
|
|
364
|
+
md = md.replace(/<br\s*\/?>/gi, "\n");
|
|
365
|
+
md = md.replace(/<hr\s*\/?>/gi, "\n---\n");
|
|
366
|
+
md = md.replace(/<blockquote[^>]*>([\s\S]*?)<\/blockquote>/gi, (_, content) => {
|
|
367
|
+
return "\n" + content.trim().split("\n").map((line) => "> " + line).join("\n") + "\n";
|
|
368
|
+
});
|
|
369
|
+
md = md.replace(/<script[^>]*type=["']math\/tex[^"']*display[^"']*["'][^>]*>([\s\S]*?)<\/script>/gi, "\n$$$$\n$1\n$$$$\n");
|
|
370
|
+
md = md.replace(/<script[^>]*type=["']math\/tex["'][^>]*>([\s\S]*?)<\/script>/gi, " $$$$$1$$$$ ");
|
|
371
|
+
md = md.replace(/<\/?[^>]+(>|$)/g, "");
|
|
372
|
+
md = md.replace(/&/g, "&");
|
|
373
|
+
md = md.replace(/</g, "<");
|
|
374
|
+
md = md.replace(/>/g, ">");
|
|
375
|
+
md = md.replace(/"/g, '"');
|
|
376
|
+
md = md.replace(/'/g, "'");
|
|
377
|
+
md = md.replace(/ /g, " ");
|
|
378
|
+
md = md.replace(/\n{3,}/g, "\n\n");
|
|
379
|
+
md = md.trim();
|
|
380
|
+
return md;
|
|
381
|
+
}
|
|
382
|
+
function convertTables(html) {
|
|
383
|
+
html = html.replace(/<figure[^>]*>([\s\S]*?)<\/figure>/gi, (match, figureContent) => {
|
|
384
|
+
if (/<table[^>]*>/i.test(figureContent)) {
|
|
385
|
+
const tableMatch = figureContent.match(/<table[^>]*>([\s\S]*?)<\/table>/i);
|
|
386
|
+
const captionMatch = figureContent.match(/<figcaption[^>]*>([\s\S]*?)<\/figcaption>/i);
|
|
387
|
+
if (tableMatch) {
|
|
388
|
+
let result = tableMatch[0];
|
|
389
|
+
if (captionMatch) {
|
|
390
|
+
const caption = captionMatch[1].replace(/<[^>]+>/g, "").trim();
|
|
391
|
+
if (caption) {
|
|
392
|
+
result += "\n*" + caption + "*\n";
|
|
393
|
+
}
|
|
394
|
+
}
|
|
395
|
+
return result;
|
|
396
|
+
}
|
|
397
|
+
}
|
|
398
|
+
return match;
|
|
399
|
+
});
|
|
400
|
+
return html.replace(/<table[^>]*>([\s\S]*?)<\/table>/gi, (_, tableContent) => {
|
|
401
|
+
const hasTheadMatch = tableContent.match(/<thead[^>]*>([\s\S]*?)<\/thead>/i);
|
|
402
|
+
const rows = [];
|
|
403
|
+
const alignments = [];
|
|
404
|
+
let headerRowIndex = -1;
|
|
405
|
+
const rowMatches = tableContent.match(/<tr[^>]*>([\s\S]*?)<\/tr>/gi) || [];
|
|
406
|
+
for (let i = 0; i < rowMatches.length; i++) {
|
|
407
|
+
const rowContent = rowMatches[i];
|
|
408
|
+
const cells = [];
|
|
409
|
+
const rowAligns = [];
|
|
410
|
+
const cellMatches = rowContent.match(/<t[hd][^>]*>([\s\S]*?)<\/t[hd]>/gi) || [];
|
|
411
|
+
const isHeaderRow = cellMatches.length > 0 && cellMatches.every((c) => c.startsWith("<th"));
|
|
412
|
+
for (const cellMatch of cellMatches) {
|
|
413
|
+
const fullMatch = cellMatch.match(/<t[hd]([^>]*)>([\s\S]*?)<\/t[hd]>/i);
|
|
414
|
+
if (fullMatch) {
|
|
415
|
+
const attrs = fullMatch[1];
|
|
416
|
+
const rawContent = fullMatch[2];
|
|
417
|
+
const alignMatch = attrs.match(/align=["']?(left|center|right)["']?/i) || attrs.match(/style=["'][^"']*text-align:\s*(left|center|right)/i);
|
|
418
|
+
const align = alignMatch ? alignMatch[1].toLowerCase() : "";
|
|
419
|
+
rowAligns.push(align);
|
|
420
|
+
let content = rawContent.replace(/<br\s*\/?>/gi, " ").replace(/<[^>]+>/g, "").replace(/ /g, " ").replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").replace(/\s+/g, " ").trim();
|
|
421
|
+
content = content.replace(/\|/g, "\\|");
|
|
422
|
+
cells.push(content);
|
|
423
|
+
}
|
|
424
|
+
}
|
|
425
|
+
if (cells.length > 0) {
|
|
426
|
+
rows.push(cells);
|
|
427
|
+
alignments.push(rowAligns);
|
|
428
|
+
if (hasTheadMatch && rowContent.indexOf("<th") !== -1) {
|
|
429
|
+
headerRowIndex = i;
|
|
430
|
+
} else if (i === 0 && isHeaderRow) {
|
|
431
|
+
headerRowIndex = 0;
|
|
432
|
+
}
|
|
433
|
+
}
|
|
434
|
+
}
|
|
435
|
+
if (rows.length === 0) {
|
|
436
|
+
return "";
|
|
437
|
+
}
|
|
438
|
+
if (headerRowIndex === -1) {
|
|
439
|
+
headerRowIndex = 0;
|
|
440
|
+
}
|
|
441
|
+
const mdRows = [];
|
|
442
|
+
const colCount = Math.max(...rows.map((r) => r.length));
|
|
443
|
+
const headerAligns = alignments[headerRowIndex] || [];
|
|
444
|
+
for (let i = 0; i < rows.length; i++) {
|
|
445
|
+
const row = rows[i];
|
|
446
|
+
while (row.length < colCount) {
|
|
447
|
+
row.push("");
|
|
448
|
+
}
|
|
449
|
+
mdRows.push("| " + row.join(" | ") + " |");
|
|
450
|
+
if (i === headerRowIndex) {
|
|
451
|
+
const separators = [];
|
|
452
|
+
for (let j = 0; j < colCount; j++) {
|
|
453
|
+
const align = headerAligns[j] || "";
|
|
454
|
+
if (align === "left") {
|
|
455
|
+
separators.push(":---");
|
|
456
|
+
} else if (align === "center") {
|
|
457
|
+
separators.push(":---:");
|
|
458
|
+
} else if (align === "right") {
|
|
459
|
+
separators.push("---:");
|
|
460
|
+
} else {
|
|
461
|
+
separators.push("---");
|
|
462
|
+
}
|
|
463
|
+
}
|
|
464
|
+
mdRows.push("| " + separators.join(" | ") + " |");
|
|
465
|
+
}
|
|
466
|
+
}
|
|
467
|
+
return "\n\n" + mdRows.join("\n") + "\n\n";
|
|
468
|
+
});
|
|
469
|
+
}
|
|
470
|
+
function markdownToHtml(markdown) {
|
|
471
|
+
return marked.parse(markdown, { async: false });
|
|
472
|
+
}
|
|
473
|
+
|
|
474
|
+
// src/lib/aws4.ts
|
|
475
|
+
async function hmacSha256(key, message) {
|
|
476
|
+
const keyBytes = key instanceof Uint8Array ? key : new Uint8Array(key);
|
|
477
|
+
const keyBuffer = new Uint8Array(keyBytes).buffer;
|
|
478
|
+
const cryptoKey = await crypto.subtle.importKey(
|
|
479
|
+
"raw",
|
|
480
|
+
keyBuffer,
|
|
481
|
+
{ name: "HMAC", hash: "SHA-256" },
|
|
482
|
+
false,
|
|
483
|
+
["sign"]
|
|
484
|
+
);
|
|
485
|
+
return crypto.subtle.sign("HMAC", cryptoKey, new TextEncoder().encode(message));
|
|
486
|
+
}
|
|
487
|
+
async function sha256(message) {
|
|
488
|
+
const msgBuffer = new TextEncoder().encode(message);
|
|
489
|
+
const hashBuffer = await crypto.subtle.digest("SHA-256", msgBuffer);
|
|
490
|
+
return arrayBufferToHex(hashBuffer);
|
|
491
|
+
}
|
|
492
|
+
function arrayBufferToHex(buffer) {
|
|
493
|
+
return Array.from(new Uint8Array(buffer)).map((b) => b.toString(16).padStart(2, "0")).join("");
|
|
494
|
+
}
|
|
495
|
+
function formatAmzDate(date) {
|
|
496
|
+
return date.toISOString().replace(/[:-]|\.\d{3}/g, "");
|
|
497
|
+
}
|
|
498
|
+
function formatDateStamp(date) {
|
|
499
|
+
return date.toISOString().slice(0, 10).replace(/-/g, "");
|
|
500
|
+
}
|
|
501
|
+
async function signAWS4(params) {
|
|
502
|
+
const {
|
|
503
|
+
method,
|
|
504
|
+
url,
|
|
505
|
+
accessKeyId,
|
|
506
|
+
secretAccessKey,
|
|
507
|
+
securityToken,
|
|
508
|
+
region = "cn-north-1",
|
|
509
|
+
service = "imagex",
|
|
510
|
+
headers = {},
|
|
511
|
+
body = ""
|
|
512
|
+
} = params;
|
|
513
|
+
const parsedUrl = new URL(url);
|
|
514
|
+
const path = parsedUrl.pathname;
|
|
515
|
+
const queryString = parsedUrl.search.slice(1);
|
|
516
|
+
const now = /* @__PURE__ */ new Date();
|
|
517
|
+
const amzDate = formatAmzDate(now);
|
|
518
|
+
const dateStamp = formatDateStamp(now);
|
|
519
|
+
const queryParams = new URLSearchParams(queryString);
|
|
520
|
+
const sortedParams = Array.from(queryParams.entries()).sort((a, b) => a[0].localeCompare(b[0]));
|
|
521
|
+
const canonicalQueryString = sortedParams.map(([k, v]) => `${encodeURIComponent(k)}=${encodeURIComponent(v)}`).join("&");
|
|
522
|
+
const signedHeadersObj = {
|
|
523
|
+
"x-amz-date": amzDate
|
|
524
|
+
};
|
|
525
|
+
if (securityToken) {
|
|
526
|
+
signedHeadersObj["x-amz-security-token"] = securityToken;
|
|
527
|
+
}
|
|
528
|
+
Object.assign(signedHeadersObj, headers);
|
|
529
|
+
const signedHeaderNames = Object.keys(signedHeadersObj).map((k) => k.toLowerCase()).sort().join(";");
|
|
530
|
+
const canonicalHeaders = Object.entries(signedHeadersObj).map(([k, v]) => `${k.toLowerCase()}:${v.trim()}`).sort().join("\n") + "\n";
|
|
531
|
+
const payloadHash = await sha256(body);
|
|
532
|
+
const canonicalRequest = [
|
|
533
|
+
method.toUpperCase(),
|
|
534
|
+
path || "/",
|
|
535
|
+
canonicalQueryString,
|
|
536
|
+
canonicalHeaders,
|
|
537
|
+
signedHeaderNames,
|
|
538
|
+
payloadHash
|
|
539
|
+
].join("\n");
|
|
540
|
+
const algorithm = "AWS4-HMAC-SHA256";
|
|
541
|
+
const credentialScope = `${dateStamp}/${region}/${service}/aws4_request`;
|
|
542
|
+
const canonicalRequestHash = await sha256(canonicalRequest);
|
|
543
|
+
const stringToSign = [
|
|
544
|
+
algorithm,
|
|
545
|
+
amzDate,
|
|
546
|
+
credentialScope,
|
|
547
|
+
canonicalRequestHash
|
|
548
|
+
].join("\n");
|
|
549
|
+
const kDate = await hmacSha256(
|
|
550
|
+
new TextEncoder().encode("AWS4" + secretAccessKey),
|
|
551
|
+
dateStamp
|
|
552
|
+
);
|
|
553
|
+
const kRegion = await hmacSha256(kDate, region);
|
|
554
|
+
const kService = await hmacSha256(kRegion, service);
|
|
555
|
+
const kSigning = await hmacSha256(kService, "aws4_request");
|
|
556
|
+
const signatureBuffer = await hmacSha256(kSigning, stringToSign);
|
|
557
|
+
const signature = arrayBufferToHex(signatureBuffer);
|
|
558
|
+
const authorization = `${algorithm} Credential=${accessKeyId}/${credentialScope}, SignedHeaders=${signedHeaderNames}, Signature=${signature}`;
|
|
559
|
+
const resultHeaders = {
|
|
560
|
+
authorization,
|
|
561
|
+
"x-amz-date": amzDate
|
|
562
|
+
};
|
|
563
|
+
if (securityToken) {
|
|
564
|
+
resultHeaders["x-amz-security-token"] = securityToken;
|
|
565
|
+
}
|
|
566
|
+
return {
|
|
567
|
+
authorization,
|
|
568
|
+
amzDate,
|
|
569
|
+
headers: resultHeaders
|
|
570
|
+
};
|
|
571
|
+
}
|
|
572
|
+
function crc32(data) {
|
|
573
|
+
let crc = 4294967295;
|
|
574
|
+
const table = getCRC32Table();
|
|
575
|
+
for (let i = 0; i < data.length; i++) {
|
|
576
|
+
crc = crc >>> 8 ^ table[(crc ^ data[i]) & 255];
|
|
577
|
+
}
|
|
578
|
+
return ((crc ^ 4294967295) >>> 0).toString(16).padStart(8, "0");
|
|
579
|
+
}
|
|
580
|
+
var crc32Table = null;
|
|
581
|
+
function getCRC32Table() {
|
|
582
|
+
if (crc32Table) return crc32Table;
|
|
583
|
+
crc32Table = new Uint32Array(256);
|
|
584
|
+
for (let i = 0; i < 256; i++) {
|
|
585
|
+
let c = i;
|
|
586
|
+
for (let j = 0; j < 8; j++) {
|
|
587
|
+
c = c & 1 ? 3988292384 ^ c >>> 1 : c >>> 1;
|
|
588
|
+
}
|
|
589
|
+
crc32Table[i] = c;
|
|
590
|
+
}
|
|
591
|
+
return crc32Table;
|
|
592
|
+
}
|
|
593
|
+
|
|
594
|
+
export {
|
|
595
|
+
createLogger,
|
|
596
|
+
parseMarkdownImages,
|
|
597
|
+
htmlToMarkdown,
|
|
598
|
+
markdownToHtml,
|
|
599
|
+
signAWS4,
|
|
600
|
+
crc32
|
|
601
|
+
};
|
|
602
|
+
//# sourceMappingURL=chunk-7Q3KKWUB.js.map
|