MCPcopy Create free account
hub / github.com/Noumena-Network/code / extractFirstPromptFromChunk

Function extractFirstPromptFromChunk

src/utils/sessionStorage.ts:5088–5184  ·  view source on GitHub ↗

* Scans a chunk of text for the first meaningful user prompt.

(chunk: string)

Source from the content-addressed store, hash-verified

5086 * Scans a chunk of text for the first meaningful user prompt.
5087 */
5088function extractFirstPromptFromChunk(chunk: string): string {
5089 let start = 0
5090 let hasTickMessages = false
5091 let firstCommandFallback = ''
5092 while (start < chunk.length) {
5093 const newlineIdx = chunk.indexOf('\n', start)
5094 const line =
5095 newlineIdx >= 0 ? chunk.slice(start, newlineIdx) : chunk.slice(start)
5096 start = newlineIdx >= 0 ? newlineIdx + 1 : chunk.length
5097
5098 if (!line.includes('"type":"user"') && !line.includes('"type": "user"')) {
5099 continue
5100 }
5101 if (line.includes('"tool_result"')) continue
5102 if (line.includes('"isMeta":true') || line.includes('"isMeta": true'))
5103 continue
5104
5105 try {
5106 const entry = jsonParse(line) as Record<string, unknown>
5107 if (entry.type !== 'user') continue
5108
5109 const message = entry.message as Record<string, unknown> | undefined
5110 if (!message) continue
5111
5112 const content = message.content
5113 // Collect all text values from the message content. For array content
5114 // (common in VS Code where IDE metadata tags come before the user's
5115 // actual prompt), iterate all text blocks so we don't miss the real
5116 // prompt hidden behind <ide_selection>/<ide_opened_file> blocks.
5117 const texts: string[] = []
5118 if (typeof content === 'string') {
5119 texts.push(content)
5120 } else if (Array.isArray(content)) {
5121 for (const block of content) {
5122 const b = block as Record<string, unknown>
5123 if (b.type === 'text' && typeof b.text === 'string') {
5124 texts.push(b.text as string)
5125 }
5126 }
5127 }
5128
5129 for (const text of texts) {
5130 if (!text) continue
5131
5132 let result = text.replace(/\n/g, ' ').trim()
5133
5134 // Skip command messages (slash commands) but remember the first one
5135 // as a fallback title. Matches skip logic in
5136 // getFirstMeaningfulUserMessageTextContent, but instead of discarding
5137 // command messages entirely, we format them cleanly (e.g. "/clear")
5138 // so the session still appears in the resume picker.
5139 const commandNameTag = extractTag(result, COMMAND_NAME_TAG)
5140 if (commandNameTag) {
5141 const name = commandNameTag.replace(/^\//, '')
5142 const commandArgs = extractTag(result, 'command-args')?.trim() || ''
5143 if (builtInCommandNames().has(name) || !commandArgs) {
5144 if (!firstCommandFallback) {
5145 firstCommandFallback = commandNameTag

Callers 1

readLiteMetadataFunction · 0.85

Calls 3

jsonParseFunction · 0.85
extractTagFunction · 0.85
hasMethod · 0.45

Tested by

no test coverage detected