@alphinex/editor
v1.0.8
Published
Theme-aware rich text editor (adapter around Tiptap/ProseMirror) + a DOMPurify-sanitized read-only renderer. See ADR-0012 and documentation/PRODUCT-RESEARCH-MASTER-PLAN.md §10 (Sprint 19).
Readme
@alphinex/editor
Theme-aware rich text editor — a thin adapter around Tiptap/ProseMirror (see ADR-0012) plus a DOMPurify-sanitized read-only renderer for displaying stored content elsewhere.
Usage
import { RichTextEditor, RichTextRenderer } from "@alphinex/editor";
import { useState } from "react";
function Note() {
const [html, setHtml] = useState("");
return <RichTextEditor onChange={(value) => setHtml(value.html)} />;
}
function ReadOnlyNote({ storedHtml }: { storedHtml: string }) {
return <RichTextRenderer html={storedHtml} />;
}For content that needs to be re-loaded back into an editor exactly as it was, store
value.json (ProseMirror JSON) instead of value.html, and pass it back in as content:
const [doc, setDoc] = useState<EditorJSONContent>();
<RichTextEditor content={doc} onChange={(value) => setDoc(value.json)} />;useRichTextEditor is the headless layer underneath, if you want to build a custom toolbar
instead of the built-in Toolbar.
Security
Every path that turns stored/edited content into HTML shown on a page goes through
sanitizeHtml() (an allow-list, not a deny-list) — see src/sanitize.ts and ADR-0012.
RichTextRenderer is the only component in this package using dangerouslySetInnerHTML, and it
always sanitizes first, regardless of where the HTML came from.
Known limitation: the toolbar's allow-list (useRichTextEditor.ts's Tiptap extensions) and
sanitize.ts's ALLOWED_TAGS/ALLOWED_ATTR must be extended together — adding a new mark/node
(tables, images, ...) to the editor without adding its tag(s) to the sanitizer's allow-list means
RichTextRenderer will silently strip content the editor itself can produce.
