From d1733f34e0da88e9f62128646bd4e5773b93981a Mon Sep 17 00:00:00 2001 From: simos Date: Sat, 1 Nov 2025 05:55:11 +0000 Subject: [PATCH] feat(chat): add CLAUDE.md support and fix scroll behavior Add system prompt configuration to enable CLAUDE.md loading from project, user config, and local directories. This allows Claude Code to use custom instructions defined in CLAUDE.md files. Fix scroll position management during message streaming to prevent conflicting with user's manual scroll actions. Remove automatic scroll state reset in scrollToBottom function and let scroll event handler manage the state naturally. Also remove debug logging for session ID capture. --- server/claude-sdk.js | 12 +++++++++++- src/components/ChatInterface.jsx | 12 ++++++++---- 2 files changed, 19 insertions(+), 5 deletions(-) diff --git a/server/claude-sdk.js b/server/claude-sdk.js index ca8c0da..9fea127 100644 --- a/server/claude-sdk.js +++ b/server/claude-sdk.js @@ -79,6 +79,16 @@ function mapCliOptionsToSDK(options = {}) { // Map model (default to sonnet) sdkOptions.model = options.model || 'sonnet'; + // Map system prompt configuration + sdkOptions.systemPrompt = { + type: 'preset', + preset: 'claude_code' // Required to use CLAUDE.md + }; + + // Map setting sources for CLAUDE.md loading + // This loads CLAUDE.md from project, user (~/.config/claude/CLAUDE.md), and local directories + sdkOptions.settingSources = ['project', 'user', 'local']; + // Map resume session if (sessionId) { sdkOptions.resume = sessionId; @@ -374,7 +384,7 @@ async function queryClaudeSDK(command, options = {}, ws) { for await (const message of queryInstance) { // Capture session ID from first message if (message.session_id && !capturedSessionId) { - console.log('📝 Captured session ID:', message.session_id); + capturedSessionId = message.session_id; addSession(capturedSessionId, queryInstance, tempImagePaths, tempDir); diff --git a/src/components/ChatInterface.jsx b/src/components/ChatInterface.jsx index f9c5e96..19d8eeb 100644 --- a/src/components/ChatInterface.jsx +++ b/src/components/ChatInterface.jsx @@ -2603,7 +2603,8 @@ function ChatInterface({ selectedProject, selectedSession, ws, sendMessage, mess const scrollToBottom = useCallback(() => { if (scrollContainerRef.current) { scrollContainerRef.current.scrollTop = scrollContainerRef.current.scrollHeight; - setIsUserScrolledUp(false); + // Don't reset isUserScrolledUp here - let the scroll handler manage it + // This prevents fighting with user's scroll position during streaming } }, []); @@ -3522,7 +3523,7 @@ function ChatInterface({ selectedProject, selectedSession, ws, sendMessage, mess const prevTop = scrollPositionRef.current.top; const newHeight = container.scrollHeight; const heightDiff = newHeight - prevHeight; - + // If content was added above the current view, adjust scroll position if (heightDiff > 0 && prevTop > 0) { container.scrollTop = prevTop + heightDiff; @@ -3536,9 +3537,12 @@ function ChatInterface({ selectedProject, selectedSession, ws, sendMessage, mess if (scrollContainerRef.current && chatMessages.length > 0 && !isLoadingSessionRef.current) { // Only scroll if we're not in the middle of loading a session // This prevents the "double scroll" effect during session switching - // Also reset scroll state + // Reset scroll state when switching sessions setIsUserScrolledUp(false); - setTimeout(() => scrollToBottom(), 200); // Delay to ensure full rendering + setTimeout(() => { + scrollToBottom(); + // After scrolling, the scroll event handler will naturally set isUserScrolledUp based on position + }, 200); // Delay to ensure full rendering } }, [selectedSession?.id, selectedProject?.name]); // Only trigger when session/project changes