Ten dokument opisuje permanentną konfigurację real-time streamingu bez buforowania w aplikacji Comet Gemini.
Wszystkie ustawienia znajdują się w pliku lib/streaming-config.ts.
export const STREAMING_CONFIG = {
ENABLE_BUFFERING: false, // ❌ Brak buforowania
ENABLE_MESSAGE_GROUPING: false, // ❌ Brak grupowania
ENABLE_ARGUMENT_CHUNKING: false, // ❌ Brak chunkowania
IMMEDIATE_PROCESSING: true, // ✅ Natychmiastowe przetwarzanie
}- Włączać buforowania - każdy event musi być przetwarzany natychmiast
- Grupować wiadomości - każdy fragment jako osobny element
- Dzielić argumentów na chunki - wysyłaj kompletny JSON
- Dodawać opóźnień - brak setTimeout, brak await przed renderowaniem
- Łączyć fragmentów - nie akumuluj tekstu przed wyświetleniem
// ✅ POPRAWNIE - natychmiastowe przetwarzanie JSON Lines
const lines = buffer.split('\n');
buffer = lines.pop() || ''; // Tylko niekompletna linia
for (const line of lines) {
if (!line.trim()) continue;
const data = JSON.parse(line); // Czysty JSON bez SSE prefix
// Natychmiastowa aktualizacja UI z flushSync
flushSync(() => setMessages(...));
}// ❌ ŹLE - buforowanie przed przetwarzaniem
let buffer = "";
while (processedUpTo < buffer.length) {
// Czekanie na więcej danych
}// ✅ POPRAWNIE - JSON Lines (każda linia = JSON + newline)
const sendEvent = (data: any) => {
const eventData = { ...data, timestamp: Date.now() };
const line = JSON.stringify(eventData) + '\n'; // Czysty JSON Lines
controller.enqueue(encoder.encode(line));
console.log(`[STREAM] Sent: ${data.type}`);
};
// Proste wywołania bez await
sendEvent({
type: "tool-argument-delta",
delta: argsStr, // Kompletny JSON
});// ❌ ŹLE - SSE format z "data: " prefix
const encoded = encoder.encode(`data: ${JSON.stringify(eventData)}\n\n`);
// To NIE jest JSON Lines!// ✅ POPRAWNIE - każda część osobno
<>
{message.parts.map((part, index) => (
<div key={`${message.id}-${index}`}>
{/* Każda część jako osobny element */}
</div>
))}
</>// ❌ ŹLE - grupowanie w kontener
<div className="flex flex-col gap-3">
{message.parts.map(...)}
</div>Plik lib/streaming-config.ts zawiera funkcję validateStreamingConfig(), która sprawdza poprawność konfiguracji przy każdym imporcie.
// Automatyczna walidacja
validateStreamingConfig();Jeśli konfiguracja jest niepoprawna, aplikacja rzuci błąd przy starcie.
Server (API)
↓
SSE Event (data: {...})
↓ controller.enqueue + setImmediate (flush)
Browser otrzymuje event
↓
Client (useCustomChat)
↓ split('\n') - natychmiast
Parse line
↓ flushSync + setMessages - natychmiast
React State
↓ render - natychmiastowy DOM update
UI (message.tsx)
↓ GPU layer repaint
Pojedynczy element (bez grupowania)
Każdy krok jest natychmiastowy - ZERO opóźnień, ZERO buforowania
- ❌ Buforowanie danych
- ❌ Chunking po 10 znaków
- ❌ Grupowanie wiadomości
- ❌ Opóźnienia w wyświetlaniu
- ✅ Real-time streaming
- ✅ Zero buforowania
- ✅ Brak grupowania
- ✅ Natychmiastowe wyświetlanie
| Data | Zmiana | Plik |
|---|---|---|
| 2025-10-03 | Usunięto buforowanie | lib/use-custom-chat.ts |
| 2025-10-03 | Usunięto chunking argumentów | app/api/chat/route.ts |
| 2025-10-03 | Usunięto grupowanie | components/message.tsx |
| 2025-10-03 | Dodano optymalne nagłówki | app/api/chat/route.ts |
| 2025-10-03 | Utworzono config | lib/streaming-config.ts |
| 2025-10-15 | Wymuszenie flush przez setImmediate | app/api/chat/route.ts |
| 2025-10-15 | Naprawa RealtimeMessage (usunięto zmienny key) | components/realtime-message.tsx |
Rozwiązanie: Sprawdź czy nie ma buforowania w useCustomChat.ts
Rozwiązanie: Sprawdź ENABLE_ARGUMENT_CHUNKING w konfiguracji
Rozwiązanie: Sprawdź ENABLE_MESSAGE_GROUPING w konfiguracji
- Server-Sent Events (SSE) standard: https://developer.mozilla.org/en-US/docs/Web/API/Server-sent_events
- React state updates: https://react.dev/learn/state-as-a-snapshot
- HTTP streaming headers: https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers
NIE MODYFIKUJ pliku lib/streaming-config.ts bez pełnego zrozumienia konsekwencji. Każda zmiana może zepsuć real-time streaming.
Jeśli musisz coś zmienić, najpierw:
- Przeczytaj tę dokumentację
- Zrozum architekturę streamingu
- Przetestuj zmiany lokalnie
- Sprawdź czy walidacja przechodzi