@ecency/render-helper 2.4.30 → 2.4.32
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/browser/index.d.ts +6 -1
- package/dist/browser/index.js +58 -9
- package/dist/browser/index.js.map +1 -1
- package/dist/node/index.cjs +59 -9
- package/dist/node/index.cjs.map +1 -1
- package/dist/node/index.mjs +58 -9
- package/dist/node/index.mjs.map +1 -1
- package/package.json +1 -1
package/dist/node/index.mjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { DOMParser as DOMParser$1, XMLSerializer } from '@xmldom/xmldom';
|
|
1
|
+
import { DOMParser as DOMParser$1, XMLSerializer as XMLSerializer$1 } from '@xmldom/xmldom';
|
|
2
2
|
import xss from 'xss';
|
|
3
3
|
import multihash from 'multihashes';
|
|
4
4
|
import querystring from 'querystring';
|
|
@@ -123,6 +123,8 @@ var ALLOWED_ATTRIBUTES = {
|
|
|
123
123
|
],
|
|
124
124
|
"img": [
|
|
125
125
|
"src",
|
|
126
|
+
"srcset",
|
|
127
|
+
"sizes",
|
|
126
128
|
"alt",
|
|
127
129
|
"class",
|
|
128
130
|
"loading",
|
|
@@ -166,17 +168,16 @@ var ALLOWED_ATTRIBUTES = {
|
|
|
166
168
|
"del": [],
|
|
167
169
|
"ins": []
|
|
168
170
|
};
|
|
169
|
-
var
|
|
171
|
+
var hasDOMParser = typeof globalThis.DOMParser !== "undefined";
|
|
172
|
+
var hasXMLSerializer = typeof globalThis.XMLSerializer !== "undefined";
|
|
173
|
+
var lenientErrorHandler = (level, msg, _context) => {
|
|
170
174
|
if (process.env.NODE_ENV === "development") {
|
|
171
175
|
console.warn("[DOMParser]", level, msg);
|
|
172
176
|
}
|
|
173
177
|
return void 0;
|
|
174
178
|
};
|
|
175
|
-
var DOMParser = new DOMParser$1({
|
|
176
|
-
|
|
177
|
-
// By providing a non-throwing error handler, parsing continues despite malformed HTML
|
|
178
|
-
onError: lenientErrorHandler
|
|
179
|
-
});
|
|
179
|
+
var DOMParser = hasDOMParser ? new globalThis.DOMParser() : new DOMParser$1({ onError: lenientErrorHandler });
|
|
180
|
+
var XMLSerializer = hasXMLSerializer ? globalThis.XMLSerializer : XMLSerializer$1;
|
|
180
181
|
|
|
181
182
|
// src/helper.ts
|
|
182
183
|
function removeDuplicateAttributes(html) {
|
|
@@ -254,6 +255,8 @@ function isValidUsername(username) {
|
|
|
254
255
|
!label.includes("..");
|
|
255
256
|
});
|
|
256
257
|
}
|
|
258
|
+
|
|
259
|
+
// src/methods/get-inner-html.method.ts
|
|
257
260
|
function getSerializedInnerHTML(node) {
|
|
258
261
|
const serializer = new XMLSerializer();
|
|
259
262
|
if (node.childNodes[0]) {
|
|
@@ -281,6 +284,10 @@ function sanitizeHtml(html) {
|
|
|
281
284
|
const decodedLower = decoded.toLowerCase();
|
|
282
285
|
if (name.startsWith("on")) return "";
|
|
283
286
|
if (tag === "img" && name === "src" && (!/^https?:\/\//.test(decodedLower) || decodedLower.startsWith("javascript:"))) return "";
|
|
287
|
+
if (tag === "img" && name === "srcset") {
|
|
288
|
+
const candidates = decoded.split(",").map((c) => c.trim().split(/\s+/)[0]);
|
|
289
|
+
if (candidates.some((url) => !/^https?:\/\//.test(url))) return "";
|
|
290
|
+
}
|
|
284
291
|
if (tag === "video" && ["src", "poster"].includes(name) && (!/^https?:\/\//.test(decodedLower) || decodedLower.startsWith("javascript:"))) return "";
|
|
285
292
|
if (tag === "img" && ["dynsrc", "lowsrc"].includes(name)) return "";
|
|
286
293
|
if (tag === "span" && name === "class" && decoded.toLowerCase().trim() === "wr") return "";
|
|
@@ -295,6 +302,9 @@ var proxyBase = "https://images.ecency.com";
|
|
|
295
302
|
function setProxyBase(p2) {
|
|
296
303
|
proxyBase = p2;
|
|
297
304
|
}
|
|
305
|
+
function getProxyBase() {
|
|
306
|
+
return proxyBase;
|
|
307
|
+
}
|
|
298
308
|
function extractPHash(url) {
|
|
299
309
|
if (url.startsWith(`${proxyBase}/p/`)) {
|
|
300
310
|
const [hash] = url.split("/p/")[1].split("?");
|
|
@@ -342,8 +352,24 @@ function proxifyImageSrc(url, width = 0, height = 0, _format = "match") {
|
|
|
342
352
|
const b58url = multihash.toB58String(Buffer.from(realUrl.toString()));
|
|
343
353
|
return `${proxyBase}/p/${b58url}?${qs}`;
|
|
344
354
|
}
|
|
355
|
+
var SRCSET_WIDTHS = [320, 600, 800, 1024, 1280];
|
|
356
|
+
function buildSrcSet(url) {
|
|
357
|
+
if (!url || typeof url !== "string") return "";
|
|
358
|
+
const escapedBase = proxyBase.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
|
|
359
|
+
const proxyPattern = new RegExp(`^${escapedBase}/p/([^?]+)`);
|
|
360
|
+
const match = url.match(proxyPattern);
|
|
361
|
+
if (match) {
|
|
362
|
+
const phash = extractPHash(url) || match[1];
|
|
363
|
+
return SRCSET_WIDTHS.map((w) => `${proxyBase}/p/${phash}?format=match&mode=fit&width=${w} ${w}w`).join(", ");
|
|
364
|
+
}
|
|
365
|
+
return SRCSET_WIDTHS.map((w) => {
|
|
366
|
+
const proxied = proxifyImageSrc(url, w);
|
|
367
|
+
return proxied ? `${proxied} ${w}w` : "";
|
|
368
|
+
}).filter(Boolean).join(", ");
|
|
369
|
+
}
|
|
345
370
|
|
|
346
371
|
// src/methods/img.method.ts
|
|
372
|
+
var IMAGE_SIZES = "(max-width: 768px) 100vw, 700px";
|
|
347
373
|
function img(el, state) {
|
|
348
374
|
const src = el.getAttribute("src") || "";
|
|
349
375
|
const decodedSrc = decodeURIComponent(
|
|
@@ -353,11 +379,15 @@ function img(el, state) {
|
|
|
353
379
|
const isInvalid = !src || decodedSrc.startsWith("javascript") || decodedSrc.startsWith("vbscript") || decodedSrc === "x";
|
|
354
380
|
if (isInvalid) {
|
|
355
381
|
el.removeAttribute("src");
|
|
382
|
+
el.removeAttribute("srcset");
|
|
383
|
+
el.removeAttribute("sizes");
|
|
356
384
|
return;
|
|
357
385
|
}
|
|
358
386
|
const isRelative = !/^https?:\/\//i.test(decodedSrc) && !decodedSrc.startsWith("/");
|
|
359
387
|
if (isRelative) {
|
|
360
388
|
el.removeAttribute("src");
|
|
389
|
+
el.removeAttribute("srcset");
|
|
390
|
+
el.removeAttribute("sizes");
|
|
361
391
|
return;
|
|
362
392
|
}
|
|
363
393
|
el.setAttribute("itemprop", "image");
|
|
@@ -372,22 +402,41 @@ function img(el, state) {
|
|
|
372
402
|
}
|
|
373
403
|
const cls = el.getAttribute("class") || "";
|
|
374
404
|
const shouldReplace = !cls.includes("no-replace");
|
|
375
|
-
const
|
|
405
|
+
const base = getProxyBase().replace(/\/+$/, "");
|
|
406
|
+
const hasAlreadyProxied = src.startsWith(`${base}/p/`) || src.startsWith(`${base}/u/`) || new RegExp(`^${base.replace(/[.*+?^${}()|[\]\\]/g, "\\$&")}/\\d+x\\d+/`).test(src);
|
|
376
407
|
if (shouldReplace && !hasAlreadyProxied) {
|
|
377
408
|
const proxified = proxifyImageSrc(decodedSrc);
|
|
378
409
|
if (proxified) {
|
|
379
410
|
el.setAttribute("src", proxified);
|
|
411
|
+
const srcset = buildSrcSet(decodedSrc);
|
|
412
|
+
if (srcset) {
|
|
413
|
+
el.setAttribute("srcset", srcset);
|
|
414
|
+
el.setAttribute("sizes", IMAGE_SIZES);
|
|
415
|
+
}
|
|
416
|
+
}
|
|
417
|
+
} else if (shouldReplace && hasAlreadyProxied) {
|
|
418
|
+
if (src.startsWith(`${base}/p/`)) {
|
|
419
|
+
const srcset = buildSrcSet(src);
|
|
420
|
+
if (srcset) {
|
|
421
|
+
el.setAttribute("srcset", srcset);
|
|
422
|
+
el.setAttribute("sizes", IMAGE_SIZES);
|
|
423
|
+
}
|
|
380
424
|
}
|
|
381
425
|
}
|
|
382
426
|
}
|
|
383
427
|
function createImageHTML(src, isLCP) {
|
|
384
428
|
const proxified = proxifyImageSrc(src);
|
|
385
429
|
if (!proxified) return "";
|
|
430
|
+
const base = getProxyBase().replace(/\/+$/, "");
|
|
431
|
+
const isAlreadyProxied = src.startsWith(`${base}/u/`) || new RegExp(`^${base.replace(/[.*+?^${}()|[\]\\]/g, "\\$&")}/\\d+x\\d+/`).test(src);
|
|
432
|
+
const srcset = isAlreadyProxied ? "" : buildSrcSet(src);
|
|
386
433
|
const loading = isLCP ? "eager" : "lazy";
|
|
387
434
|
const fetch = isLCP ? 'fetchpriority="high"' : 'decoding="async"';
|
|
435
|
+
const srcsetAttr = srcset ? `srcset="${srcset}" sizes="${IMAGE_SIZES}"` : "";
|
|
388
436
|
return `<img
|
|
389
437
|
class="markdown-img-link"
|
|
390
438
|
src="${proxified}"
|
|
439
|
+
${srcsetAttr}
|
|
391
440
|
loading="${loading}"
|
|
392
441
|
${fetch}
|
|
393
442
|
itemprop="image"
|
|
@@ -1780,6 +1829,6 @@ function getPostBodySummary(obj, length, platform) {
|
|
|
1780
1829
|
return res;
|
|
1781
1830
|
}
|
|
1782
1831
|
|
|
1783
|
-
export { SECTION_LIST, catchPostImage, isValidPermlink, getPostBodySummary as postBodySummary, proxifyImageSrc, markdown2Html as renderPostBody, setCacheSize, setProxyBase, simpleMarkdownToHTML };
|
|
1832
|
+
export { SECTION_LIST, buildSrcSet, catchPostImage, isValidPermlink, getPostBodySummary as postBodySummary, proxifyImageSrc, markdown2Html as renderPostBody, setCacheSize, setProxyBase, simpleMarkdownToHTML };
|
|
1784
1833
|
//# sourceMappingURL=index.mjs.map
|
|
1785
1834
|
//# sourceMappingURL=index.mjs.map
|