botholomew 0.7.11 → 0.7.13

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "botholomew",
3
- "version": "0.7.11",
3
+ "version": "0.7.13",
4
4
  "description": "Local, autonomous AI agent for knowledge work — works your task queue while you sleep.",
5
5
  "type": "module",
6
6
  "bin": {
@@ -9,6 +9,7 @@ import {
9
9
  listContextItemsByPrefix,
10
10
  searchContextByKeyword,
11
11
  } from "../../db/context.ts";
12
+ import { isMarkdownItem, renderMarkdown } from "../markdown.ts";
12
13
 
13
14
  interface ContextPanelProps {
14
15
  dbPath: string;
@@ -118,10 +119,15 @@ export const ContextPanel = memo(function ContextPanel({
118
119
  [items, scrollOffset, visibleRows],
119
120
  );
120
121
 
121
- // Preview content split into lines for scrolling
122
+ // Preview content split into lines for scrolling. Markdown files are
123
+ // rendered through Bun.markdown.ansi so headers/emphasis/code display
124
+ // with ANSI formatting in the terminal.
122
125
  const previewLines = useMemo(() => {
123
126
  if (!preview?.content) return [];
124
- return preview.content.split("\n");
127
+ const body = isMarkdownItem(preview)
128
+ ? renderMarkdown(preview.content)
129
+ : preview.content;
130
+ return body.split("\n");
125
131
  }, [preview]);
126
132
 
127
133
  useInput(
@@ -266,13 +272,17 @@ export const ContextPanel = memo(function ContextPanel({
266
272
  {visibleItems.map((item, vi) => {
267
273
  const i = vi + scrollOffset;
268
274
  const ci = item as ContextItem;
275
+ const slashIdx = ci.context_path.lastIndexOf("/");
276
+ const dir =
277
+ slashIdx >= 0 ? ci.context_path.slice(0, slashIdx + 1) : "";
269
278
  return (
270
279
  <Box key={ci.id}>
271
280
  <Text
272
281
  backgroundColor={i === cursor ? "#333" : undefined}
273
282
  color={i === cursor ? "cyan" : undefined}
274
283
  >
275
- {" "}📄 {ci.context_path}
284
+ {" "}📄 <Text dimColor>{dir}</Text>
285
+ {ci.title}
276
286
  <Text dimColor> ({ci.mime_type})</Text>
277
287
  </Text>
278
288
  </Box>
@@ -1,6 +1,7 @@
1
1
  import { Box, Text, useStdout } from "ink";
2
2
  import Spinner from "ink-spinner";
3
3
  import { memo, useMemo } from "react";
4
+ import { renderMarkdown } from "../markdown.ts";
4
5
  import { theme } from "../theme.ts";
5
6
  import { ToolCall, type ToolCallData } from "./ToolCall.tsx";
6
7
 
@@ -48,11 +49,6 @@ function wrapAndPad(text: string, width: number): string {
48
49
  return lines.join("\n");
49
50
  }
50
51
 
51
- function renderMarkdown(text: string): string {
52
- if (!text) return "";
53
- return Bun.markdown.ansi(text).trimEnd();
54
- }
55
-
56
52
  export const MessageBubble = memo(function MessageBubble({
57
53
  message,
58
54
  }: {
@@ -0,0 +1,15 @@
1
+ import type { ContextItem } from "../db/context.ts";
2
+
3
+ export function renderMarkdown(text: string): string {
4
+ if (!text) return "";
5
+ return Bun.markdown.ansi(text).trimEnd();
6
+ }
7
+
8
+ export function isMarkdownItem(
9
+ item: Pick<ContextItem, "mime_type" | "source_path" | "context_path">,
10
+ ): boolean {
11
+ if (item.mime_type === "text/markdown") return true;
12
+ if (item.source_path?.toLowerCase().endsWith(".md")) return true;
13
+ if (item.context_path.toLowerCase().endsWith(".md")) return true;
14
+ return false;
15
+ }