Bug #14
Updated by Tomislav Pleše about 1 month ago
### **1. Submitting the First Prompt - Creating the Root Point** ``` USER ACTION: Types prompt in input field and presses Send ↓ PromptInputField._handleSendRequest() ↓ HomeScreen.onPrompt(promptText) - promptArgs = PromptArgs(currentPointId: '', parentPointId: null, isShardChild: false) ↓ HomeScreenManager.handlePrompt() ↓ ThreadManager.updateThreadMap() ↓ PointManager.createNewPoint() - Creates Point with id == parentPointId (ROOT) - Returns newPoint ↓ ThreadManager.updateThreadMap() [ROOT DETECTION] - if (newPoint.id == newPoint.parentPointId) - threadMap[newPoint.id] = newPoint - Returns newPoint ↓ HomeScreenManager.handlePrompt() - apiService.sendPromptToAi() - threadMap[updatedNewPoint.id] = updatedNewPoint - onMapUpdated() ↓ HomeScreen.onMapUpdated() - setState() - _flatTreeList = FlatTreeManager.buildFlatTreeList(threadMap) ↓ FlatTreeManager.buildFlatTreeList() - Finds root points (parentPointId == id) - _addRootPoint() → _addPrompt() - Creates TreeNodeModel for Prompt → _addResponse() - Creates TreeNodeModel for Response - Returns List<TreeNodeModel> ↓ HomeScreen.build() - TreeSliverThread(flatTreeList: _flatTreeList) ↓ TreeSliverThread.build() - SliverList.builder for each node in flatTreeList - TreeSliverItem() renders each card ↓ DISPLAY: Root Prompt + Root Response shown as cards ``` --- ### **2. Submitting the Second Prompt - Child of Root Point** ``` USER ACTION: Taps Root card to select it ↓ TreeSliverThread._handleNodeTap(node) - onNodeSelected(node.pointId) ↓ HomeScreen.onNodeSelected(currentPointId) - selectedPoint = threadMap[currentPointId] - setState() - promptArgs = PromptArgs( currentPointId: currentPointId, parentPointId: selectedPoint.parentPointId, isShardChild: false ) ↓ USER ACTION: Types new prompt and presses Send ↓ PromptInputField._handleSendRequest() ↓ HomeScreen.onPrompt(promptText) - currentPromptArgs uses the selected point's relationships ↓ HomeScreenManager.handlePrompt() ↓ ThreadManager.updateThreadMap() ↓ PointManager.createNewPoint() - Creates Point with parentPointId = Root's id - Returns newPoint ↓ ThreadManager.updateThreadMap() [REGULAR CHILD FLOW] - Not root (id != parentPointId) - Not isShardChild - parentShardId is empty - FLOW: Regular Point Child ↓ PointManager.updateParentPoint() - Adds newPoint.id to parentPoint.pointChildren[] - Updates parent in DB - Returns updatedParentPoint ↓ ThreadManager.updateThreadMap() - threadMap[newPoint.id] = newPoint - threadMap[updatedParentPoint.id] = updatedParentPoint - onMapUpdated() ↓ HomeScreen.onMapUpdated() - _flatTreeList = FlatTreeManager.buildFlatTreeList(threadMap) ↓ FlatTreeManager.buildFlatTreeList() - _addRootPoint() → _addPrompt() - Root Prompt → _addResponse() - Root Response → FOR each childId in root.pointChildren: → _addPointWithDescendants() → _addPrompt() - Child Prompt → _addResponse() - Child Response ↓ DISPLAY: Root cards + Second Point cards (indented) ``` --- ### **3. Submitting Sub-Prompt - Creating Shard from Second Point** ``` USER ACTION: Selects text in Second Point's Response card ↓ TreeSliverItem._buildSelectableText() - contextMenuBuilder adds "Sub-prompt" option ↓ USER ACTION: Taps "Sub-prompt" ↓ TreeSliverItem._handleSubPrompt(selectedText, selection) - Creates PromptArgs( currentPointId: node.pointId, parentPointId: node.pointId, parentShardId: node.shardId, isShardChild: true, selectedText: selectedText, startPosition: selection.start, endPosition: selection.end ) - prepareSubPromptInput(promptArgs) ↓ HomeScreen.prepareSubPromptInput(promptArgs) - setState() - this.promptArgs = promptArgs - promptInputFieldKey.currentState.setText(selectedText) ↓ USER ACTION: Modifies text and presses Send ↓ HomeScreen.onPrompt(promptText) - isSubPrompt = true - currentPromptArgs = promptArgs (with isShardChild: true) ↓ HomeScreenManager.handlePrompt() ↓ ThreadManager.updateThreadMap() ↓ PointManager.createNewPoint() - Creates Point with parentPointId = Second Point's id - parentShardId initially null/empty - Returns newPoint ↓ ThreadManager.updateThreadMap() [NEW SHARD CREATION FLOW] - isShardChild == true - selectedText != null - FLOW: New Shard Creation ↓ ShardManager.addShardToParentPoint() - Creates new Shard with: → anchor(startPosition, endPosition) → shardChildren = [newPoint.id] - Adds shard to parentPoint.shardsList[] - Updates parent in DB - Returns updatedParentPoint ↓ ThreadManager.updateThreadMap() - Gets parentShardId from updatedParentPoint - updatedNewPoint = newPoint.copyWith(parentShardId: parentShardId) - Updates newPoint in DB - threadMap[updatedNewPoint.id] = updatedNewPoint - threadMap[updatedParentPoint.id] = updatedParentPoint - onMapUpdated() ↓ HomeScreen.onMapUpdated() - _flatTreeList = FlatTreeManager.buildFlatTreeList(threadMap) ↓ FlatTreeManager.buildFlatTreeList() - _addRootPoint() → _addPrompt() - Root → _addResponse() - Root → _addPointWithDescendants() - Second Point: → _addPrompt() - Second Point Prompt → _addShardSegments() - Second Point Response SPLIT: → Creates TreeNodeModel(nodeType: shardResponse) - Shard 1 text → FOR each childId in shard.shardChildren: → _addPointWithDescendants() - Sub-Prompt Point → _addPrompt() - Sub-Prompt Prompt → _addResponse() - Sub-Prompt Response → Creates TreeNodeModel(nodeType: shardResponse, isLastShard: true) - Shard 2 text ↓ DISPLAY: Root cards + Second Point Prompt + Shard-1 + Sub-Prompt cards (indented) + Shard-2 ``` --- ### **4. Submitting Prompt Under First Child of a Shard** ``` USER ACTION: Taps Sub-Prompt Point card to select it ↓ TreeSliverThread._handleNodeTap(node) - onNodeSelected(node.pointId) ↓ HomeScreen.onNodeSelected(currentPointId) - selectedPoint = threadMap[currentPointId] - setState() - promptArgs = PromptArgs( currentPointId: currentPointId, parentPointId: selectedPoint.parentPointId, // Second Point's id parentShardId: selectedPoint.parentShardId, // Shard-1's id isShardChild: false ) ↓ USER ACTION: Types new prompt and presses Send ↓ HomeScreen.onPrompt(promptText) - isSubPrompt = false - currentPromptArgs uses selected point's relationships ↓ HomeScreenManager.handlePrompt() ↓ ThreadManager.updateThreadMap() ↓ PointManager.createNewPoint() - Creates Point with: → parentPointId = Second Point's id → parentShardId = Shard-1's id (from promptArgs) - Returns newPoint ↓ ThreadManager.updateThreadMap() [EXISTING SHARD CHILD FLOW] - Not isShardChild (false) - parentShardId != null and NOT empty - FLOW: Existing Shard Child ↓ ThreadManager.addChildToExistingShard() - Finds shard in parentPoint.shardsList where shardId == parentShardId - Adds newPoint.id to shard.shardChildren[] - Creates updatedShard with new child - Updates parentPoint.shardsList[] - Updates parent in DB - Returns updatedParentPoint ↓ ThreadManager.updateThreadMap() - threadMap[newPoint.id] = newPoint - threadMap[updatedParentPoint.id] = updatedParentPoint - onMapUpdated() ↓ HomeScreen.onMapUpdated() - _flatTreeList = FlatTreeManager.buildFlatTreeList(threadMap) ↓ FlatTreeManager.buildFlatTreeList() - _addRootPoint() → Second Point has shardsList → _addShardSegments(): → Shard-1 TreeNodeModel → FOR each childId in Shard-1.shardChildren: → _addPointWithDescendants() - Sub-Prompt Point (original) → _addPointWithDescendants() - NEW Point (sibling): → _addPrompt() - NEW Prompt → _addResponse() - NEW Response → Shard-2 TreeNodeModel ↓ DISPLAY: All previous cards + NEW Point cards (same level as Sub-Prompt, under Shard-1) ``` ------ ### **Key ** Key Class Responsibilities Summary:** Summary: ** | Class | Method | Responsibility | |:-----------------:|:-------------------------:|:--------------------------------------------------:| | PromptInputField | _handleSendRequest() | Validates and sends prompt text | | HomeScreen | onPrompt() | Determines prompt flow (root/child/subprompt) | | HomeScreen | onNodeSelected() | Updates promptArgs when user selects a node | | HomeScreen | prepareSubPromptInput() | Prepares input for sub-prompt (sharding) | | HomeScreenManager | handlePrompt() | Orchestrates prompt handling and API calls | | ThreadManager | updateThreadMap() | Routes to correct flow (root/child/shard/existing) | | PointManager | createNewPoint() | Creates new Point with correct relationships | | ShardManager | addShardToParentPoint() | Creates new shard with anchor | | ThreadManager | addChildToExistingShard() | Adds child to existing shard | | FlatTreeManager | buildFlatTreeList() | Converts threadMap to flat list of TreeNodeModel | | FlatTreeManager | _addShardSegments() | Splits response into shard segments | | TreeSliverThread | build() | Renders list of TreeSliverItems | | TreeSliverItem | build() | Renders individual card (Prompt or Response) | | TreeSliverItem | _handleSubPrompt() | Initiates sub-prompt creation flow |