@nebula-ai/sdk 0.0.24 → 0.0.27

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/index.mjs CHANGED
@@ -1,10 +1,4 @@
1
1
  // src/types.ts
2
- var RetrievalType = /* @__PURE__ */ ((RetrievalType2) => {
3
- RetrievalType2["BASIC"] = "basic";
4
- RetrievalType2["ADVANCED"] = "advanced";
5
- RetrievalType2["CUSTOM"] = "custom";
6
- return RetrievalType2;
7
- })(RetrievalType || {});
8
2
  var GraphSearchResultType = /* @__PURE__ */ ((GraphSearchResultType2) => {
9
3
  GraphSearchResultType2["ENTITY"] = "entity";
10
4
  GraphSearchResultType2["RELATIONSHIP"] = "relationship";
@@ -161,10 +155,10 @@ var NebulaClient = class {
161
155
  }
162
156
  // Cluster Management Methods
163
157
  /** Create a new cluster */
164
- async createCluster(name, description, metadata) {
165
- const data = { name };
166
- if (description) data.description = description;
167
- if (metadata) data.metadata = metadata;
158
+ async createCluster(options) {
159
+ const data = { name: options.name };
160
+ if (options.description) data.description = options.description;
161
+ if (options.metadata) data.metadata = options.metadata;
168
162
  const response = await this._makeRequest("POST", "/v1/collections", data);
169
163
  const result = response.results || response;
170
164
  return this._clusterFromDict(result);
@@ -182,8 +176,11 @@ var NebulaClient = class {
182
176
  return this._clusterFromDict(result);
183
177
  }
184
178
  /** Get all clusters */
185
- async listClusters(limit = 100, offset = 0) {
186
- const params = { limit, offset };
179
+ async listClusters(options) {
180
+ const params = {
181
+ limit: options?.limit ?? 100,
182
+ offset: options?.offset ?? 0
183
+ };
187
184
  const response = await this._makeRequest("GET", "/v1/collections", void 0, params);
188
185
  let clusters;
189
186
  if (response.results) {
@@ -197,10 +194,13 @@ var NebulaClient = class {
197
194
  }
198
195
  // Conversations Methods
199
196
  /** List conversations for the authenticated user */
200
- async listConversations(limit = 100, offset = 0, cluster_ids) {
201
- const params = { limit, offset };
202
- if (cluster_ids && cluster_ids.length > 0) {
203
- params.collection_ids = cluster_ids;
197
+ async listConversations(options) {
198
+ const params = {
199
+ limit: options?.limit ?? 100,
200
+ offset: options?.offset ?? 0
201
+ };
202
+ if (options?.cluster_ids && options.cluster_ids.length > 0) {
203
+ params.collection_ids = options.cluster_ids;
204
204
  }
205
205
  const response = await this._makeRequest("GET", "/v1/conversations", void 0, params);
206
206
  let conversations;
@@ -286,12 +286,12 @@ var NebulaClient = class {
286
286
  });
287
287
  }
288
288
  /** Update a cluster */
289
- async updateCluster(clusterId, name, description, metadata) {
289
+ async updateCluster(options) {
290
290
  const data = {};
291
- if (name !== void 0) data.name = name;
292
- if (description !== void 0) data.description = description;
293
- if (metadata !== void 0) data.metadata = metadata;
294
- const response = await this._makeRequest("POST", `/v1/collections/${clusterId}`, data);
291
+ if (options.name !== void 0) data.name = options.name;
292
+ if (options.description !== void 0) data.description = options.description;
293
+ if (options.metadata !== void 0) data.metadata = options.metadata;
294
+ const response = await this._makeRequest("POST", `/v1/collections/${options.clusterId}`, data);
295
295
  const result = response.results || response;
296
296
  return this._clusterFromDict(result);
297
297
  }
@@ -454,11 +454,29 @@ var NebulaClient = class {
454
454
  }
455
455
  return results;
456
456
  }
457
- /** Delete a specific memory */
458
- async delete(memoryId) {
457
+ /** Delete one or more memories */
458
+ async delete(memoryIds) {
459
459
  try {
460
- await this._makeRequest("DELETE", `/v1/documents/${memoryId}`);
461
- return true;
460
+ if (typeof memoryIds === "string") {
461
+ try {
462
+ await this._makeRequest("DELETE", `/v1/documents/${memoryIds}`);
463
+ return true;
464
+ } catch {
465
+ try {
466
+ const response = await this._makeRequest("POST", "/v1/documents/delete", {
467
+ ids: memoryIds
468
+ });
469
+ return typeof response === "object" && response.success !== void 0 ? response.success : true;
470
+ } catch (error) {
471
+ throw error;
472
+ }
473
+ }
474
+ } else {
475
+ const response = await this._makeRequest("POST", "/v1/documents/delete", {
476
+ ids: memoryIds
477
+ });
478
+ return response;
479
+ }
462
480
  } catch (error) {
463
481
  if (error instanceof Error) {
464
482
  throw error;
@@ -479,12 +497,16 @@ var NebulaClient = class {
479
497
  }
480
498
  }
481
499
  /** Get all memories from specific clusters */
482
- async listMemories(clusterIds, limit = 100, offset = 0) {
483
- const ids = Array.isArray(clusterIds) ? clusterIds : [clusterIds];
500
+ async listMemories(options) {
501
+ const ids = Array.isArray(options.cluster_ids) ? options.cluster_ids : [options.cluster_ids];
484
502
  if (!ids.length) {
485
503
  throw new NebulaClientException("cluster_ids must be provided to list_memories().");
486
504
  }
487
- const params = { limit, offset, collection_ids: ids };
505
+ const params = {
506
+ limit: options.limit ?? 100,
507
+ offset: options.offset ?? 0,
508
+ collection_ids: ids
509
+ };
488
510
  const response = await this._makeRequest("GET", "/v1/documents", void 0, params);
489
511
  let documents;
490
512
  if (response.results) {
@@ -511,32 +533,122 @@ var NebulaClient = class {
511
533
  return this._memoryResponseFromDict(memoryData, []);
512
534
  }
513
535
  // Search Methods
514
- /** Search within specific clusters */
515
- async search(query, clusters, limitOrOptions, retrievalType = "advanced" /* ADVANCED */, filters, searchSettings) {
516
- const clusterIds = Array.isArray(clusters) ? clusters : [clusters];
536
+ /**
537
+ * Search within specific clusters with optional metadata filtering.
538
+ *
539
+ * @param options - Search configuration
540
+ * @param options.query - Search query string
541
+ * @param options.cluster_ids - One or more cluster IDs to search within
542
+ * @param options.limit - Maximum number of results to return (default: 10)
543
+ * @param options.retrieval_type - Retrieval strategy (default: ADVANCED)
544
+ * @param options.filters - Optional filters to apply to the search. Supports comprehensive metadata filtering
545
+ * with MongoDB-like operators for both vector/chunk search and graph search.
546
+ * @param options.searchSettings - Optional search configuration
547
+ *
548
+ * @returns Promise resolving to array of SearchResult objects containing both vector/chunk and graph search results
549
+ *
550
+ * @example
551
+ * // Basic equality filter
552
+ * await client.search({
553
+ * query: "machine learning",
554
+ * cluster_ids: ["research-cluster"],
555
+ * filters: {
556
+ * "metadata.category": { $eq: "research" },
557
+ * "metadata.verified": true // Shorthand for $eq
558
+ * }
559
+ * });
560
+ *
561
+ * @example
562
+ * // Numeric comparisons
563
+ * await client.search({
564
+ * query: "high priority",
565
+ * cluster_ids: ["tasks"],
566
+ * filters: {
567
+ * "metadata.priority": { $gte: 8 },
568
+ * "metadata.score": { $lt: 100 }
569
+ * }
570
+ * });
571
+ *
572
+ * @example
573
+ * // String matching
574
+ * await client.search({
575
+ * query: "employees",
576
+ * cluster_ids: ["team"],
577
+ * filters: {
578
+ * "metadata.email": { $ilike: "%@company.com" } // Case-insensitive
579
+ * }
580
+ * });
581
+ *
582
+ * @example
583
+ * // Array operations
584
+ * await client.search({
585
+ * query: "developers",
586
+ * cluster_ids: ["team"],
587
+ * filters: {
588
+ * "metadata.skills": { $overlap: ["python", "typescript"] } // Has any
589
+ * }
590
+ * });
591
+ *
592
+ * @example
593
+ * // Nested paths
594
+ * await client.search({
595
+ * query: "users",
596
+ * cluster_ids: ["profiles"],
597
+ * filters: {
598
+ * "metadata.user.preferences.theme": { $eq: "dark" }
599
+ * }
600
+ * });
601
+ *
602
+ * @example
603
+ * // Complex logical combinations
604
+ * await client.search({
605
+ * query: "candidates",
606
+ * cluster_ids: ["hiring"],
607
+ * filters: {
608
+ * $and: [
609
+ * { "metadata.verified": true },
610
+ * { "metadata.level": { $gte: 5 } },
611
+ * {
612
+ * $or: [
613
+ * { "metadata.skills": { $overlap: ["python", "go"] } },
614
+ * { "metadata.years_experience": { $gte: 8 } }
615
+ * ]
616
+ * }
617
+ * ]
618
+ * }
619
+ * });
620
+ *
621
+ * @remarks
622
+ * Supported Operators:
623
+ * - Comparison: $eq, $ne, $lt, $lte, $gt, $gte
624
+ * - String: $like (case-sensitive), $ilike (case-insensitive)
625
+ * - Array: $in, $nin, $overlap, $contains
626
+ * - JSONB: $json_contains
627
+ * - Logical: $and, $or
628
+ *
629
+ * For comprehensive filtering documentation, see the Metadata Filtering Guide:
630
+ * https://docs.nebulacloud.app/guides/metadata-filtering
631
+ */
632
+ async search(options) {
633
+ const clusterIds = Array.isArray(options.cluster_ids) ? options.cluster_ids : [options.cluster_ids];
517
634
  if (!clusterIds.length) {
518
635
  throw new NebulaClientException("cluster_ids must be provided to search().");
519
636
  }
520
- let limit = 10;
521
- if (typeof limitOrOptions === "number") {
522
- limit = limitOrOptions;
523
- } else if (typeof limitOrOptions === "object" && limitOrOptions) {
524
- if (typeof limitOrOptions.limit === "number") limit = limitOrOptions.limit;
525
- }
526
- if (typeof retrievalType === "string") {
527
- retrievalType = RetrievalType[retrievalType.toUpperCase()] || "advanced" /* ADVANCED */;
528
- }
529
- const effectiveSettings = { ...searchSettings };
637
+ const limit = options.limit ?? 10;
638
+ const searchMode = options.search_mode ?? "super";
639
+ const effectiveSettings = {
640
+ ...options.searchSettings
641
+ };
530
642
  effectiveSettings.limit = limit;
531
643
  const userFilters = { ...effectiveSettings.filters };
532
- if (filters) {
533
- Object.assign(userFilters, filters);
644
+ if (options.filters) {
645
+ Object.assign(userFilters, options.filters);
534
646
  }
535
647
  userFilters.collection_ids = { $overlap: clusterIds };
536
648
  effectiveSettings.filters = userFilters;
537
649
  const data = {
538
- query,
539
- search_mode: "custom",
650
+ query: options.query,
651
+ search_mode: searchMode,
540
652
  search_settings: effectiveSettings
541
653
  };
542
654
  const response = await this._makeRequest("POST", "/v1/retrieval/search", data);
@@ -570,7 +682,12 @@ Assistant: ${String(assistantMessage || "")}`;
570
682
  if (sessionId && !includeAllSessions) {
571
683
  filters["metadata.session_id"] = sessionId;
572
684
  }
573
- return this.search(query, [clusterId], { limit: 10 }, "advanced" /* ADVANCED */, filters);
685
+ return this.search({
686
+ query,
687
+ cluster_ids: [clusterId],
688
+ limit: 10,
689
+ filters
690
+ });
574
691
  }
575
692
  // Health Check
576
693
  async healthCheck() {
@@ -666,6 +783,23 @@ Assistant: ${String(assistantMessage || "")}`;
666
783
  const score = data.score !== void 0 ? Number(data.score) : 0;
667
784
  const metadata = data.metadata || {};
668
785
  const chunkIds = Array.isArray(data.chunk_ids) ? data.chunk_ids : void 0;
786
+ let timestamp;
787
+ if (data.timestamp) {
788
+ if (typeof data.timestamp === "string") {
789
+ timestamp = data.timestamp;
790
+ } else if (data.timestamp instanceof Date) {
791
+ timestamp = data.timestamp.toISOString();
792
+ } else {
793
+ const parsed = new Date(data.timestamp);
794
+ if (!Number.isNaN(parsed.valueOf())) {
795
+ timestamp = parsed.toISOString();
796
+ }
797
+ }
798
+ }
799
+ const displayName = typeof data.display_name === "string" ? data.display_name : void 0;
800
+ const sourceRole = typeof data.source_role === "string" ? data.source_role : void 0;
801
+ const documentId = data.document_id ? String(data.document_id) : void 0;
802
+ const ownerId = data.owner_id ? String(data.owner_id) : void 0;
669
803
  let entity;
670
804
  let rel;
671
805
  let comm;
@@ -705,7 +839,12 @@ Assistant: ${String(assistantMessage || "")}`;
705
839
  graph_entity: entity,
706
840
  graph_relationship: rel,
707
841
  graph_community: comm,
708
- chunk_ids: chunkIds
842
+ chunk_ids: chunkIds,
843
+ timestamp,
844
+ display_name: displayName,
845
+ source_role: sourceRole,
846
+ document_id: documentId,
847
+ owner_id: ownerId
709
848
  };
710
849
  }
711
850
  async _sha256(message) {
@@ -724,6 +863,6 @@ Assistant: ${String(assistantMessage || "")}`;
724
863
  }
725
864
  };
726
865
 
727
- export { GraphSearchResultType, NebulaAuthenticationException, NebulaClient, NebulaClientException, NebulaClusterNotFoundException, NebulaException, NebulaRateLimitException, NebulaValidationException, RetrievalType };
866
+ export { GraphSearchResultType, NebulaAuthenticationException, NebulaClient, NebulaClientException, NebulaClusterNotFoundException, NebulaException, NebulaRateLimitException, NebulaValidationException };
728
867
  //# sourceMappingURL=index.mjs.map
729
868
  //# sourceMappingURL=index.mjs.map
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/types.ts","../src/client.ts"],"names":["RetrievalType","GraphSearchResultType","response"],"mappings":"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","file":"index.mjs","sourcesContent":["// Data models matching the actual Nebula Python SDK exactly\n\n// Enums\nexport enum RetrievalType {\n BASIC = \"basic\",\n ADVANCED = \"advanced\",\n CUSTOM = \"custom\"\n}\n\nexport enum GraphSearchResultType {\n ENTITY = \"entity\",\n RELATIONSHIP = \"relationship\",\n COMMUNITY = \"community\"\n}\n\n// Core interfaces matching Python SDK exactly\nexport interface MemoryResponse {\n id: string;\n content?: string;\n chunks?: string[];\n metadata: Record<string, any>;\n cluster_ids: string[];\n created_at?: string;\n updated_at?: string;\n}\n\nexport interface Memory {\n cluster_id: string;\n content: string;\n role?: string; // user, assistant, or custom\n parent_id?: string;\n metadata: Record<string, any>;\n}\n\nexport interface Cluster {\n id: string;\n name: string;\n description?: string;\n metadata: Record<string, any>;\n created_at?: string;\n updated_at?: string;\n memory_count: number;\n owner_id?: string;\n}\n\nexport interface SearchResult {\n id: string;\n score: number;\n metadata: Record<string, any>;\n source?: string;\n\n // Chunk fields\n content?: string;\n\n // Graph variant discriminator and payload\n graph_result_type?: GraphSearchResultType;\n graph_entity?: GraphEntityResult;\n graph_relationship?: GraphRelationshipResult;\n graph_community?: GraphCommunityResult;\n chunk_ids?: string[];\n}\n\nexport interface GraphEntityResult {\n id?: string;\n name: string;\n description: string;\n metadata: Record<string, any>;\n}\n\nexport interface GraphRelationshipResult {\n id?: string;\n subject: string;\n predicate: string;\n object: string;\n subject_id?: string;\n object_id?: string;\n description?: string;\n metadata: Record<string, any>;\n}\n\nexport interface GraphCommunityResult {\n id?: string;\n name: string;\n summary: string;\n metadata: Record<string, any>;\n}\n\nexport interface AgentResponse {\n content: string;\n agent_id: string;\n conversation_id?: string;\n metadata: Record<string, any>;\n citations: Record<string, any>[];\n}\n\nexport interface SearchOptions {\n limit: number;\n filters?: Record<string, any>;\n retrieval_type: RetrievalType;\n}\n\n// Configuration interface\nexport interface NebulaClientConfig {\n apiKey: string;\n baseUrl?: string;\n timeout?: number;\n}\n\n// Error types matching Python SDK\nexport class NebulaException extends Error {\n constructor(\n message: string,\n public statusCode?: number,\n public details?: any\n ) {\n super(message);\n this.name = 'NebulaException';\n }\n}\n\nexport class NebulaClientException extends NebulaException {\n constructor(message: string, public cause?: Error) {\n super(message);\n this.name = 'NebulaClientException';\n }\n}\n\nexport class NebulaAuthenticationException extends NebulaException {\n constructor(message: string = 'Invalid API key') {\n super(message, 401);\n this.name = 'NebulaAuthenticationException';\n }\n}\n\nexport class NebulaRateLimitException extends NebulaException {\n constructor(message: string = 'Rate limit exceeded') {\n super(message, 429);\n this.name = 'NebulaRateLimitException';\n }\n}\n\nexport class NebulaValidationException extends NebulaException {\n constructor(message: string = 'Validation error', public details?: any) {\n super(message, 400);\n this.name = 'NebulaValidationException';\n }\n}\n\nexport class NebulaClusterNotFoundException extends NebulaException {\n constructor(message: string = 'Cluster not found') {\n super(message, 404);\n this.name = 'NebulaClusterNotFoundException';\n }\n}\n","import {\n Memory,\n MemoryResponse,\n Cluster,\n SearchResult,\n RetrievalType,\n GraphSearchResultType,\n GraphEntityResult,\n GraphRelationshipResult,\n GraphCommunityResult,\n NebulaClientConfig,\n NebulaException,\n NebulaClientException,\n NebulaAuthenticationException,\n NebulaRateLimitException,\n NebulaValidationException,\n} from './types';\n\n/**\n * Official Nebula JavaScript/TypeScript SDK\n * Mirrors the exact Nebula Python SDK client.py implementation\n */\nexport class NebulaClient {\n private apiKey: string;\n private baseUrl: string;\n private timeout: number;\n\n constructor(config: NebulaClientConfig) {\n this.apiKey = config.apiKey;\n if (!this.apiKey) {\n throw new NebulaClientException(\n 'API key is required. Pass it to the constructor or set NEBULA_API_KEY environment variable.'\n );\n }\n\n this.baseUrl = (config.baseUrl || 'https://api.nebulacloud.app').replace(/\\/$/, '');\n this.timeout = config.timeout || 30000;\n }\n\n // Public mutators used by tests\n setApiKey(next: string) {\n this.apiKey = next;\n }\n setBaseUrl(next: string) {\n this.baseUrl = (next || this.baseUrl).replace(/\\/$/, '');\n }\n // Kept for backwards-compat tests; no-op in current implementation\n setCorsProxy(_next: string) {\n // no-op\n }\n\n /** Check if API key is set */\n isApiKeySet(): boolean {\n return !!(this.apiKey && this.apiKey.trim() !== '');\n }\n\n /** Detect if a token looks like a Nebula API key (public.raw) */\n private _isNebulaApiKey(token?: string): boolean {\n const candidate = token || this.apiKey;\n if (!candidate) return false;\n const parts = candidate.split('.');\n if (parts.length !== 2) return false;\n const [publicPart, rawPart] = parts;\n return publicPart.startsWith('key_') && !!rawPart && rawPart.length > 0;\n }\n\n /** Build authentication headers */\n private _buildAuthHeaders(includeContentType: boolean = true): Record<string, string> {\n const headers: Record<string, string> = {};\n\n if (this._isNebulaApiKey()) {\n headers['X-API-Key'] = this.apiKey;\n } else {\n headers['Authorization'] = `Bearer ${this.apiKey}`;\n }\n\n if (includeContentType) {\n headers['Content-Type'] = 'application/json';\n }\n\n return headers;\n }\n\n /** Make an HTTP request to the Nebula API */\n private async _makeRequest(\n method: string,\n endpoint: string,\n jsonData?: Record<string, any>,\n params?: Record<string, any>\n ): Promise<any> {\n const url = new URL(endpoint, this.baseUrl);\n\n if (params) {\n console.log('SDK: _makeRequest params before processing:', params);\n Object.entries(params).forEach(([key, value]) => {\n if (value !== undefined && value !== null) {\n // Handle array parameters (e.g., collection_ids)\n if (Array.isArray(value)) {\n console.log(`SDK: Adding array param ${key}:`, value);\n value.forEach((item) => {\n url.searchParams.append(key, String(item));\n console.log(`SDK: Appended ${key}=${item} to URL`);\n });\n } else {\n console.log(`SDK: Adding single param ${key}:`, value);\n url.searchParams.append(key, String(value));\n }\n }\n });\n }\n\n console.log('SDK: Final URL being requested:', url.toString());\n\n const headers = this._buildAuthHeaders(true);\n\n const controller = new AbortController();\n const timeoutId = setTimeout(() => controller.abort(), this.timeout);\n\n try {\n const response = await fetch(url.toString(), {\n method,\n headers,\n body: jsonData ? JSON.stringify(jsonData) : undefined,\n signal: controller.signal,\n });\n\n clearTimeout(timeoutId);\n\n if (response.status === 200) {\n return await response.json();\n } else if (response.status === 401) {\n throw new NebulaAuthenticationException('Invalid API key');\n } else if (response.status === 429) {\n throw new NebulaRateLimitException('Rate limit exceeded');\n } else if (response.status === 400) {\n const errorData = await response.json().catch(() => ({}));\n throw new NebulaValidationException(errorData.message || 'Validation error', errorData.details);\n } else {\n const errorData = await response.json().catch(() => ({}));\n throw new NebulaException(errorData.message || `API error: ${response.status}`, response.status, errorData);\n }\n } catch (error) {\n clearTimeout(timeoutId);\n\n if (error instanceof NebulaException) {\n throw error;\n }\n\n if (error instanceof Error && error.name === 'AbortError') {\n throw new NebulaClientException(`Request timed out after ${this.timeout} milliseconds`);\n }\n\n if (error instanceof Error) {\n throw new NebulaClientException(`Request failed: ${error.message}`, error);\n }\n\n throw new NebulaClientException(`Request failed: ${String(error)}`);\n }\n }\n\n // Cluster Management Methods\n\n /** Create a new cluster */\n async createCluster(\n name: string,\n description?: string,\n metadata?: Record<string, any>\n ): Promise<Cluster> {\n const data: Record<string, any> = { name };\n if (description) data.description = description;\n if (metadata) data.metadata = metadata;\n\n const response = await this._makeRequest('POST', '/v1/collections', data);\n const result = response.results || response;\n return this._clusterFromDict(result);\n }\n\n /** Get a specific cluster by ID */\n async getCluster(clusterId: string): Promise<Cluster> {\n const response = await this._makeRequest('GET', `/v1/collections/${clusterId}`);\n const result = response.results || response;\n return this._clusterFromDict(result);\n }\n\n /** Get a specific cluster by name */\n async getClusterByName(name: string): Promise<Cluster> {\n const response = await this._makeRequest('GET', `/v1/collections/name/${name}`);\n const result = response.results || response;\n return this._clusterFromDict(result);\n }\n\n /** Get all clusters */\n async listClusters(limit: number = 100, offset: number = 0): Promise<Cluster[]> {\n const params = { limit, offset };\n const response = await this._makeRequest('GET', '/v1/collections', undefined, params);\n\n let clusters: any[];\n if (response.results) {\n clusters = response.results;\n } else if (Array.isArray(response)) {\n clusters = response;\n } else {\n clusters = [response];\n }\n\n return clusters.map((cluster) => this._clusterFromDict(cluster));\n }\n\n // Conversations Methods\n\n /** List conversations for the authenticated user */\n async listConversations(limit: number = 100, offset: number = 0, cluster_ids?: string[]): Promise<any[]> {\n const params: Record<string, any> = { limit, offset };\n // Convert cluster_ids to collection_ids for the API\n if (cluster_ids && cluster_ids.length > 0) {\n params.collection_ids = cluster_ids;\n }\n const response = await this._makeRequest('GET', '/v1/conversations', undefined, params);\n\n let conversations: any[];\n if (response && response.results) {\n conversations = response.results;\n } else if (Array.isArray(response)) {\n conversations = response;\n } else {\n conversations = response ? [response] : [];\n }\n\n return conversations;\n }\n\n /** Get conversation messages directly from the conversations API */\n async getConversationMessages(conversationId: string): Promise<MemoryResponse[]>;\n async getConversationMessages(conversationIds: string[]): Promise<Record<string, MemoryResponse[]>>;\n async getConversationMessages(conversationIdOrIds: string | string[]): Promise<MemoryResponse[] | Record<string, MemoryResponse[]>> {\n // Handle single conversation ID (backward compatibility)\n if (typeof conversationIdOrIds === 'string') {\n const response = await this._makeRequest('GET', `/v1/conversations/${conversationIdOrIds}`);\n\n if (!response || !response.results) {\n return [];\n }\n\n return this._transformConversationMessages(response.results);\n }\n\n // Handle multiple conversation IDs\n if (!Array.isArray(conversationIdOrIds) || conversationIdOrIds.length === 0) {\n return {};\n }\n\n // Use POST request with conversation IDs in body for batch retrieval\n // This performs a single SQL query with IN clause for optimal performance\n const response = await this._makeRequest('POST', '/v1/conversations/batch', {\n conversation_ids: conversationIdOrIds\n });\n\n console.log('🔍 SDK: Raw batch response:', response);\n console.log('🔍 SDK: Response has results?', !!response?.results);\n if (response?.results) {\n console.log('🔍 SDK: Results keys:', Object.keys(response.results));\n console.log('🔍 SDK: Sample result:', Object.keys(response.results)[0], ':', response.results[Object.keys(response.results)[0]]);\n }\n\n const results: Record<string, MemoryResponse[]> = {};\n\n if (response && response.results) {\n // Backend returns { \"results\": { \"results\": { conversation_id: MessageResponse[] } } } format (double-nested)\n const batchResults = response.results.results || response.results;\n console.log('🔍 SDK: Processing', Object.keys(batchResults).length, 'conversations');\n for (const [conversationId, messages] of Object.entries(batchResults)) {\n if (Array.isArray(messages)) {\n const transformed = this._transformConversationMessages(messages as any[]);\n results[conversationId] = transformed;\n console.log(`🔍 SDK: Conversation ${conversationId.slice(-8)}: ${messages.length} raw -> ${transformed.length} transformed`);\n } else {\n results[conversationId] = [];\n console.log(`🔍 SDK: Conversation ${conversationId.slice(-8)}: not array, setting empty`);\n }\n }\n }\n\n // Ensure all requested conversation IDs are present in results (even if empty)\n for (const conversationId of conversationIdOrIds) {\n if (!(conversationId in results)) {\n results[conversationId] = [];\n }\n }\n\n return results;\n }\n\n /** Helper method to transform conversation messages to MemoryResponse format */\n private _transformConversationMessages(messageResponses: any[]): MemoryResponse[] {\n return messageResponses.map((msgResp: any) => {\n const msgId = String(msgResp.id || '');\n const msg = msgResp.message || {}; // The actual Message object\n const metadata = msgResp.metadata || {};\n\n // Normalize content to a string - could be string or object\n let text: string = '';\n const rawContent = msg.content;\n if (typeof rawContent === 'string') {\n text = rawContent;\n } else if (rawContent && typeof rawContent === 'object') {\n // Handle structured content\n text = String(rawContent.content || rawContent.text || JSON.stringify(rawContent));\n } else if (rawContent != null) {\n text = String(rawContent);\n }\n\n // Get role from the Message object\n const role = msg.role || metadata.role || 'user';\n\n // Merge message metadata with response metadata\n const combinedMetadata = {\n ...metadata,\n role, // Ensure role is in metadata for UI compatibility\n };\n\n return {\n id: msgId,\n content: text,\n metadata: combinedMetadata,\n created_at: msgResp.created_at,\n cluster_ids: msgResp.collection_ids || [],\n } as MemoryResponse;\n });\n }\n\n /** Update a cluster */\n async updateCluster(\n clusterId: string,\n name?: string,\n description?: string,\n metadata?: Record<string, any>\n ): Promise<Cluster> {\n const data: Record<string, any> = {};\n if (name !== undefined) data.name = name;\n if (description !== undefined) data.description = description;\n if (metadata !== undefined) data.metadata = metadata;\n\n const response = await this._makeRequest('POST', `/v1/collections/${clusterId}`, data);\n const result = response.results || response;\n return this._clusterFromDict(result);\n }\n\n /** Delete a cluster */\n async deleteCluster(clusterId: string): Promise<boolean> {\n await this._makeRequest('DELETE', `/v1/collections/${clusterId}`);\n return true;\n }\n\n // Memory Management Methods\n\n /**\n * Legacy convenience: store raw text content into a cluster as a document\n */\n async store(content: string, clusterId: string, metadata: Record<string, any> = {}): Promise<MemoryResponse> {\n const docMetadata = {\n ...metadata,\n memory_type: 'memory',\n timestamp: new Date().toISOString(),\n } as Record<string, any>;\n\n const data = {\n metadata: JSON.stringify(docMetadata),\n ingestion_mode: 'fast',\n collection_ids: JSON.stringify([clusterId]),\n raw_text: String(content || ''),\n } as const;\n\n const url = `${this.baseUrl}/v1/documents`;\n const headers = this._buildAuthHeaders(false);\n\n const response = await fetch(url, {\n method: 'POST',\n headers,\n body: this._formDataFromObject(data as any),\n });\n\n if (!response.ok) {\n const errorData = await response.json().catch(() => ({}));\n throw new NebulaException(\n errorData.message || `Failed to create document: ${response.status}`,\n response.status,\n errorData\n );\n }\n\n const respData = await response.json();\n const id = respData?.results?.document_id || respData?.results?.id || respData?.id || '';\n\n const result: MemoryResponse = {\n id: String(id),\n content: String(content || ''),\n metadata: docMetadata,\n cluster_ids: [clusterId],\n created_at: docMetadata.timestamp,\n updated_at: docMetadata.timestamp,\n };\n return result;\n }\n\n /** Store a single memory */\n async storeMemory(memory: Memory | Record<string, any>): Promise<string> {\n let mem: Memory;\n\n if ('cluster_id' in memory) {\n mem = memory as Memory;\n } else {\n mem = {\n cluster_id: (memory as any).cluster_id,\n content: (memory as any).content,\n role: (memory as any).role,\n parent_id: (memory as any).parent_id,\n metadata: (memory as any).metadata || {},\n };\n }\n\n // Conversation mode\n if (mem.role) {\n let convId = mem.parent_id;\n if (!convId) {\n const created = await this._makeRequest('POST', '/v1/conversations', {});\n const conv = created.results || created;\n convId = conv.id;\n if (!convId) {\n throw new NebulaClientException('Failed to create conversation: no id returned');\n }\n }\n\n const payload = {\n messages: [\n {\n content: String(mem.content),\n role: mem.role,\n metadata: mem.metadata,\n },\n ],\n collection_id: mem.cluster_id,\n } as const;\n\n await this._makeRequest('POST', `/v1/conversations/${convId}/messages`, payload);\n return String(convId);\n }\n\n // Text/JSON memory mode\n const contentText = String(mem.content || '');\n const contentHash = await this._sha256(contentText);\n const docMetadata = { ...mem.metadata } as Record<string, any>;\n docMetadata.memory_type = 'memory';\n docMetadata.content_hash = contentHash;\n\n const data = {\n metadata: JSON.stringify(docMetadata),\n ingestion_mode: 'fast',\n collection_ids: JSON.stringify([mem.cluster_id]),\n raw_text: contentText,\n } as const;\n\n const url = `${this.baseUrl}/v1/documents`;\n const headers = this._buildAuthHeaders(false);\n\n const response = await fetch(url, {\n method: 'POST',\n headers,\n body: this._formDataFromObject(data as any),\n });\n\n if (!response.ok) {\n const errorData = await response.json().catch(() => ({}));\n throw new NebulaException(\n errorData.message || `Failed to create document: ${response.status}`,\n response.status,\n errorData\n );\n }\n\n const respData = await response.json();\n if (respData.results) {\n if (respData.results.document_id) return String(respData.results.document_id);\n if (respData.results.id) return String(respData.results.id);\n }\n return '';\n }\n\n /** Store multiple memories */\n async storeMemories(memories: Memory[]): Promise<string[]> {\n const results: string[] = [];\n const convGroups: Record<string, Memory[]> = {};\n const others: Memory[] = [];\n\n for (const m of memories) {\n if (m.role) {\n const key = m.parent_id || `__new__::${m.cluster_id}`;\n if (!convGroups[key]) convGroups[key] = [];\n convGroups[key].push(m);\n } else {\n others.push(m);\n }\n }\n\n for (const [key, group] of Object.entries(convGroups)) {\n const clusterId = group[0].cluster_id;\n let convId: string;\n\n if (key.startsWith('__new__::')) {\n const created = await this._makeRequest('POST', '/v1/conversations', {});\n const conv = created.results || created;\n convId = conv.id;\n if (!convId) {\n throw new NebulaClientException('Failed to create conversation: no id returned');\n }\n } else {\n convId = key;\n }\n\n const messages = group.map((m) => ({\n content: String(m.content || ''),\n role: m.role,\n metadata: m.metadata || {},\n }));\n\n const payload = { messages, collection_id: clusterId };\n await this._makeRequest('POST', `/v1/conversations/${convId}/messages`, payload);\n\n results.push(...Array(group.length).fill(String(convId)));\n }\n\n for (const m of others) {\n results.push(await this.storeMemory(m));\n }\n\n return results;\n }\n\n /** Delete a specific memory */\n async delete(memoryId: string): Promise<boolean> {\n try {\n await this._makeRequest('DELETE', `/v1/documents/${memoryId}`);\n return true;\n } catch (error) {\n if (error instanceof Error) {\n throw error;\n }\n throw new NebulaClientException(`Unknown error: ${String(error)}`);\n }\n }\n\n /** Delete a conversation and all its messages */\n async deleteConversation(conversationId: string): Promise<boolean> {\n try {\n await this._makeRequest('DELETE', `/v1/conversations/${conversationId}`);\n return true;\n } catch (error) {\n if (error instanceof Error) {\n throw error;\n }\n throw new NebulaClientException(`Unknown error: ${String(error)}`);\n }\n }\n\n /** Get all memories from specific clusters */\n async listMemories(\n clusterIds: string | string[],\n limit: number = 100,\n offset: number = 0\n ): Promise<MemoryResponse[]> {\n const ids = Array.isArray(clusterIds) ? clusterIds : [clusterIds];\n if (!ids.length) {\n throw new NebulaClientException('cluster_ids must be provided to list_memories().');\n }\n\n const params = { limit, offset, collection_ids: ids };\n const response = await this._makeRequest('GET', '/v1/documents', undefined, params);\n\n let documents: any[];\n if (response.results) {\n documents = response.results;\n } else if (Array.isArray(response)) {\n documents = response;\n } else {\n documents = [response];\n }\n\n return documents.map((doc) => this._memoryResponseFromDict(doc, ids));\n }\n\n /** Get a specific memory by ID */\n async getMemory(memoryId: string): Promise<MemoryResponse> {\n const response = await this._makeRequest('GET', `/v1/documents/${memoryId}`);\n\n const content = response.text || response.content;\n const chunks = Array.isArray(response.chunks) ? response.chunks : undefined;\n\n const memoryData = {\n id: response.id,\n content,\n chunks,\n metadata: response.metadata || {},\n collection_ids: response.collection_ids || [],\n };\n\n return this._memoryResponseFromDict(memoryData, []);\n }\n\n // Search Methods\n\n /** Search within specific clusters */\n async search(\n query: string,\n clusters: string | string[],\n limitOrOptions?: number | { limit?: number },\n retrievalType: RetrievalType | string = RetrievalType.ADVANCED,\n filters?: Record<string, any>,\n searchSettings?: Record<string, any>\n ): Promise<SearchResult[]> {\n const clusterIds = Array.isArray(clusters) ? clusters : [clusters];\n if (!clusterIds.length) {\n throw new NebulaClientException('cluster_ids must be provided to search().');\n }\n\n // Support legacy call shape: (query, clusterId, {limit})\n let limit = 10;\n if (typeof limitOrOptions === 'number') {\n limit = limitOrOptions;\n } else if (typeof limitOrOptions === 'object' && limitOrOptions) {\n if (typeof limitOrOptions.limit === 'number') limit = limitOrOptions.limit;\n }\n\n if (typeof retrievalType === 'string') {\n retrievalType = (RetrievalType as any)[retrievalType.toUpperCase()] || RetrievalType.ADVANCED;\n }\n\n // Build effective search settings with simplified structure\n const effectiveSettings: Record<string, any> = { ...searchSettings };\n effectiveSettings.limit = limit;\n // Retrieval type is now handled internally by the backend\n\n const userFilters = { ...effectiveSettings.filters } as Record<string, any>;\n if (filters) {\n Object.assign(userFilters, filters);\n }\n userFilters.collection_ids = { $overlap: clusterIds };\n effectiveSettings.filters = userFilters;\n\n const data = {\n query,\n search_mode: 'custom',\n search_settings: effectiveSettings,\n };\n\n const response = await this._makeRequest('POST', '/v1/retrieval/search', data);\n\n let chunkResults: any[] = [];\n let graphResults: any[] = [];\n\n if (response.results) {\n chunkResults = response.results.chunk_search_results || [];\n graphResults = response.results.graph_search_results || [];\n }\n\n const out: SearchResult[] = [];\n out.push(...chunkResults.map((result) => this._searchResultFromDict(result)));\n for (const g of graphResults) {\n out.push(this._searchResultFromGraphDict(g));\n }\n\n return out;\n }\n\n /**\n * Legacy wrapper: store a two-message conversation turn as a document\n */\n async storeConversation(\n userMessage: string,\n assistantMessage: string,\n clusterId: string,\n sessionId: string\n ): Promise<MemoryResponse> {\n const content = `User: ${String(userMessage || '')}\\nAssistant: ${String(assistantMessage || '')}`;\n const metadata = { session_id: sessionId, content_type: 'conversation' } as Record<string, any>;\n return this.store(content, clusterId, metadata);\n }\n\n /**\n * Legacy wrapper: search conversations optionally scoped by session\n */\n async searchConversations(\n query: string,\n clusterId: string,\n sessionId?: string,\n includeAllSessions: boolean = true\n ): Promise<SearchResult[]> {\n const filters: Record<string, any> = { 'metadata.content_type': 'conversation' };\n if (sessionId && !includeAllSessions) {\n (filters as any)['metadata.session_id'] = sessionId;\n }\n return this.search(query, [clusterId], { limit: 10 }, RetrievalType.ADVANCED, filters);\n }\n\n // Health Check\n async healthCheck(): Promise<Record<string, any>> {\n return this._makeRequest('GET', '/health');\n }\n\n // Helpers\n\n private _clusterFromDict(data: any): Cluster {\n let createdAt: string | undefined;\n if (data.created_at) {\n createdAt = typeof data.created_at === 'string' ? data.created_at : data.created_at.toISOString();\n }\n\n let updatedAt: string | undefined;\n if (data.updated_at) {\n updatedAt = typeof data.updated_at === 'string' ? data.updated_at : data.updated_at.toISOString();\n }\n\n const clusterId = String(data.id || '');\n const clusterName = data.name || '';\n const clusterDescription = data.description;\n const clusterOwnerId = data.owner_id ? String(data.owner_id) : undefined;\n const memoryCount = data.document_count || 0;\n\n const metadata = {\n graph_cluster_status: data.graph_cluster_status || '',\n graph_sync_status: data.graph_sync_status || '',\n user_count: data.user_count || 0,\n document_count: data.document_count || 0,\n };\n\n return {\n id: clusterId,\n name: clusterName,\n description: clusterDescription,\n metadata,\n created_at: createdAt,\n updated_at: updatedAt,\n memory_count: memoryCount,\n owner_id: clusterOwnerId,\n } as Cluster;\n }\n\n private _memoryResponseFromDict(data: any, clusterIds: string[]): MemoryResponse {\n let createdAt: string | undefined;\n if (data.created_at) {\n createdAt = typeof data.created_at === 'string' ? data.created_at : data.created_at.toISOString();\n }\n\n let updatedAt: string | undefined;\n if (data.updated_at) {\n updatedAt = typeof data.updated_at === 'string' ? data.updated_at : data.updated_at.toISOString();\n }\n\n const memoryId = String(data.id || '');\n const content = data.content || data.text;\n let chunks: string[] | undefined;\n\n if (data.chunks && Array.isArray(data.chunks)) {\n if (data.chunks.every((x: any) => typeof x === 'string')) {\n chunks = data.chunks;\n } else {\n chunks = data.chunks\n .filter((item: any) => item && typeof item === 'object' && 'text' in item)\n .map((item: any) => item.text);\n }\n }\n\n const metadata = { ...data.metadata };\n if (data.document_id) {\n (metadata as any).document_id = data.document_id;\n }\n\n let finalId = memoryId;\n if (data.document_id && !memoryId) {\n finalId = data.document_id;\n }\n\n if (data.document_metadata) {\n Object.assign(metadata, data.document_metadata);\n }\n\n return {\n id: finalId,\n content,\n chunks,\n metadata,\n cluster_ids: data.collection_ids || clusterIds,\n created_at: createdAt,\n updated_at: updatedAt,\n } as MemoryResponse;\n }\n\n private _searchResultFromDict(data: any): SearchResult {\n const content = data.content || data.text || '';\n const resultId = data.id || data.chunk_id || '';\n\n return {\n id: String(resultId),\n content: String(content),\n score: Number(data.score || 0.0),\n metadata: data.metadata || {},\n source: data.source,\n };\n }\n\n private _searchResultFromGraphDict(data: any): SearchResult {\n const rid = data.id ? String(data.id) : '';\n const rtype =\n GraphSearchResultType[(data.result_type || 'entity').toUpperCase() as keyof typeof GraphSearchResultType] ||\n GraphSearchResultType.ENTITY;\n const content = data.content || {};\n const score = data.score !== undefined ? Number(data.score) : 0.0;\n const metadata = data.metadata || {};\n const chunkIds = Array.isArray(data.chunk_ids) ? data.chunk_ids : undefined;\n\n let entity: GraphEntityResult | undefined;\n let rel: GraphRelationshipResult | undefined;\n let comm: GraphCommunityResult | undefined;\n\n if (rtype === GraphSearchResultType.ENTITY) {\n entity = {\n id: content.id ? String(content.id) : undefined,\n name: content.name || '',\n description: content.description || '',\n metadata: content.metadata || {},\n };\n } else if (rtype === GraphSearchResultType.RELATIONSHIP) {\n rel = {\n id: content.id ? String(content.id) : undefined,\n subject: content.subject || '',\n predicate: content.predicate || '',\n object: content.object || '',\n subject_id: content.subject_id ? String(content.subject_id) : undefined,\n object_id: content.object_id ? String(content.object_id) : undefined,\n description: content.description,\n metadata: content.metadata || {},\n };\n } else {\n comm = {\n id: content.id ? String(content.id) : undefined,\n name: content.name || '',\n summary: content.summary || '',\n metadata: content.metadata || {},\n };\n }\n\n return {\n id: rid,\n score,\n metadata,\n source: 'graph',\n content: undefined,\n graph_result_type: rtype,\n graph_entity: entity,\n graph_relationship: rel,\n graph_community: comm,\n chunk_ids: chunkIds,\n } as SearchResult;\n }\n\n private async _sha256(message: string): Promise<string> {\n const msgBuffer = new TextEncoder().encode(message);\n const hashBuffer = await crypto.subtle.digest('SHA-256', msgBuffer);\n const hashArray = Array.from(new Uint8Array(hashBuffer));\n const hashHex = hashArray.map((b) => b.toString(16).padStart(2, '0')).join('');\n return hashHex;\n }\n\n private _formDataFromObject(obj: Record<string, any>): FormData {\n const formData = new FormData();\n Object.entries(obj).forEach(([key, value]) => {\n formData.append(key, value as any);\n });\n return formData;\n }\n}\n"]}
1
+ {"version":3,"sources":["../src/types.ts","../src/client.ts"],"names":["GraphSearchResultType","response"],"mappings":"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","file":"index.mjs","sourcesContent":["// Data models matching the actual Nebula Python SDK exactly\n\n// Enums\nexport enum GraphSearchResultType {\n ENTITY = \"entity\",\n RELATIONSHIP = \"relationship\",\n COMMUNITY = \"community\"\n}\n\n// Core interfaces matching Python SDK exactly\nexport interface MemoryResponse {\n id: string;\n content?: string;\n chunks?: string[];\n metadata: Record<string, any>;\n cluster_ids: string[];\n created_at?: string;\n updated_at?: string;\n}\n\nexport interface Memory {\n cluster_id: string;\n content: string;\n role?: string; // user, assistant, or custom\n parent_id?: string;\n metadata: Record<string, any>;\n}\n\nexport interface Cluster {\n id: string;\n name: string;\n description?: string;\n metadata: Record<string, any>;\n created_at?: string;\n updated_at?: string;\n memory_count: number;\n owner_id?: string;\n}\n\nexport interface SearchResult {\n id: string;\n score: number;\n metadata: Record<string, any>;\n source?: string;\n timestamp?: string;\n display_name?: string;\n source_role?: string;\n document_id?: string;\n owner_id?: string;\n\n // Chunk fields\n content?: string;\n\n // Graph variant discriminator and payload\n graph_result_type?: GraphSearchResultType;\n graph_entity?: GraphEntityResult;\n graph_relationship?: GraphRelationshipResult;\n graph_community?: GraphCommunityResult;\n chunk_ids?: string[];\n}\n\nexport interface GraphEntityResult {\n id?: string;\n name: string;\n description: string;\n metadata: Record<string, any>;\n}\n\nexport interface GraphRelationshipResult {\n id?: string;\n subject: string;\n predicate: string;\n object: string;\n subject_id?: string;\n object_id?: string;\n description?: string;\n metadata: Record<string, any>;\n}\n\nexport interface GraphCommunityResult {\n id?: string;\n name: string;\n summary: string;\n metadata: Record<string, any>;\n}\n\nexport interface AgentResponse {\n content: string;\n agent_id: string;\n conversation_id?: string;\n metadata: Record<string, any>;\n citations: Record<string, any>[];\n}\n\nexport interface SearchOptions {\n limit: number;\n filters?: Record<string, any>;\n search_mode?: 'fast' | 'super';\n}\n\n// Configuration interface\nexport interface NebulaClientConfig {\n apiKey: string;\n baseUrl?: string;\n timeout?: number;\n}\n\n// Error types matching Python SDK\nexport class NebulaException extends Error {\n constructor(\n message: string,\n public statusCode?: number,\n public details?: any\n ) {\n super(message);\n this.name = 'NebulaException';\n }\n}\n\nexport class NebulaClientException extends NebulaException {\n constructor(message: string, public cause?: Error) {\n super(message);\n this.name = 'NebulaClientException';\n }\n}\n\nexport class NebulaAuthenticationException extends NebulaException {\n constructor(message: string = 'Invalid API key') {\n super(message, 401);\n this.name = 'NebulaAuthenticationException';\n }\n}\n\nexport class NebulaRateLimitException extends NebulaException {\n constructor(message: string = 'Rate limit exceeded') {\n super(message, 429);\n this.name = 'NebulaRateLimitException';\n }\n}\n\nexport class NebulaValidationException extends NebulaException {\n constructor(message: string = 'Validation error', public details?: any) {\n super(message, 400);\n this.name = 'NebulaValidationException';\n }\n}\n\nexport class NebulaClusterNotFoundException extends NebulaException {\n constructor(message: string = 'Cluster not found') {\n super(message, 404);\n this.name = 'NebulaClusterNotFoundException';\n }\n}\n","import {\n Memory,\n MemoryResponse,\n Cluster,\n SearchResult,\n GraphSearchResultType,\n GraphEntityResult,\n GraphRelationshipResult,\n GraphCommunityResult,\n NebulaClientConfig,\n NebulaException,\n NebulaClientException,\n NebulaAuthenticationException,\n NebulaRateLimitException,\n NebulaValidationException,\n} from './types';\n\n/**\n * Official Nebula JavaScript/TypeScript SDK\n * Mirrors the exact Nebula Python SDK client.py implementation\n */\nexport class NebulaClient {\n private apiKey: string;\n private baseUrl: string;\n private timeout: number;\n\n constructor(config: NebulaClientConfig) {\n this.apiKey = config.apiKey;\n if (!this.apiKey) {\n throw new NebulaClientException(\n 'API key is required. Pass it to the constructor or set NEBULA_API_KEY environment variable.'\n );\n }\n\n this.baseUrl = (config.baseUrl || 'https://api.nebulacloud.app').replace(/\\/$/, '');\n this.timeout = config.timeout || 30000;\n }\n\n // Public mutators used by tests\n setApiKey(next: string) {\n this.apiKey = next;\n }\n setBaseUrl(next: string) {\n this.baseUrl = (next || this.baseUrl).replace(/\\/$/, '');\n }\n // Kept for backwards-compat tests; no-op in current implementation\n setCorsProxy(_next: string) {\n // no-op\n }\n\n /** Check if API key is set */\n isApiKeySet(): boolean {\n return !!(this.apiKey && this.apiKey.trim() !== '');\n }\n\n /** Detect if a token looks like a Nebula API key (public.raw) */\n private _isNebulaApiKey(token?: string): boolean {\n const candidate = token || this.apiKey;\n if (!candidate) return false;\n const parts = candidate.split('.');\n if (parts.length !== 2) return false;\n const [publicPart, rawPart] = parts;\n return publicPart.startsWith('key_') && !!rawPart && rawPart.length > 0;\n }\n\n /** Build authentication headers */\n private _buildAuthHeaders(includeContentType: boolean = true): Record<string, string> {\n const headers: Record<string, string> = {};\n\n if (this._isNebulaApiKey()) {\n headers['X-API-Key'] = this.apiKey;\n } else {\n headers['Authorization'] = `Bearer ${this.apiKey}`;\n }\n\n if (includeContentType) {\n headers['Content-Type'] = 'application/json';\n }\n\n return headers;\n }\n\n /** Make an HTTP request to the Nebula API */\n private async _makeRequest(\n method: string,\n endpoint: string,\n jsonData?: Record<string, any>,\n params?: Record<string, any>\n ): Promise<any> {\n const url = new URL(endpoint, this.baseUrl);\n\n if (params) {\n console.log('SDK: _makeRequest params before processing:', params);\n Object.entries(params).forEach(([key, value]) => {\n if (value !== undefined && value !== null) {\n // Handle array parameters (e.g., collection_ids)\n if (Array.isArray(value)) {\n console.log(`SDK: Adding array param ${key}:`, value);\n value.forEach((item) => {\n url.searchParams.append(key, String(item));\n console.log(`SDK: Appended ${key}=${item} to URL`);\n });\n } else {\n console.log(`SDK: Adding single param ${key}:`, value);\n url.searchParams.append(key, String(value));\n }\n }\n });\n }\n\n console.log('SDK: Final URL being requested:', url.toString());\n\n const headers = this._buildAuthHeaders(true);\n\n const controller = new AbortController();\n const timeoutId = setTimeout(() => controller.abort(), this.timeout);\n\n try {\n const response = await fetch(url.toString(), {\n method,\n headers,\n body: jsonData ? JSON.stringify(jsonData) : undefined,\n signal: controller.signal,\n });\n\n clearTimeout(timeoutId);\n\n if (response.status === 200) {\n return await response.json();\n } else if (response.status === 401) {\n throw new NebulaAuthenticationException('Invalid API key');\n } else if (response.status === 429) {\n throw new NebulaRateLimitException('Rate limit exceeded');\n } else if (response.status === 400) {\n const errorData = await response.json().catch(() => ({}));\n throw new NebulaValidationException(errorData.message || 'Validation error', errorData.details);\n } else {\n const errorData = await response.json().catch(() => ({}));\n throw new NebulaException(errorData.message || `API error: ${response.status}`, response.status, errorData);\n }\n } catch (error) {\n clearTimeout(timeoutId);\n\n if (error instanceof NebulaException) {\n throw error;\n }\n\n if (error instanceof Error && error.name === 'AbortError') {\n throw new NebulaClientException(`Request timed out after ${this.timeout} milliseconds`);\n }\n\n if (error instanceof Error) {\n throw new NebulaClientException(`Request failed: ${error.message}`, error);\n }\n\n throw new NebulaClientException(`Request failed: ${String(error)}`);\n }\n }\n\n // Cluster Management Methods\n\n /** Create a new cluster */\n async createCluster(options: {\n name: string;\n description?: string;\n metadata?: Record<string, any>;\n }): Promise<Cluster> {\n const data: Record<string, any> = { name: options.name };\n if (options.description) data.description = options.description;\n if (options.metadata) data.metadata = options.metadata;\n\n const response = await this._makeRequest('POST', '/v1/collections', data);\n const result = response.results || response;\n return this._clusterFromDict(result);\n }\n\n /** Get a specific cluster by ID */\n async getCluster(clusterId: string): Promise<Cluster> {\n const response = await this._makeRequest('GET', `/v1/collections/${clusterId}`);\n const result = response.results || response;\n return this._clusterFromDict(result);\n }\n\n /** Get a specific cluster by name */\n async getClusterByName(name: string): Promise<Cluster> {\n const response = await this._makeRequest('GET', `/v1/collections/name/${name}`);\n const result = response.results || response;\n return this._clusterFromDict(result);\n }\n\n /** Get all clusters */\n async listClusters(options?: {\n limit?: number;\n offset?: number;\n }): Promise<Cluster[]> {\n const params = {\n limit: options?.limit ?? 100,\n offset: options?.offset ?? 0\n };\n const response = await this._makeRequest('GET', '/v1/collections', undefined, params);\n\n let clusters: any[];\n if (response.results) {\n clusters = response.results;\n } else if (Array.isArray(response)) {\n clusters = response;\n } else {\n clusters = [response];\n }\n\n return clusters.map((cluster) => this._clusterFromDict(cluster));\n }\n\n // Conversations Methods\n\n /** List conversations for the authenticated user */\n async listConversations(options?: {\n limit?: number;\n offset?: number;\n cluster_ids?: string[];\n }): Promise<any[]> {\n const params: Record<string, any> = {\n limit: options?.limit ?? 100,\n offset: options?.offset ?? 0\n };\n // Convert cluster_ids to collection_ids for the API\n if (options?.cluster_ids && options.cluster_ids.length > 0) {\n params.collection_ids = options.cluster_ids;\n }\n const response = await this._makeRequest('GET', '/v1/conversations', undefined, params);\n\n let conversations: any[];\n if (response && response.results) {\n conversations = response.results;\n } else if (Array.isArray(response)) {\n conversations = response;\n } else {\n conversations = response ? [response] : [];\n }\n\n return conversations;\n }\n\n /** Get conversation messages directly from the conversations API */\n async getConversationMessages(conversationId: string): Promise<MemoryResponse[]>;\n async getConversationMessages(conversationIds: string[]): Promise<Record<string, MemoryResponse[]>>;\n async getConversationMessages(conversationIdOrIds: string | string[]): Promise<MemoryResponse[] | Record<string, MemoryResponse[]>> {\n // Handle single conversation ID (backward compatibility)\n if (typeof conversationIdOrIds === 'string') {\n const response = await this._makeRequest('GET', `/v1/conversations/${conversationIdOrIds}`);\n\n if (!response || !response.results) {\n return [];\n }\n\n return this._transformConversationMessages(response.results);\n }\n\n // Handle multiple conversation IDs\n if (!Array.isArray(conversationIdOrIds) || conversationIdOrIds.length === 0) {\n return {};\n }\n\n // Use POST request with conversation IDs in body for batch retrieval\n // This performs a single SQL query with IN clause for optimal performance\n const response = await this._makeRequest('POST', '/v1/conversations/batch', {\n conversation_ids: conversationIdOrIds\n });\n\n console.log('🔍 SDK: Raw batch response:', response);\n console.log('🔍 SDK: Response has results?', !!response?.results);\n if (response?.results) {\n console.log('🔍 SDK: Results keys:', Object.keys(response.results));\n console.log('🔍 SDK: Sample result:', Object.keys(response.results)[0], ':', response.results[Object.keys(response.results)[0]]);\n }\n\n const results: Record<string, MemoryResponse[]> = {};\n\n if (response && response.results) {\n // Backend returns { \"results\": { \"results\": { conversation_id: MessageResponse[] } } } format (double-nested)\n const batchResults = response.results.results || response.results;\n console.log('🔍 SDK: Processing', Object.keys(batchResults).length, 'conversations');\n for (const [conversationId, messages] of Object.entries(batchResults)) {\n if (Array.isArray(messages)) {\n const transformed = this._transformConversationMessages(messages as any[]);\n results[conversationId] = transformed;\n console.log(`🔍 SDK: Conversation ${conversationId.slice(-8)}: ${messages.length} raw -> ${transformed.length} transformed`);\n } else {\n results[conversationId] = [];\n console.log(`🔍 SDK: Conversation ${conversationId.slice(-8)}: not array, setting empty`);\n }\n }\n }\n\n // Ensure all requested conversation IDs are present in results (even if empty)\n for (const conversationId of conversationIdOrIds) {\n if (!(conversationId in results)) {\n results[conversationId] = [];\n }\n }\n\n return results;\n }\n\n /** Helper method to transform conversation messages to MemoryResponse format */\n private _transformConversationMessages(messageResponses: any[]): MemoryResponse[] {\n return messageResponses.map((msgResp: any) => {\n const msgId = String(msgResp.id || '');\n const msg = msgResp.message || {}; // The actual Message object\n const metadata = msgResp.metadata || {};\n\n // Normalize content to a string - could be string or object\n let text: string = '';\n const rawContent = msg.content;\n if (typeof rawContent === 'string') {\n text = rawContent;\n } else if (rawContent && typeof rawContent === 'object') {\n // Handle structured content\n text = String(rawContent.content || rawContent.text || JSON.stringify(rawContent));\n } else if (rawContent != null) {\n text = String(rawContent);\n }\n\n // Get role from the Message object\n const role = msg.role || metadata.role || 'user';\n\n // Merge message metadata with response metadata\n const combinedMetadata = {\n ...metadata,\n role, // Ensure role is in metadata for UI compatibility\n };\n\n return {\n id: msgId,\n content: text,\n metadata: combinedMetadata,\n created_at: msgResp.created_at,\n cluster_ids: msgResp.collection_ids || [],\n } as MemoryResponse;\n });\n }\n\n /** Update a cluster */\n async updateCluster(options: {\n clusterId: string;\n name?: string;\n description?: string;\n metadata?: Record<string, any>;\n }): Promise<Cluster> {\n const data: Record<string, any> = {};\n if (options.name !== undefined) data.name = options.name;\n if (options.description !== undefined) data.description = options.description;\n if (options.metadata !== undefined) data.metadata = options.metadata;\n\n const response = await this._makeRequest('POST', `/v1/collections/${options.clusterId}`, data);\n const result = response.results || response;\n return this._clusterFromDict(result);\n }\n\n /** Delete a cluster */\n async deleteCluster(clusterId: string): Promise<boolean> {\n await this._makeRequest('DELETE', `/v1/collections/${clusterId}`);\n return true;\n }\n\n // Memory Management Methods\n\n /**\n * Legacy convenience: store raw text content into a cluster as a document\n */\n async store(content: string, clusterId: string, metadata: Record<string, any> = {}): Promise<MemoryResponse> {\n const docMetadata = {\n ...metadata,\n memory_type: 'memory',\n timestamp: new Date().toISOString(),\n } as Record<string, any>;\n\n const data = {\n metadata: JSON.stringify(docMetadata),\n ingestion_mode: 'fast',\n collection_ids: JSON.stringify([clusterId]),\n raw_text: String(content || ''),\n } as const;\n\n const url = `${this.baseUrl}/v1/documents`;\n const headers = this._buildAuthHeaders(false);\n\n const response = await fetch(url, {\n method: 'POST',\n headers,\n body: this._formDataFromObject(data as any),\n });\n\n if (!response.ok) {\n const errorData = await response.json().catch(() => ({}));\n throw new NebulaException(\n errorData.message || `Failed to create document: ${response.status}`,\n response.status,\n errorData\n );\n }\n\n const respData = await response.json();\n const id = respData?.results?.document_id || respData?.results?.id || respData?.id || '';\n\n const result: MemoryResponse = {\n id: String(id),\n content: String(content || ''),\n metadata: docMetadata,\n cluster_ids: [clusterId],\n created_at: docMetadata.timestamp,\n updated_at: docMetadata.timestamp,\n };\n return result;\n }\n\n /** Store a single memory */\n async storeMemory(memory: Memory | Record<string, any>): Promise<string> {\n let mem: Memory;\n\n if ('cluster_id' in memory) {\n mem = memory as Memory;\n } else {\n mem = {\n cluster_id: (memory as any).cluster_id,\n content: (memory as any).content,\n role: (memory as any).role,\n parent_id: (memory as any).parent_id,\n metadata: (memory as any).metadata || {},\n };\n }\n\n // Conversation mode\n if (mem.role) {\n let convId = mem.parent_id;\n if (!convId) {\n const created = await this._makeRequest('POST', '/v1/conversations', {});\n const conv = created.results || created;\n convId = conv.id;\n if (!convId) {\n throw new NebulaClientException('Failed to create conversation: no id returned');\n }\n }\n\n const payload = {\n messages: [\n {\n content: String(mem.content),\n role: mem.role,\n metadata: mem.metadata,\n },\n ],\n collection_id: mem.cluster_id,\n } as const;\n\n await this._makeRequest('POST', `/v1/conversations/${convId}/messages`, payload);\n return String(convId);\n }\n\n // Text/JSON memory mode\n const contentText = String(mem.content || '');\n const contentHash = await this._sha256(contentText);\n const docMetadata = { ...mem.metadata } as Record<string, any>;\n docMetadata.memory_type = 'memory';\n docMetadata.content_hash = contentHash;\n\n const data = {\n metadata: JSON.stringify(docMetadata),\n ingestion_mode: 'fast',\n collection_ids: JSON.stringify([mem.cluster_id]),\n raw_text: contentText,\n } as const;\n\n const url = `${this.baseUrl}/v1/documents`;\n const headers = this._buildAuthHeaders(false);\n\n const response = await fetch(url, {\n method: 'POST',\n headers,\n body: this._formDataFromObject(data as any),\n });\n\n if (!response.ok) {\n const errorData = await response.json().catch(() => ({}));\n throw new NebulaException(\n errorData.message || `Failed to create document: ${response.status}`,\n response.status,\n errorData\n );\n }\n\n const respData = await response.json();\n if (respData.results) {\n if (respData.results.document_id) return String(respData.results.document_id);\n if (respData.results.id) return String(respData.results.id);\n }\n return '';\n }\n\n /** Store multiple memories */\n async storeMemories(memories: Memory[]): Promise<string[]> {\n const results: string[] = [];\n const convGroups: Record<string, Memory[]> = {};\n const others: Memory[] = [];\n\n for (const m of memories) {\n if (m.role) {\n const key = m.parent_id || `__new__::${m.cluster_id}`;\n if (!convGroups[key]) convGroups[key] = [];\n convGroups[key].push(m);\n } else {\n others.push(m);\n }\n }\n\n for (const [key, group] of Object.entries(convGroups)) {\n const clusterId = group[0].cluster_id;\n let convId: string;\n\n if (key.startsWith('__new__::')) {\n const created = await this._makeRequest('POST', '/v1/conversations', {});\n const conv = created.results || created;\n convId = conv.id;\n if (!convId) {\n throw new NebulaClientException('Failed to create conversation: no id returned');\n }\n } else {\n convId = key;\n }\n\n const messages = group.map((m) => ({\n content: String(m.content || ''),\n role: m.role,\n metadata: m.metadata || {},\n }));\n\n const payload = { messages, collection_id: clusterId };\n await this._makeRequest('POST', `/v1/conversations/${convId}/messages`, payload);\n\n results.push(...Array(group.length).fill(String(convId)));\n }\n\n for (const m of others) {\n results.push(await this.storeMemory(m));\n }\n\n return results;\n }\n\n /** Delete one or more memories */\n async delete(memoryIds: string | string[]): Promise<boolean | {\n message: string;\n results: {\n successful: string[];\n failed: Array<{ id: string; error: string }>;\n summary: {\n total: number;\n succeeded: number;\n failed: number;\n };\n };\n }> {\n try {\n // Handle single ID vs array\n if (typeof memoryIds === 'string') {\n // Single deletion - try existing endpoint first for backward compatibility\n try {\n await this._makeRequest('DELETE', `/v1/documents/${memoryIds}`);\n return true;\n } catch {\n // Fall back to new unified endpoint\n try {\n const response = await this._makeRequest('POST', '/v1/documents/delete', {\n ids: memoryIds,\n });\n return typeof response === 'object' && response.success !== undefined\n ? response.success\n : true;\n } catch (error) {\n throw error;\n }\n }\n } else {\n // Batch deletion\n const response = await this._makeRequest('POST', '/v1/documents/delete', {\n ids: memoryIds,\n });\n return response;\n }\n } catch (error) {\n if (error instanceof Error) {\n throw error;\n }\n throw new NebulaClientException(`Unknown error: ${String(error)}`);\n }\n }\n\n /** Delete a conversation and all its messages */\n async deleteConversation(conversationId: string): Promise<boolean> {\n try {\n await this._makeRequest('DELETE', `/v1/conversations/${conversationId}`);\n return true;\n } catch (error) {\n if (error instanceof Error) {\n throw error;\n }\n throw new NebulaClientException(`Unknown error: ${String(error)}`);\n }\n }\n\n /** Get all memories from specific clusters */\n async listMemories(options: {\n cluster_ids: string | string[];\n limit?: number;\n offset?: number;\n }): Promise<MemoryResponse[]> {\n const ids = Array.isArray(options.cluster_ids) ? options.cluster_ids : [options.cluster_ids];\n if (!ids.length) {\n throw new NebulaClientException('cluster_ids must be provided to list_memories().');\n }\n\n const params = {\n limit: options.limit ?? 100,\n offset: options.offset ?? 0,\n collection_ids: ids\n };\n const response = await this._makeRequest('GET', '/v1/documents', undefined, params);\n\n let documents: any[];\n if (response.results) {\n documents = response.results;\n } else if (Array.isArray(response)) {\n documents = response;\n } else {\n documents = [response];\n }\n\n return documents.map((doc) => this._memoryResponseFromDict(doc, ids));\n }\n\n /** Get a specific memory by ID */\n async getMemory(memoryId: string): Promise<MemoryResponse> {\n const response = await this._makeRequest('GET', `/v1/documents/${memoryId}`);\n\n const content = response.text || response.content;\n const chunks = Array.isArray(response.chunks) ? response.chunks : undefined;\n\n const memoryData = {\n id: response.id,\n content,\n chunks,\n metadata: response.metadata || {},\n collection_ids: response.collection_ids || [],\n };\n\n return this._memoryResponseFromDict(memoryData, []);\n }\n\n // Search Methods\n\n /**\n * Search within specific clusters with optional metadata filtering.\n *\n * @param options - Search configuration\n * @param options.query - Search query string\n * @param options.cluster_ids - One or more cluster IDs to search within\n * @param options.limit - Maximum number of results to return (default: 10)\n * @param options.retrieval_type - Retrieval strategy (default: ADVANCED)\n * @param options.filters - Optional filters to apply to the search. Supports comprehensive metadata filtering\n * with MongoDB-like operators for both vector/chunk search and graph search.\n * @param options.searchSettings - Optional search configuration\n *\n * @returns Promise resolving to array of SearchResult objects containing both vector/chunk and graph search results\n *\n * @example\n * // Basic equality filter\n * await client.search({\n * query: \"machine learning\",\n * cluster_ids: [\"research-cluster\"],\n * filters: {\n * \"metadata.category\": { $eq: \"research\" },\n * \"metadata.verified\": true // Shorthand for $eq\n * }\n * });\n *\n * @example\n * // Numeric comparisons\n * await client.search({\n * query: \"high priority\",\n * cluster_ids: [\"tasks\"],\n * filters: {\n * \"metadata.priority\": { $gte: 8 },\n * \"metadata.score\": { $lt: 100 }\n * }\n * });\n *\n * @example\n * // String matching\n * await client.search({\n * query: \"employees\",\n * cluster_ids: [\"team\"],\n * filters: {\n * \"metadata.email\": { $ilike: \"%@company.com\" } // Case-insensitive\n * }\n * });\n *\n * @example\n * // Array operations\n * await client.search({\n * query: \"developers\",\n * cluster_ids: [\"team\"],\n * filters: {\n * \"metadata.skills\": { $overlap: [\"python\", \"typescript\"] } // Has any\n * }\n * });\n *\n * @example\n * // Nested paths\n * await client.search({\n * query: \"users\",\n * cluster_ids: [\"profiles\"],\n * filters: {\n * \"metadata.user.preferences.theme\": { $eq: \"dark\" }\n * }\n * });\n *\n * @example\n * // Complex logical combinations\n * await client.search({\n * query: \"candidates\",\n * cluster_ids: [\"hiring\"],\n * filters: {\n * $and: [\n * { \"metadata.verified\": true },\n * { \"metadata.level\": { $gte: 5 } },\n * {\n * $or: [\n * { \"metadata.skills\": { $overlap: [\"python\", \"go\"] } },\n * { \"metadata.years_experience\": { $gte: 8 } }\n * ]\n * }\n * ]\n * }\n * });\n *\n * @remarks\n * Supported Operators:\n * - Comparison: $eq, $ne, $lt, $lte, $gt, $gte\n * - String: $like (case-sensitive), $ilike (case-insensitive)\n * - Array: $in, $nin, $overlap, $contains\n * - JSONB: $json_contains\n * - Logical: $and, $or\n *\n * For comprehensive filtering documentation, see the Metadata Filtering Guide:\n * https://docs.nebulacloud.app/guides/metadata-filtering\n */\n async search(options: {\n query: string;\n cluster_ids: string | string[];\n limit?: number;\n filters?: Record<string, any>;\n search_mode?: 'fast' | 'super';\n searchSettings?: Record<string, any>;\n }): Promise<SearchResult[]> {\n const clusterIds = Array.isArray(options.cluster_ids) ? options.cluster_ids : [options.cluster_ids];\n if (!clusterIds.length) {\n throw new NebulaClientException('cluster_ids must be provided to search().');\n }\n\n const limit = options.limit ?? 10;\n const searchMode = options.search_mode ?? 'super';\n\n // Build effective search settings with simplified structure\n const effectiveSettings: Record<string, any> = {\n ...options.searchSettings\n };\n effectiveSettings.limit = limit;\n\n const userFilters = { ...effectiveSettings.filters } as Record<string, any>;\n if (options.filters) {\n Object.assign(userFilters, options.filters);\n }\n userFilters.collection_ids = { $overlap: clusterIds };\n effectiveSettings.filters = userFilters;\n\n const data = {\n query: options.query,\n search_mode: searchMode,\n search_settings: effectiveSettings,\n };\n\n const response = await this._makeRequest('POST', '/v1/retrieval/search', data);\n\n let chunkResults: any[] = [];\n let graphResults: any[] = [];\n\n if (response.results) {\n chunkResults = response.results.chunk_search_results || [];\n graphResults = response.results.graph_search_results || [];\n }\n\n const out: SearchResult[] = [];\n out.push(...chunkResults.map((result) => this._searchResultFromDict(result)));\n for (const g of graphResults) {\n out.push(this._searchResultFromGraphDict(g));\n }\n\n return out;\n }\n\n /**\n * Legacy wrapper: store a two-message conversation turn as a document\n */\n async storeConversation(\n userMessage: string,\n assistantMessage: string,\n clusterId: string,\n sessionId: string\n ): Promise<MemoryResponse> {\n const content = `User: ${String(userMessage || '')}\\nAssistant: ${String(assistantMessage || '')}`;\n const metadata = { session_id: sessionId, content_type: 'conversation' } as Record<string, any>;\n return this.store(content, clusterId, metadata);\n }\n\n /**\n * Legacy wrapper: search conversations optionally scoped by session\n */\n async searchConversations(\n query: string,\n clusterId: string,\n sessionId?: string,\n includeAllSessions: boolean = true\n ): Promise<SearchResult[]> {\n const filters: Record<string, any> = { 'metadata.content_type': 'conversation' };\n if (sessionId && !includeAllSessions) {\n (filters as any)['metadata.session_id'] = sessionId;\n }\n return this.search({\n query,\n cluster_ids: [clusterId],\n limit: 10,\n filters\n });\n }\n\n // Health Check\n async healthCheck(): Promise<Record<string, any>> {\n return this._makeRequest('GET', '/health');\n }\n\n // Helpers\n\n private _clusterFromDict(data: any): Cluster {\n let createdAt: string | undefined;\n if (data.created_at) {\n createdAt = typeof data.created_at === 'string' ? data.created_at : data.created_at.toISOString();\n }\n\n let updatedAt: string | undefined;\n if (data.updated_at) {\n updatedAt = typeof data.updated_at === 'string' ? data.updated_at : data.updated_at.toISOString();\n }\n\n const clusterId = String(data.id || '');\n const clusterName = data.name || '';\n const clusterDescription = data.description;\n const clusterOwnerId = data.owner_id ? String(data.owner_id) : undefined;\n const memoryCount = data.document_count || 0;\n\n const metadata = {\n graph_cluster_status: data.graph_cluster_status || '',\n graph_sync_status: data.graph_sync_status || '',\n user_count: data.user_count || 0,\n document_count: data.document_count || 0,\n };\n\n return {\n id: clusterId,\n name: clusterName,\n description: clusterDescription,\n metadata,\n created_at: createdAt,\n updated_at: updatedAt,\n memory_count: memoryCount,\n owner_id: clusterOwnerId,\n } as Cluster;\n }\n\n private _memoryResponseFromDict(data: any, clusterIds: string[]): MemoryResponse {\n let createdAt: string | undefined;\n if (data.created_at) {\n createdAt = typeof data.created_at === 'string' ? data.created_at : data.created_at.toISOString();\n }\n\n let updatedAt: string | undefined;\n if (data.updated_at) {\n updatedAt = typeof data.updated_at === 'string' ? data.updated_at : data.updated_at.toISOString();\n }\n\n const memoryId = String(data.id || '');\n const content = data.content || data.text;\n let chunks: string[] | undefined;\n\n if (data.chunks && Array.isArray(data.chunks)) {\n if (data.chunks.every((x: any) => typeof x === 'string')) {\n chunks = data.chunks;\n } else {\n chunks = data.chunks\n .filter((item: any) => item && typeof item === 'object' && 'text' in item)\n .map((item: any) => item.text);\n }\n }\n\n const metadata = { ...data.metadata };\n if (data.document_id) {\n (metadata as any).document_id = data.document_id;\n }\n\n let finalId = memoryId;\n if (data.document_id && !memoryId) {\n finalId = data.document_id;\n }\n\n if (data.document_metadata) {\n Object.assign(metadata, data.document_metadata);\n }\n\n return {\n id: finalId,\n content,\n chunks,\n metadata,\n cluster_ids: data.collection_ids || clusterIds,\n created_at: createdAt,\n updated_at: updatedAt,\n } as MemoryResponse;\n }\n\n private _searchResultFromDict(data: any): SearchResult {\n const content = data.content || data.text || '';\n const resultId = data.id || data.chunk_id || '';\n\n return {\n id: String(resultId),\n content: String(content),\n score: Number(data.score || 0.0),\n metadata: data.metadata || {},\n source: data.source,\n };\n }\n\n private _searchResultFromGraphDict(data: any): SearchResult {\n const rid = data.id ? String(data.id) : '';\n const rtype =\n GraphSearchResultType[(data.result_type || 'entity').toUpperCase() as keyof typeof GraphSearchResultType] ||\n GraphSearchResultType.ENTITY;\n const content = data.content || {};\n const score = data.score !== undefined ? Number(data.score) : 0.0;\n const metadata = data.metadata || {};\n const chunkIds = Array.isArray(data.chunk_ids) ? data.chunk_ids : undefined;\n let timestamp: string | undefined;\n if (data.timestamp) {\n if (typeof data.timestamp === 'string') {\n timestamp = data.timestamp;\n } else if (data.timestamp instanceof Date) {\n timestamp = data.timestamp.toISOString();\n } else {\n const parsed = new Date(data.timestamp);\n if (!Number.isNaN(parsed.valueOf())) {\n timestamp = parsed.toISOString();\n }\n }\n }\n\n const displayName = typeof data.display_name === 'string' ? data.display_name : undefined;\n const sourceRole = typeof data.source_role === 'string' ? data.source_role : undefined;\n const documentId = data.document_id ? String(data.document_id) : undefined;\n const ownerId = data.owner_id ? String(data.owner_id) : undefined;\n\n let entity: GraphEntityResult | undefined;\n let rel: GraphRelationshipResult | undefined;\n let comm: GraphCommunityResult | undefined;\n\n if (rtype === GraphSearchResultType.ENTITY) {\n entity = {\n id: content.id ? String(content.id) : undefined,\n name: content.name || '',\n description: content.description || '',\n metadata: content.metadata || {},\n };\n } else if (rtype === GraphSearchResultType.RELATIONSHIP) {\n rel = {\n id: content.id ? String(content.id) : undefined,\n subject: content.subject || '',\n predicate: content.predicate || '',\n object: content.object || '',\n subject_id: content.subject_id ? String(content.subject_id) : undefined,\n object_id: content.object_id ? String(content.object_id) : undefined,\n description: content.description,\n metadata: content.metadata || {},\n };\n } else {\n comm = {\n id: content.id ? String(content.id) : undefined,\n name: content.name || '',\n summary: content.summary || '',\n metadata: content.metadata || {},\n };\n }\n\n return {\n id: rid,\n score,\n metadata,\n source: 'graph',\n content: undefined,\n graph_result_type: rtype,\n graph_entity: entity,\n graph_relationship: rel,\n graph_community: comm,\n chunk_ids: chunkIds,\n timestamp,\n display_name: displayName,\n source_role: sourceRole,\n document_id: documentId,\n owner_id: ownerId,\n } as SearchResult;\n }\n\n private async _sha256(message: string): Promise<string> {\n const msgBuffer = new TextEncoder().encode(message);\n const hashBuffer = await crypto.subtle.digest('SHA-256', msgBuffer);\n const hashArray = Array.from(new Uint8Array(hashBuffer));\n const hashHex = hashArray.map((b) => b.toString(16).padStart(2, '0')).join('');\n return hashHex;\n }\n\n private _formDataFromObject(obj: Record<string, any>): FormData {\n const formData = new FormData();\n Object.entries(obj).forEach(([key, value]) => {\n formData.append(key, value as any);\n });\n return formData;\n }\n}\n"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@nebula-ai/sdk",
3
- "version": "0.0.24",
3
+ "version": "0.0.27",
4
4
  "description": "Official JavaScript/TypeScript SDK for Nebula AI Memory",
5
5
  "main": "dist/index.js",
6
6
  "module": "dist/index.mjs",