feat(render): full post-body pipeline + image proxy (#3976–#3978 intent)#3987
Open
ety001 wants to merge 1 commit into
Open
feat(render): full post-body pipeline + image proxy (#3976–#3978 intent)#3987ety001 wants to merge 1 commit into
ety001 wants to merge 1 commit into
Conversation
…tize-html) + image proxy Implements the complete post-body rendering pipeline on the next branch and absorbs the intent of master's image-proxy fixes #3976–#3978 (which target files that don't exist on next — this is a from-scratch reimplementation, not a cherry-pick). Pipeline (order is security-critical): markdown-it (markdown→HTML) → HtmlReady (mutation/normalize) → sanitize-html (XSS) New files: - lib/media/proxify-url.ts: proxifyImageUrl + isDefaultImageSize/defaultSrcSet. Absorbs #3976 (only first-party via /p), #3977 (idempotent /p/ URLs — no double base58-encode), #3978 (canonicalize steemitimages.com/D* to cdn before encoding). Proxy prefix via NEXT_PUBLIC_IMAGE_PROXY_PREFIX. - lib/media/links.ts: URL/first-party/image regexes (local = *.steemit.com). - lib/sanitize-config.ts: sanitize-html config — allowedTags/Attributes/Schemes, transformTags with the iframe whitelist (vimeo/youtube/3speak/soundcloud/ twitch/dtube verbatim). This is the real XSS filter. - lib/html-ready.ts: HtmlReady mutation layer — link normalization, iframe wrapping in videoWrapper, image https-ify + clickable wrap, #tag/@mention linkify, naked-image-URL detection, proxifyImages. (Scoped to MVP: video embed-replacement chains and the external Phishing module not ported.) Rewritten: - components/elements/MarkdownViewer.tsx: the regex hack → real pipeline. Public props (text/className/large/hideImages) unchanged; PostFull unaffected. Deps: markdown-it (actively-maintained CommonMark renderer, replaces the unmaintained remarkable; identical options surface), bs58@6 (ESM current major), sanitize-html (v2), @xmldom/xmldom, plus @types/{markdown-it,sanitize-html}. Verified: tsc clean, eslint clean, next build ✓. Runtime-tested the proxy: first-party proxied via /p/:base58, idempotent under double-proxy, third-party passthrough, /D urls canonicalized to cdn inside the encoded URL. Not in scope: next/image (deliberately excluded — conflicts with /p/ double optimization), voting-slider UX, master's non-image fixes.
a8ef5eb to
3f8f47f
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Implements the complete post-body rendering pipeline on the
nextbranch and absorbs the intent of master's image-proxy fixes #3976–#3978.Those three commits target
src/app/utils/ProxifyUrl.js,src/shared/HtmlReady.js, etc. — files that don't exist onnext(it's a from-scratch rewrite). So this is a reimplementation of the same intent, not a cherry-pick: the currentMarkdownViewer.tsxis a regex hack that doesn't even render![]()images.Pipeline (order is security-critical)
sanitize-htmlis the real XSS filter (iframe whitelist, allowedTags/Attributes). Using bridgebody_htmldirectly would bypass it — unsafe. So we render raw markdownbodyand sanitize ourselves.New files
lib/media/proxify-url.ts—proxifyImageUrl. Absorbs all three fixes:/p/(third-party passthrough)/p/URLs (no double base58-encode)steemitimages.com/D*→cdn.steemitimages.cominside the encoded URLlib/media/links.ts— URL/first-party/image regexes.lib/sanitize-config.ts— sanitize-html config: allowedTags/Attributes/Schemes,transformTagswith the iframe whitelist verbatim (vimeo/youtube/3speak/soundcloud/twitch/dtube).lib/html-ready.ts— HtmlReady mutation: link normalize, iframe→videoWrapper wrap, image https-ify + clickable wrap, #tag/@mention linkify, naked-URL→img,proxifyImages. (MVP-scoped: video embed-replacement chains + external Phishing module not ported.)Rewritten
components/elements/MarkdownViewer.tsx— regex hack → real pipeline. Public props (text/className/large/hideImages) unchanged;PostFullunaffected.Dependencies
markdown-it(actively-maintained CommonMark renderer, replaces unmaintainedremarkable; identical options surface),bs58@6(current ESM major),sanitize-htmlv2,@xmldom/xmldom, plus@types/{markdown-it,sanitize-html}.Verification
tsc --noEmit— cleaneslint— cleannext build— ✓ Compiled successfully/p/:base58, idempotent under double-proxy, third-party passthrough,/Durls canonicalized to cdn inside the encoded URLNot in scope
next/image(deliberately excluded — conflicts with/p/double-optimization), voting-slider UX, master's non-image fixes.