// LinkedText.jsx — roadmap #28 (Parts 1–3).
//
// Renders a backend-provided list of text/link segments (see
// backend/app/rfc_links.py). References in PR descriptions and comments
// arrive pre-scanned as structured segments — this component maps them
// onto plain text runs, anchors, and inline affordances. It never renders
// HTML from the server (no dangerouslySetInnerHTML), so the surface is
// XSS-safe regardless of what a comment author typed.
//
// Segment types:
// * `rfc` — Part 1: a link to an accepted (active) RFC.
// * `rfc-pending` — Part 3: the term names a pending (super-draft)
// RFC; a signed-in viewer who isn't its owner gets
// an inline "ask to contribute" affordance routing
// to the contribute form (App reads `?contribute=`).
// * `rfc-candidate` — Part 2: a strong-candidate term with no RFC yet;
// a viewer with create rights (`canCreate`) gets a
// "create RFC" affordance routing to the propose
// flow pre-filled (App reads `?propose=`).
//
// Affordances degrade to plain text when the viewer lacks the relevant
// right, so the visible prose is identical for everyone — only the
// offered actions differ.
//
// `segments` is the enriched array; `text` is the raw fallback used when
// the field is absent (an older cached response, or a caller that didn't
// pass segments).
import { Link } from 'react-router-dom'
import { entryPath, useProjectId } from '../lib/entryPaths'
export default function LinkedText({ segments, text, viewer, canCreate }) {
const pid = useProjectId()
if (!Array.isArray(segments) || segments.length === 0) {
return <>{text ?? ''}>
}
// A signed-in, beta-granted viewer can ask to contribute; the backend
// re-checks ownership/collaborator status and rejects self-requests.
const canContribute = !!viewer && viewer.permission_state === 'granted'
return (
<>
{segments.map((seg, i) => {
if (seg.type === 'rfc') {
return (
{seg.label}
)
}
if (seg.type === 'rfc-pending') {
const who = seg.owner || 'Someone'
return (
{seg.label}
{canContribute && (
ask to contribute
)}
)
}
if (seg.type === 'rfc-candidate') {
const term = seg.term || seg.label
return (
{seg.label}
{canCreate && (
+ create RFC
)}
)
}
return {seg.text}
})}
>
)
}