added react-markdown

This commit is contained in:
Storme-bit
2026-04-17 22:45:24 -07:00
parent fc864041c5
commit 1cc7b62d79
2 changed files with 43 additions and 18 deletions

View File

@@ -1,5 +1,6 @@
import React, { useState, useEffect, useCallback } from 'react';
import { getEpisodes, deleteEpisode } from '../api/orchestration';
import ReactMarkdown from 'react-markdown';
const PAGE_SIZE = 20;
@@ -41,6 +42,8 @@ export default function MemoryView({ onNavigate }) {
load();
}
const totalPages = Math.ceil(total / PAGE_SIZE);
const currentPage = Math.floor(offset / PAGE_SIZE) + 1;
@@ -119,9 +122,20 @@ export default function MemoryView({ onNavigate }) {
);
}
function stripMarkdown(text) {
return text
.replace(/\*\*(.*?)\*\*/g, '$1') // bold
.replace(/\*(.*?)\*/g, '$1') // italic
.replace(/`([^`]+)`/g, '$1') // inline code
.replace(/^#{1,6}\s+/gm, '') // headings
.replace(/^\s*[-*+]\s+/gm, '') // list markers
.trim();
}
function EpisodeCard({ episode, expanded, onToggle, onDelete }) {
const date = new Date(episode.created_at * 1000).toLocaleString();
const preview = episode.user_message.slice(0, 80) + (episode.user_message.length > 80 ? '…' : '');
const preview = stripMarkdown(episode.user_message).slice(0, 80) +
(episode.user_message.length > 80 ? '…' : '');
return (
<div style={{
@@ -156,12 +170,25 @@ function EpisodeCard({ episode, expanded, onToggle, onDelete }) {
}
function MessageBlock({ label, content, color }) {
const isAI = label === 'NexusAI';
return (
<div style={{ marginTop: 12 }}>
<p style={{ fontSize: 11, fontWeight: 600, color, marginBottom: 4, textTransform: 'uppercase', letterSpacing: '0.05em' }}>
{label}
</p>
<p className="text-sm" style={{ whiteSpace: 'pre-wrap', lineHeight: 1.6 }}>{content}</p>
<ReactMarkdown
components={{
p: ({children}) => <p style={{ margin: '0 0 8px', lineHeight: 1.6, fontSize: 13 }}>{children}</p>,
ul: ({children}) => <ul style={{ margin: '0 0 8px', paddingLeft: '20px' }}>{children}</ul>,
ol: ({children}) => <ol style={{ margin: '0 0 8px', paddingLeft: '20px' }}>{children}</ol>,
li: ({children}) => <li style={{ marginBottom: '2px', fontSize: 13 }}>{children}</li>,
code: ({inline, children}) => inline
? <code style={{ background: 'var(--bg-elevated)', padding: '1px 5px', borderRadius: 'var(--radius-sm)', fontSize: 12, fontFamily: 'monospace' }}>{children}</code>
: <pre style={{ background: 'var(--bg-elevated)', padding: '10px 12px', borderRadius: 'var(--radius-md)', overflowX: 'auto', fontSize: 12, fontFamily: 'monospace' }}><code>{children}</code></pre>,
strong: ({children}) => <strong style={{ fontWeight: 600, color: 'var(--text-primary)' }}>{children}</strong>,
}}
>{content}</ReactMarkdown>
</div>
);
}

View File

@@ -34,9 +34,7 @@ export default function MessageBubble({ message }) {
border: isUser ? 'none' : '1px solid var(--border)',
wordBreak: 'break-word',
}}>
{isUser
? message.text
: <ReactMarkdown
<ReactMarkdown
components={{
// Tighten up default spacing so it fits the bubble style
p: ({ children }) => <p style={{ margin: '0 0 8px', lineHeight: 1.6 }}>{children}</p>,
@@ -49,7 +47,7 @@ export default function MessageBubble({ message }) {
strong: ({ children }) => <strong style={{ fontWeight: 600, color: 'var(--text-primary)' }}>{children}</strong>,
}}
>{message.text}</ReactMarkdown>
}
{message.streaming && (
<span style={{
display: 'inline-block',