@retrivora-ai/rag-engine 1.7.6 → 1.7.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/server.mjs CHANGED
@@ -39,7 +39,7 @@ import {
39
39
  sseFrame,
40
40
  sseMetaFrame,
41
41
  sseTextFrame
42
- } from "./chunk-XGVKIPNY.mjs";
42
+ } from "./chunk-UHGYLTTY.mjs";
43
43
  import "./chunk-YLTMFW4M.mjs";
44
44
  import {
45
45
  PineconeProvider
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@retrivora-ai/rag-engine",
3
- "version": "1.7.6",
3
+ "version": "1.7.7",
4
4
  "description": "Retrivora AI is a plug-and-play AI engine for RAG chat experiences — generic vector DB + LLM provider, embeddable or standalone.",
5
5
  "author": "Abhinav Alkuchi",
6
6
  "license": "MIT",
@@ -9,6 +9,7 @@ import { ChatViewportSize } from '../types/props';
9
9
  import { SourceCard } from './SourceCard';
10
10
  import { ProductCarousel } from './ProductCarousel';
11
11
  import { DynamicChart } from './DynamicChart';
12
+ import { VisualizationRenderer } from './VisualizationRenderer';
12
13
 
13
14
  // ─── JSON sanitization ────────────────────────────────────────────────────────
14
15
  // Order matters: each step is a targeted fix, no step undoes a previous one.
@@ -988,6 +989,13 @@ export function MessageBubble({
988
989
  </ReactMarkdown>
989
990
  )}
990
991
 
992
+ {/* Automated UI Fallback (if LLM failed to output structured block but UITransformer found data) */}
993
+ {!isUser && !structuredContent.payload && message.uiTransformation && (
994
+ <div className="mt-4 border-t border-slate-100 dark:border-white/5 pt-4">
995
+ <VisualizationRenderer data={message.uiTransformation} />
996
+ </div>
997
+ )}
998
+
991
999
  {isStreaming && message.content && (
992
1000
  <span className="inline-block w-1.5 h-3.5 ml-1 bg-emerald-500 animate-pulse align-middle" />
993
1001
  )}
@@ -13,6 +13,7 @@ import { BatchProcessor, BatchOptions } from './BatchProcessor';
13
13
  import { EmbeddingStrategyResolver } from '../config/EmbeddingStrategy';
14
14
  import { QueryProcessor } from './QueryProcessor';
15
15
  import { IngestDocument, ChatResponse, VectorMatch, GraphSearchResult, RetrievalResult, UpsertDocument } from '../types';
16
+ import { UITransformer } from '../utils/UITransformer';
16
17
 
17
18
  // ─── LRU Embedding Cache ───────────────────────────────────────────────────────
18
19
 
@@ -230,6 +231,8 @@ Classify the query into ONE of the following intents:
230
231
  - ALWAYS return EXACTLY ONE \`\`\`ui\`\`\` block
231
232
  - JSON must be VALID
232
233
  - No explanation inside block
234
+ - NEVER use ASCII charts, Markdown tables, or text-based drawings for data.
235
+ - If data is tabular or statistical, ALWAYS use the \`\`\`ui\`\`\` block.
233
236
 
234
237
  ---
235
238
 
@@ -562,8 +565,18 @@ User: "distribution of products across categories"
562
565
  yield reply;
563
566
  }
564
567
 
565
- // Yield retrieval metadata at the end so UI can show sources
566
- yield { reply: '', sources, graphData };
568
+ // 6. Automated UI Fallback (UITransformer)
569
+ // This provides a secondary, rule-based visualization frame in case the LLM
570
+ // fails to adhere to the strict protocol or outputs a text fallback.
571
+ const uiTransformation = UITransformer.transform(question, sources);
572
+
573
+ // Yield retrieval metadata and automated UI transformation at the end
574
+ yield {
575
+ reply: '',
576
+ sources,
577
+ graphData,
578
+ ui_transformation: uiTransformation
579
+ } as ChatResponse;
567
580
 
568
581
  } catch (error) {
569
582
  throw new Error(`[Pipeline] Stream failed: ${error instanceof Error ? error.message : String(error)}`);
@@ -27,7 +27,8 @@ import { useStoredMessages } from './useStoredMessages';
27
27
  interface SseTextFrame { type: 'text'; text: string }
28
28
  interface SseMetaFrame { type: 'metadata'; sources?: VectorMatch[] }
29
29
  interface SseErrorFrame { type: 'error'; error: string }
30
- type SseFrame = SseTextFrame | SseMetaFrame | SseErrorFrame;
30
+ interface SseUiFrame { type: 'ui_transformation'; data: any }
31
+ type SseFrame = SseTextFrame | SseMetaFrame | SseErrorFrame | SseUiFrame;
31
32
 
32
33
  /**
33
34
  * Parse all complete SSE frames from a raw chunk string.
@@ -124,6 +125,7 @@ export function useRagChat(
124
125
  const decoder = new TextDecoder();
125
126
  let assistantContent = '';
126
127
  let sources: VectorMatch[] = [];
128
+ let uiTransformation: any = null;
127
129
  // Buffer for partial SSE frames that arrive split across reads
128
130
  let buffer = '';
129
131
 
@@ -157,6 +159,8 @@ export function useRagChat(
157
159
  assistantContent += frame.text;
158
160
  } else if (frame.type === 'metadata') {
159
161
  sources = frame.sources ?? [];
162
+ } else if (frame.type === 'ui_transformation') {
163
+ uiTransformation = frame.data;
160
164
  } else if (frame.type === 'error') {
161
165
  setError(frame.error || 'Stream error');
162
166
  }
@@ -166,7 +170,12 @@ export function useRagChat(
166
170
  setMessages((prev) =>
167
171
  prev.map((msg) =>
168
172
  msg.id === assistantMessageId
169
- ? { ...msg, content: assistantContent, sources: sources.length > 0 ? sources : msg.sources }
173
+ ? {
174
+ ...msg,
175
+ content: assistantContent,
176
+ sources: sources.length > 0 ? sources : msg.sources,
177
+ uiTransformation: uiTransformation || (msg as any).uiTransformation
178
+ }
170
179
  : msg
171
180
  )
172
181
  );
@@ -185,6 +194,7 @@ export function useRagChat(
185
194
  role: 'assistant',
186
195
  content: assistantContent,
187
196
  sources: sources.length > 0 ? sources : undefined,
197
+ uiTransformation: uiTransformation || undefined,
188
198
  createdAt: new Date().toISOString(),
189
199
  };
190
200
  onReply?.(finalAssistantMessage);
package/src/types/chat.ts CHANGED
@@ -10,6 +10,7 @@ export interface ChatMessage {
10
10
  export interface RagMessage extends ChatMessage {
11
11
  id: string;
12
12
  sources?: VectorMatch[];
13
+ uiTransformation?: any;
13
14
  createdAt: string;
14
15
  }
15
16