Skip to content

Enhance streaming logic to handle partial JSON objects properly #46

@isabelle-cedar

Description

@isabelle-cedar

Summary

Currently, when streaming partial JSON objects in chunks, they are incorrectly processed as plain text instead of being accumulated and parsed as complete JSON objects. This causes the intended object type handler to not be called for valid JSON objects that are split across multiple streaming chunks.

Problem Description

Location: /packages/cedar-os/src/store/agentConnection/agentUtils.ts lines 77-149 in the processDataContent function

Current Behavior:

  • When a JSON object is streamed in parts (e.g., first chunk: {, second chunk: "type": "action", third chunk: }), each chunk is individually parsed with JSON.parse()
  • Since partial JSON chunks are invalid JSON, they fall through to the plain text handler
  • The complete object is never reconstructed and handled as an object type

Expected Behavior:

  • When encountering a { character, the system should buffer subsequent chunks until a complete, valid JSON object is formed
  • Once valid JSON is detected, call the object type handler instead of treating it as text chunks
  • This should work similar to how complete objects are currently handled when streamed as single chunks

Code References

In /packages/cedar-os/src/store/agentConnection/agentUtils.ts:

// Lines 84-149: Current logic immediately tries JSON.parse on each chunk
try {
    const parsed = JSON.parse(data);
    // ... handle parsed object
} catch {
    // Falls back to treating as plain text - this is the problem
    if (data.trim() && data \!== '[DONE]' && data \!== 'done') {
        const processedContent = processContentChunk(data);
        currentTextMessage += processedContent;
        handler({ type: 'chunk', content: processedContent });
    }
}

Proposed Solution

  1. Add JSON Buffer System: Implement a buffer to accumulate potential JSON chunks
  2. Bracket Detection: When encountering {, start buffering mode
  3. Validation Loop: On each new chunk in buffer mode, attempt to parse the accumulated content
  4. Handler Dispatch: Once valid JSON is formed, call handler({ type: 'object', object: parsed })
  5. Fallback Mechanism: If buffer grows too large or contains invalid patterns, flush as text

Implementation Considerations

  • Track brace nesting level to handle nested objects
  • Set reasonable buffer size limits to prevent memory issues
  • Maintain compatibility with existing single-chunk object streaming
  • Ensure text chunks that aren't part of JSON objects continue to work normally

Acceptance Criteria

  • Partial JSON objects streamed across multiple chunks are properly reconstructed
  • Complete JSON objects trigger the object type handler instead of chunk handlers
  • Existing functionality for single-chunk objects remains unchanged
  • Text-only streaming continues to work as expected
  • Memory usage remains bounded even with malformed JSON streams

🤖 Generated with Claude Code

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions