diff --git a/frontend/src/druksui/Blocks.tsx b/frontend/src/druksui/Blocks.tsx index 17311c00..4a55411c 100644 --- a/frontend/src/druksui/Blocks.tsx +++ b/frontend/src/druksui/Blocks.tsx @@ -1,13 +1,10 @@ -import { useContext } from 'react' -import { Link as RouteLink } from 'wouter' - import type { Action, Block, Link } from '../api/types' import { Markdown } from '../components/Markdown' import { GateControls } from './GateControls' -import { Chart, Facts, ImageGallery, List, Metrics, Table } from './DataBlocks' +import { Chart, Facts, ImageGallery, LinkControl, List, Metrics, Table } from './DataBlocks' import { ActionButton, Form } from './Form' import { Files, Image, Progress, Timeline } from './RunBlocks' -import { fillPath, PagesContext, RegionContext } from './pages' +import { RegionContext } from './pages' export function Blocks({ blocks }: { blocks: Block[] }) { return ( @@ -163,38 +160,3 @@ function LinkRow({ links }: { links: (Action | Link)[] }) { ) } -function LinkControl({ link }: { link: Link }) { - const { app, pages } = useContext(PagesContext) - if (link.url) { - return ( - - {link.label} - - ) - } - if (link.subject) { - // The subject's own platform page — the full story of what druks did. - return ( - - {link.label} - - ) - } - const target = pages.find((entry) => entry.name === link.page) - const href = target ? fillPath(target.path, link.arguments) : '' - if (href) { - return ( - - {link.label} - - ) - } - return ( - - {link.label} - - ) -} diff --git a/frontend/src/druksui/DataBlocks.test.tsx b/frontend/src/druksui/DataBlocks.test.tsx index 4cf66345..8513f71a 100644 --- a/frontend/src/druksui/DataBlocks.test.tsx +++ b/frontend/src/druksui/DataBlocks.test.tsx @@ -86,6 +86,31 @@ describe('values', () => { expect(screen.getByText('peer-7').getAttribute('href')).toBe('/field_notes/notes/7') }) + it('follows a subject link out of a list item', () => { + renderBlocks([ + { + block: 'list', + title: '', + items: [ + { + value: 'text', + text: 'peer-7', + link: { + block: 'link', + label: 'peer-7', + page: '', + arguments: {}, + url: '', + subject: { subjectType: 'note', subjectId: '7' }, + }, + }, + ], + }, + ]) + + expect(screen.getByText('peer-7').getAttribute('href')).toBe('/field_notes/note/7') + }) + it('shows a number the way the app gave it', () => { renderBlocks([ { diff --git a/frontend/src/druksui/DataBlocks.tsx b/frontend/src/druksui/DataBlocks.tsx index 6d04f305..cbf9bc78 100644 --- a/frontend/src/druksui/DataBlocks.tsx +++ b/frontend/src/druksui/DataBlocks.tsx @@ -52,27 +52,44 @@ export function Datum({ value }: { value: Value }) { } function TextDatum({ text, link }: { text: string; link: Link | null }) { - const { pages } = useContext(PagesContext) if (!link) return {text} + return +} + +/** A control that navigates. It is a block of its own, or the link on a value, + which shows the value's own text. */ +export function LinkControl({ link, label = link.label }: { link: Link; label?: string }) { + const { app, pages } = useContext(PagesContext) if (link.url) { return ( - {text} + {label} ) } + if (link.subject) { + // The subject's own platform page — the full story of what druks did. + return ( + + {label} + + ) + } const target = pages.find((entry) => entry.name === link.page) const href = target ? fillPath(target.path, link.arguments) : '' if (href) { return ( - {text} + {label} ) } return ( - {text} + {label} ) }