merge main
This commit is contained in:
@@ -15,6 +15,7 @@
|
||||
"@assistant-ui/react": "^0.8.0",
|
||||
"@assistant-ui/react-markdown": "^0.8.0",
|
||||
"@faker-js/faker": "^9.5.1",
|
||||
"@assistant-ui/react-syntax-highlighter": "^0.7.2",
|
||||
"@langchain/core": "^0.3.41",
|
||||
"@langchain/google-genai": "^0.1.10",
|
||||
"@langchain/langgraph": "^0.2.49",
|
||||
@@ -35,6 +36,7 @@
|
||||
"esbuild": "^0.25.0",
|
||||
"esbuild-plugin-tailwindcss": "^2.0.1",
|
||||
"framer-motion": "^12.4.9",
|
||||
"katex": "^0.16.21",
|
||||
"lucide-react": "^0.476.0",
|
||||
"next-themes": "^0.4.4",
|
||||
"prettier": "^3.5.2",
|
||||
@@ -42,7 +44,10 @@
|
||||
"react-dom": "^19.0.0",
|
||||
"react-markdown": "^10.0.1",
|
||||
"react-router-dom": "^6.17.0",
|
||||
"react-syntax-highlighter": "^15.5.0",
|
||||
"rehype-katex": "^7.0.1",
|
||||
"remark-gfm": "^4.0.1",
|
||||
"remark-math": "^6.0.0",
|
||||
"sonner": "^2.0.1",
|
||||
"tailwind-merge": "^3.0.2",
|
||||
"tailwindcss-animate": "^1.0.7",
|
||||
@@ -61,6 +66,7 @@
|
||||
"@types/node": "^22.13.5",
|
||||
"@types/react": "^19.0.8",
|
||||
"@types/react-dom": "^19.0.3",
|
||||
"@types/react-syntax-highlighter": "^15.5.13",
|
||||
"@vitejs/plugin-react": "^4.3.4",
|
||||
"autoprefixer": "^10.4.20",
|
||||
"eslint": "^9.19.0",
|
||||
|
||||
6411
pnpm-lock.yaml
generated
6411
pnpm-lock.yaml
generated
File diff suppressed because it is too large
Load Diff
@@ -10,6 +10,7 @@ import {
|
||||
SheetHeader,
|
||||
SheetTitle,
|
||||
} from "@/components/ui/sheet";
|
||||
import { Skeleton } from "@/components/ui/skeleton";
|
||||
|
||||
function ThreadList({
|
||||
threads,
|
||||
@@ -55,8 +56,19 @@ function ThreadList({
|
||||
);
|
||||
}
|
||||
|
||||
function ThreadHistoryLoading() {
|
||||
return (
|
||||
<div className="h-full flex flex-col gap-2 items-start justify-start overflow-y-scroll [&::-webkit-scrollbar]:w-1.5 [&::-webkit-scrollbar-thumb]:rounded-full [&::-webkit-scrollbar-thumb]:bg-gray-300 [&::-webkit-scrollbar-track]:bg-transparent">
|
||||
{Array.from({ length: 30 }).map((_, i) => (
|
||||
<Skeleton key={`skeleton-${i}`} className="w-[264px] h-10" />
|
||||
))}
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export default function ThreadHistory() {
|
||||
const [threads, setThreads] = useState<Thread[]>([]);
|
||||
const [loading, setLoading] = useState<boolean>(false);
|
||||
const [chatHistoryOpen, setChatHistoryOpen] = useQueryParam(
|
||||
"chatHistoryOpen",
|
||||
BooleanParam,
|
||||
@@ -65,14 +77,19 @@ export default function ThreadHistory() {
|
||||
const { getThreads } = useThreads();
|
||||
|
||||
useEffect(() => {
|
||||
getThreads().then(setThreads).catch(console.error);
|
||||
if (typeof window === "undefined") return;
|
||||
setLoading(true);
|
||||
getThreads()
|
||||
.then(setThreads)
|
||||
.catch(console.error)
|
||||
.finally(() => setLoading(false));
|
||||
}, []);
|
||||
|
||||
return (
|
||||
<>
|
||||
<div className="hidden lg:flex flex-col border-r-[1px] border-slate-300 items-start justify-start gap-6 h-screen w-[300px] shrink-0 px-2 py-4 shadow-inner-right">
|
||||
<h1 className="text-2xl font-medium pl-4">Thread History</h1>
|
||||
<ThreadList threads={threads} />
|
||||
{loading ? <ThreadHistoryLoading /> : <ThreadList threads={threads} />}
|
||||
</div>
|
||||
<Sheet open={!!chatHistoryOpen} onOpenChange={setChatHistoryOpen}>
|
||||
<SheetContent side="left" className="lg:hidden flex">
|
||||
|
||||
@@ -9,15 +9,24 @@ import {
|
||||
} from "@assistant-ui/react-markdown";
|
||||
import ReactMarkdown from "react-markdown";
|
||||
import remarkGfm from "remark-gfm";
|
||||
import rehypeKatex from "rehype-katex";
|
||||
import remarkMath from "remark-math";
|
||||
import { FC, memo, useState } from "react";
|
||||
import { CheckIcon, CopyIcon } from "lucide-react";
|
||||
import { SyntaxHighlighter } from "@/components/thread/syntax-highlighter";
|
||||
|
||||
import { TooltipIconButton } from "@/components/thread/tooltip-icon-button";
|
||||
import { cn } from "@/lib/utils";
|
||||
|
||||
import "katex/dist/katex.min.css";
|
||||
|
||||
const MarkdownTextImpl = ({ children }: { children: string }) => {
|
||||
return (
|
||||
<ReactMarkdown remarkPlugins={[remarkGfm]} components={defaultComponents}>
|
||||
<ReactMarkdown
|
||||
remarkPlugins={[remarkGfm, remarkMath]}
|
||||
rehypePlugins={[rehypeKatex]}
|
||||
components={defaultComponents}
|
||||
>
|
||||
{children}
|
||||
</ReactMarkdown>
|
||||
);
|
||||
@@ -195,7 +204,7 @@ const defaultComponents = memoizeMarkdownComponents({
|
||||
pre: ({ className, ...props }) => (
|
||||
<pre
|
||||
className={cn(
|
||||
"overflow-x-auto rounded-b-lg bg-black p-4 text-white",
|
||||
"overflow-x-auto rounded-b-lg bg-black p-4 text-white max-w-4xl",
|
||||
className,
|
||||
)}
|
||||
{...props}
|
||||
@@ -211,4 +220,5 @@ const defaultComponents = memoizeMarkdownComponents({
|
||||
);
|
||||
},
|
||||
CodeHeader,
|
||||
SyntaxHighlighter,
|
||||
});
|
||||
|
||||
24
src/components/thread/syntax-highlighter.tsx
Normal file
24
src/components/thread/syntax-highlighter.tsx
Normal file
@@ -0,0 +1,24 @@
|
||||
import { PrismAsyncLight } from "react-syntax-highlighter";
|
||||
import { makePrismAsyncLightSyntaxHighlighter } from "@assistant-ui/react-syntax-highlighter";
|
||||
|
||||
import tsx from "react-syntax-highlighter/dist/esm/languages/prism/tsx";
|
||||
import python from "react-syntax-highlighter/dist/esm/languages/prism/python";
|
||||
|
||||
import { coldarkDark } from "react-syntax-highlighter/dist/cjs/styles/prism";
|
||||
|
||||
// register languages you want to support
|
||||
PrismAsyncLight.registerLanguage("js", tsx);
|
||||
PrismAsyncLight.registerLanguage("jsx", tsx);
|
||||
PrismAsyncLight.registerLanguage("ts", tsx);
|
||||
PrismAsyncLight.registerLanguage("tsx", tsx);
|
||||
PrismAsyncLight.registerLanguage("python", python);
|
||||
|
||||
export const SyntaxHighlighter = makePrismAsyncLightSyntaxHighlighter({
|
||||
style: coldarkDark,
|
||||
customStyle: {
|
||||
margin: 0,
|
||||
width: "100%",
|
||||
background: "transparent",
|
||||
padding: "1.5rem 1rem",
|
||||
},
|
||||
});
|
||||
13
src/components/ui/skeleton.tsx
Normal file
13
src/components/ui/skeleton.tsx
Normal file
@@ -0,0 +1,13 @@
|
||||
import { cn } from "@/lib/utils";
|
||||
|
||||
function Skeleton({ className, ...props }: React.ComponentProps<"div">) {
|
||||
return (
|
||||
<div
|
||||
data-slot="skeleton"
|
||||
className={cn("bg-primary/10 animate-pulse rounded-md", className)}
|
||||
{...props}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
export { Skeleton };
|
||||
Reference in New Issue
Block a user