Compare commits

...

9 Commits

Author SHA1 Message Date
github-actions[bot] 2afcbe6587 Release 0.5.20 (#1132)
Co-authored-by: github-actions[bot] <github-actions[bot]@users.noreply.github.com>
2024-08-28 10:43:26 +07:00
Marcus Schiesser 22ff486fbe fix: Add tiktoken WASM to withLlamaIndex (#1134)
Co-authored-by: Thuc Pham <51660321+thucpn@users.noreply.github.com>
2024-08-28 10:39:14 +07:00
Thuc Pham eed0b0415d fix: use metadata mode LLM for generating context (#1133)
Co-authored-by: Marcus Schiesser <mail@marcusschiesser.de>
2024-08-23 22:56:18 +07:00
Sebastian van Gerwen d9d6c56ed5 pgvectorstore support new conditions and operations (#1131)
Co-authored-by: Sebastian van Gerwen <svangerwen@invertigro.com>
Co-authored-by: Marcus Schiesser <marcus.schiesser@googlemail.com>
2024-08-23 14:40:39 +07:00
github-actions[bot] f99a237093 Release 0.5.19 (#1128)
Co-authored-by: github-actions[bot] <github-actions[bot]@users.noreply.github.com>
2024-08-19 14:04:47 +07:00
Thuc Pham fcbf18344c feat: implement llamacloud file service (#1125) 2024-08-19 14:01:41 +07:00
github-actions[bot] bf8cbeb6c5 Release 0.5.18 (#1124)
Co-authored-by: github-actions[bot] <github-actions[bot]@users.noreply.github.com>
2024-08-19 12:53:28 +09:00
Alex Yang e27e7dd054 chore: bump natural to 8.0.1 (#1126) 2024-08-17 07:15:08 -07:00
Thuc Pham 8b66cf4341 feat: support organization id in llamacloud index (#1123)
Co-authored-by: Marcus Schiesser <mail@marcusschiesser.de>
2024-08-15 13:51:48 +07:00
40 changed files with 806 additions and 1620 deletions
+23
View File
@@ -1,5 +1,28 @@
# docs
## 0.0.61
### Patch Changes
- Updated dependencies [d9d6c56]
- Updated dependencies [22ff486]
- Updated dependencies [eed0b04]
- llamaindex@0.5.20
## 0.0.60
### Patch Changes
- Updated dependencies [fcbf183]
- llamaindex@0.5.19
## 0.0.59
### Patch Changes
- Updated dependencies [8b66cf4]
- llamaindex@0.5.18
## 0.0.58
### Patch Changes
+10 -3
View File
@@ -6,10 +6,17 @@ sidebar_position: 2
We support Node.JS versions 18, 20 and 22, with experimental support for Deno, Bun and Vercel Edge functions.
## NextJS App Router
## NextJS
If you're using NextJS App Router route handlers/serverless functions, you'll need to use the NodeJS mode:
If you're using NextJS you'll need to add `withLlamaIndex` to your `next.config.js` file. This will add the necessary configuration for included 3rd-party libraries to your build:
```js
export const runtime = "nodejs"; // default
// next.config.js
const withLlamaIndex = require("llamaindex/next");
module.exports = withLlamaIndex({
// your next.js config
});
```
For details, check the latest [withLlamaIndex](https://github.com/run-llama/LlamaIndexTS/blob/main/packages/llamaindex/src/next.ts) implementation.
+1 -1
View File
@@ -1,6 +1,6 @@
{
"name": "docs",
"version": "0.0.58",
"version": "0.0.61",
"private": true,
"scripts": {
"docusaurus": "docusaurus",
@@ -1,5 +1,31 @@
# @llamaindex/autotool-02-next-example
## 0.1.45
### Patch Changes
- Updated dependencies [d9d6c56]
- Updated dependencies [22ff486]
- Updated dependencies [eed0b04]
- llamaindex@0.5.20
- @llamaindex/autotool@2.0.1
## 0.1.44
### Patch Changes
- Updated dependencies [fcbf183]
- llamaindex@0.5.19
- @llamaindex/autotool@2.0.1
## 0.1.43
### Patch Changes
- Updated dependencies [8b66cf4]
- llamaindex@0.5.18
- @llamaindex/autotool@2.0.1
## 0.1.42
### Patch Changes
@@ -1,7 +1,7 @@
{
"name": "@llamaindex/autotool-02-next-example",
"private": true,
"version": "0.1.42",
"version": "0.1.45",
"scripts": {
"dev": "next dev",
"build": "next build",
+1 -1
View File
@@ -51,7 +51,7 @@
"unplugin": "^1.10.1"
},
"peerDependencies": {
"llamaindex": "^0.5.17",
"llamaindex": "^0.5.20",
"openai": "^4",
"typescript": "^4"
},
+7
View File
@@ -1,5 +1,12 @@
# @llamaindex/community
## 0.0.30
### Patch Changes
- Updated dependencies [e27e7dd]
- @llamaindex/core@0.1.9
## 0.0.29
### Patch Changes
+1 -1
View File
@@ -1,7 +1,7 @@
{
"name": "@llamaindex/community",
"description": "Community package for LlamaIndexTS",
"version": "0.0.29",
"version": "0.0.30",
"type": "module",
"types": "dist/type/index.d.ts",
"main": "dist/cjs/index.js",
+6
View File
@@ -1,5 +1,11 @@
# @llamaindex/core
## 0.1.9
### Patch Changes
- e27e7dd: chore: bump `natural` to 8.0.1
## 0.1.8
### Patch Changes
+2 -2
View File
@@ -1,7 +1,7 @@
{
"name": "@llamaindex/core",
"type": "module",
"version": "0.1.8",
"version": "0.1.9",
"description": "LlamaIndex Core Module",
"exports": {
"./node-parser": {
@@ -132,7 +132,7 @@
"devDependencies": {
"ajv": "^8.16.0",
"bunchee": "5.3.1",
"natural": "^7.1.0"
"natural": "^8.0.1"
},
"dependencies": {
"@llamaindex/env": "workspace:*",
File diff suppressed because it is too large Load Diff
@@ -1,4 +1,5 @@
declare class SentenceTokenizer {
constructor(abbreviations?: string[]);
tokenize(text: string): string[];
}
@@ -0,0 +1,222 @@
var __getOwnPropNames = Object.getOwnPropertyNames;
var __commonJS = (cb, mod) =>
function __require() {
return (
mod ||
(0, cb[__getOwnPropNames(cb)[0]])((mod = { exports: {} }).exports, mod),
mod.exports
);
};
// lib/natural/tokenizers/tokenizer.js
var require_tokenizer = __commonJS({
"lib/natural/tokenizers/tokenizer.js"(exports, module) {
"use strict";
var Tokenizer = class {
trim(array) {
while (array[array.length - 1] === "") {
array.pop();
}
while (array[0] === "") {
array.shift();
}
return array;
}
};
module.exports = Tokenizer;
},
});
// lib/natural/tokenizers/sentence_tokenizer.js
var require_sentence_tokenizer = __commonJS({
"lib/natural/tokenizers/sentence_tokenizer.js"(exports, module) {
var Tokenizer = require_tokenizer();
var NUM = "NUMBER";
var DELIM = "DELIM";
var URI = "URI";
var ABBREV = "ABBREV";
var DEBUG = false;
function generateUniqueCode(base, index) {
return `{{${base}_${index}}}`;
}
function escapeRegExp(string) {
return string.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
}
var SentenceTokenizer = class extends Tokenizer {
constructor(abbreviations) {
super();
if (abbreviations) {
this.abbreviations = abbreviations;
} else {
this.abbreviations = [];
}
this.replacementMap = null;
this.replacementCounter = 0;
}
replaceUrisWithPlaceholders(text) {
const urlPattern =
/(https?:\/\/\S+|www\.\S+|ftp:\/\/\S+|(mailto:)?[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}|file:\/\/\S+)/gi;
const modifiedText = text.replace(urlPattern, (match) => {
const placeholder = generateUniqueCode(
URI,
this.replacementCounter++,
);
this.replacementMap.set(placeholder, match);
return placeholder;
});
return modifiedText;
}
replaceAbbreviations(text) {
if (this.abbreviations.length === 0) {
return text;
}
const pattern = new RegExp(
`(${this.abbreviations.map((abbrev) => escapeRegExp(abbrev)).join("|")})`,
"gi",
);
const replacedText = text.replace(pattern, (match) => {
const code = generateUniqueCode(ABBREV, this.replacementCounter++);
this.replacementMap.set(code, match);
return code;
});
return replacedText;
}
replaceDelimitersWithPlaceholders(text) {
const delimiterPattern = /([.?!… ]*)([.?!…])(["'”’)}\]]?)/g;
const modifiedText = text.replace(
delimiterPattern,
(match, p1, p2, p3) => {
const placeholder = generateUniqueCode(
DELIM,
this.replacementCounter++,
);
this.delimiterMap.set(placeholder, p1 + p2 + p3);
return placeholder;
},
);
return modifiedText;
}
splitOnPlaceholders(text, placeholders) {
if (this.delimiterMap.size === 0) {
return [text];
}
const keys = Array.from(this.delimiterMap.keys());
const pattern = new RegExp(`(${keys.map(escapeRegExp).join("|")})`);
const parts = text.split(pattern);
const sentences = [];
for (let i = 0; i < parts.length; i += 2) {
const sentence = parts[i];
const placeholder = parts[i + 1] || "";
sentences.push(sentence + placeholder);
}
return sentences;
}
replaceNumbersWithCode(text) {
const numberPattern = /\b\d{1,3}(?:,\d{3})*(?:\.\d+)?\b/g;
const replacedText = text.replace(numberPattern, (match) => {
const code = generateUniqueCode(NUM, this.replacementCounter++);
this.replacementMap.set(code, match);
return code;
});
return replacedText;
}
revertReplacements(text) {
let originalText = text;
for (const [
placeholder,
replacement,
] of this.replacementMap.entries()) {
const pattern = new RegExp(escapeRegExp(placeholder), "g");
originalText = originalText.replace(pattern, replacement);
}
return originalText;
}
revertDelimiters(text) {
let originalText = text;
for (const [placeholder, replacement] of this.delimiterMap.entries()) {
const pattern = new RegExp(escapeRegExp(placeholder), "g");
originalText = originalText.replace(pattern, replacement);
}
return originalText;
}
tokenize(text) {
this.replacementCounter = 0;
this.replacementMap = /* @__PURE__ */ new Map();
this.delimiterMap = /* @__PURE__ */ new Map();
DEBUG &&
console.log(
"---Start of sentence tokenization-----------------------",
);
DEBUG && console.log("Original input: >>>" + text + "<<<");
const result1 = this.replaceAbbreviations(text);
DEBUG &&
console.log(
"Phase 1: replacing abbreviations: " + JSON.stringify(result1),
);
const result2 = this.replaceUrisWithPlaceholders(result1);
DEBUG &&
console.log("Phase 2: replacing URIs: " + JSON.stringify(result2));
const result3 = this.replaceNumbersWithCode(result2);
DEBUG &&
console.log(
"Phase 3: replacing numbers with placeholders: " +
JSON.stringify(result3),
);
const result4 = this.replaceDelimitersWithPlaceholders(result3);
DEBUG &&
console.log(
"Phase 4: replacing delimiters with placeholders: " +
JSON.stringify(result4),
);
const sentences = this.splitOnPlaceholders(result4);
DEBUG &&
console.log(
"Phase 5: splitting into sentences on placeholders: " +
JSON.stringify(sentences),
);
const newSentences = sentences.map((s) => {
const s1 = this.revertReplacements(s);
return this.revertDelimiters(s1);
});
DEBUG &&
console.log(
"Phase 6: replacing back abbreviations, URIs, numbers and delimiters: " +
JSON.stringify(newSentences),
);
const trimmedSentences = this.trim(newSentences);
DEBUG &&
console.log(
"Phase 7: trimming array of empty sentences: " +
JSON.stringify(trimmedSentences),
);
const trimmedSentences2 = trimmedSentences.map((sent) => sent.trim());
DEBUG &&
console.log(
"Phase 8: trimming sentences from surrounding whitespace: " +
JSON.stringify(trimmedSentences2),
);
DEBUG &&
console.log(
"---End of sentence tokenization--------------------------",
);
DEBUG &&
console.log(
"---Replacement map---------------------------------------",
);
DEBUG && console.log([...this.replacementMap.entries()]);
DEBUG &&
console.log(
"---Delimiter map-----------------------------------------",
);
DEBUG && console.log([...this.delimiterMap.entries()]);
DEBUG &&
console.log(
"---------------------------------------------------------",
);
return trimmedSentences2;
}
};
module.exports = SentenceTokenizer;
},
});
export default require_sentence_tokenizer();
+9 -3
View File
@@ -1,5 +1,5 @@
import type { TextSplitter } from "./base";
import SentenceTokenizerNew from "./sentence-tokenizer-parser.js";
import SentenceTokenizer from "./sentence_tokenizer";
export type TextSplitterFn = (text: string) => string[];
@@ -31,11 +31,17 @@ export const splitByChar = (): TextSplitterFn => {
return (text: string) => text.split("");
};
let sentenceTokenizer: SentenceTokenizerNew | null = null;
let sentenceTokenizer: SentenceTokenizer | null = null;
export const splitBySentenceTokenizer = (): TextSplitterFn => {
if (!sentenceTokenizer) {
sentenceTokenizer = new SentenceTokenizerNew();
sentenceTokenizer = new SentenceTokenizer([
"i.e.",
"etc.",
"vs.",
"Inc.",
"A.S.A.P.",
]);
}
const tokenizer = sentenceTokenizer;
return (text: string) => {
+23
View File
@@ -1,5 +1,28 @@
# @llamaindex/experimental
## 0.0.70
### Patch Changes
- Updated dependencies [d9d6c56]
- Updated dependencies [22ff486]
- Updated dependencies [eed0b04]
- llamaindex@0.5.20
## 0.0.69
### Patch Changes
- Updated dependencies [fcbf183]
- llamaindex@0.5.19
## 0.0.68
### Patch Changes
- Updated dependencies [8b66cf4]
- llamaindex@0.5.18
## 0.0.67
### Patch Changes
+1 -1
View File
@@ -1,7 +1,7 @@
{
"name": "@llamaindex/experimental",
"description": "Experimental package for LlamaIndexTS",
"version": "0.0.67",
"version": "0.0.70",
"type": "module",
"types": "dist/type/index.d.ts",
"main": "dist/cjs/index.js",
+22
View File
@@ -1,5 +1,27 @@
# llamaindex
## 0.5.20
### Patch Changes
- d9d6c56: Add support for MetadataFilters for PostgreSQL
- 22ff486: Add tiktoken WASM to withLlamaIndex
- eed0b04: fix: use LLM metadata mode for generating context of ContextChatEngine
## 0.5.19
### Patch Changes
- fcbf183: implement llamacloud file service
## 0.5.18
### Patch Changes
- 8b66cf4: feat: support organization id in llamacloud index
- Updated dependencies [e27e7dd]
- @llamaindex/core@0.1.9
## 0.5.17
### Patch Changes
@@ -1,5 +1,28 @@
# @llamaindex/cloudflare-worker-agent-test
## 0.0.54
### Patch Changes
- Updated dependencies [d9d6c56]
- Updated dependencies [22ff486]
- Updated dependencies [eed0b04]
- llamaindex@0.5.20
## 0.0.53
### Patch Changes
- Updated dependencies [fcbf183]
- llamaindex@0.5.19
## 0.0.52
### Patch Changes
- Updated dependencies [8b66cf4]
- llamaindex@0.5.18
## 0.0.51
### Patch Changes
@@ -1,6 +1,6 @@
{
"name": "@llamaindex/cloudflare-worker-agent-test",
"version": "0.0.51",
"version": "0.0.54",
"type": "module",
"private": true,
"scripts": {
@@ -1,5 +1,28 @@
# @llamaindex/next-agent-test
## 0.1.54
### Patch Changes
- Updated dependencies [d9d6c56]
- Updated dependencies [22ff486]
- Updated dependencies [eed0b04]
- llamaindex@0.5.20
## 0.1.53
### Patch Changes
- Updated dependencies [fcbf183]
- llamaindex@0.5.19
## 0.1.52
### Patch Changes
- Updated dependencies [8b66cf4]
- llamaindex@0.5.18
## 0.1.51
### Patch Changes
@@ -1,6 +1,6 @@
{
"name": "@llamaindex/next-agent-test",
"version": "0.1.51",
"version": "0.1.54",
"private": true,
"scripts": {
"dev": "next dev",
@@ -1,5 +1,28 @@
# test-edge-runtime
## 0.1.53
### Patch Changes
- Updated dependencies [d9d6c56]
- Updated dependencies [22ff486]
- Updated dependencies [eed0b04]
- llamaindex@0.5.20
## 0.1.52
### Patch Changes
- Updated dependencies [fcbf183]
- llamaindex@0.5.19
## 0.1.51
### Patch Changes
- Updated dependencies [8b66cf4]
- llamaindex@0.5.18
## 0.1.50
### Patch Changes
@@ -1,6 +1,6 @@
{
"name": "@llamaindex/nextjs-edge-runtime-test",
"version": "0.1.50",
"version": "0.1.53",
"private": true,
"scripts": {
"dev": "next dev",
@@ -1,5 +1,28 @@
# @llamaindex/next-node-runtime
## 0.0.35
### Patch Changes
- Updated dependencies [d9d6c56]
- Updated dependencies [22ff486]
- Updated dependencies [eed0b04]
- llamaindex@0.5.20
## 0.0.34
### Patch Changes
- Updated dependencies [fcbf183]
- llamaindex@0.5.19
## 0.0.33
### Patch Changes
- Updated dependencies [8b66cf4]
- llamaindex@0.5.18
## 0.0.32
### Patch Changes
@@ -1,6 +1,6 @@
{
"name": "@llamaindex/next-node-runtime-test",
"version": "0.0.32",
"version": "0.0.35",
"private": true,
"scripts": {
"dev": "next dev",
@@ -1,5 +1,28 @@
# @llamaindex/waku-query-engine-test
## 0.0.54
### Patch Changes
- Updated dependencies [d9d6c56]
- Updated dependencies [22ff486]
- Updated dependencies [eed0b04]
- llamaindex@0.5.20
## 0.0.53
### Patch Changes
- Updated dependencies [fcbf183]
- llamaindex@0.5.19
## 0.0.52
### Patch Changes
- Updated dependencies [8b66cf4]
- llamaindex@0.5.18
## 0.0.51
### Patch Changes
@@ -1,6 +1,6 @@
{
"name": "@llamaindex/waku-query-engine-test",
"version": "0.0.51",
"version": "0.0.54",
"type": "module",
"private": true,
"scripts": {
+1 -1
View File
@@ -1,6 +1,6 @@
{
"name": "llamaindex",
"version": "0.5.17",
"version": "0.5.20",
"license": "MIT",
"type": "module",
"keywords": [
@@ -0,0 +1,99 @@
import {
FilesService,
PipelinesService,
ProjectsService,
} from "@llamaindex/cloud/api";
import { initService } from "./utils.js";
export class LLamaCloudFileService {
/**
* Get list of projects, each project contains a list of pipelines
*/
public static async getAllProjectsWithPipelines() {
initService();
try {
const projects = await ProjectsService.listProjectsApiV1ProjectsGet();
const pipelines =
await PipelinesService.searchPipelinesApiV1PipelinesGet();
return projects.map((project) => ({
...project,
pipelines: pipelines.filter((p) => p.project_id === project.id),
}));
} catch (error) {
console.error("Error listing projects and pipelines:", error);
return [];
}
}
/**
* Upload a file to a pipeline in LlamaCloud
*/
public static async addFileToPipeline(
projectId: string,
pipelineId: string,
uploadFile: File | Blob,
customMetadata: Record<string, any> = {},
) {
initService();
const file = await FilesService.uploadFileApiV1FilesPost({
projectId,
formData: {
upload_file: uploadFile,
},
});
const files = [
{
file_id: file.id,
custom_metadata: { file_id: file.id, ...customMetadata },
},
];
await PipelinesService.addFilesToPipelineApiV1PipelinesPipelineIdFilesPut({
pipelineId,
requestBody: files,
});
// Wait 2s for the file to be processed
const maxAttempts = 20;
let attempt = 0;
while (attempt < maxAttempts) {
const result =
await PipelinesService.getPipelineFileStatusApiV1PipelinesPipelineIdFilesFileIdStatusGet(
{
pipelineId,
fileId: file.id,
},
);
if (result.status === "ERROR") {
throw new Error(`File processing failed: ${JSON.stringify(result)}`);
}
if (result.status === "SUCCESS") {
// File is ingested - return the file id
return file.id;
}
attempt += 1;
await new Promise((resolve) => setTimeout(resolve, 100)); // Sleep for 100ms
}
throw new Error(
`File processing did not complete after ${maxAttempts} attempts.`,
);
}
/**
* Get download URL for a file in LlamaCloud
*/
public static async getFileUrl(pipelineId: string, filename: string) {
initService();
const allPipelineFiles =
await PipelinesService.listPipelineFilesApiV1PipelinesPipelineIdFilesGet({
pipelineId,
});
const file = allPipelineFiles.find((file) => file.name === filename);
if (!file?.file_id) return null;
const fileContent =
await FilesService.readFileContentApiV1FilesIdContentGet({
id: file.file_id,
projectId: file.project_id,
});
return fileContent.url;
}
}
@@ -8,7 +8,7 @@ import type { CloudRetrieveParams } from "./LlamaCloudRetriever.js";
import { LlamaCloudRetriever } from "./LlamaCloudRetriever.js";
import { getPipelineCreate } from "./config.js";
import type { CloudConstructorParams } from "./constants.js";
import { getAppBaseUrl, initService } from "./utils.js";
import { getAppBaseUrl, getProjectId, initService } from "./utils.js";
import { PipelinesService, ProjectsService } from "@llamaindex/cloud/api";
import { SentenceSplitter } from "@llamaindex/core/node-parser";
@@ -132,18 +132,28 @@ export class LlamaCloudIndex {
await this.waitForPipelineIngestion(verbose, raiseOnError);
}
private async getPipelineId(
name: string,
projectName: string,
public async getPipelineId(
name?: string,
projectName?: string,
): Promise<string> {
const pipelines = await PipelinesService.searchPipelinesApiV1PipelinesGet({
projectName,
pipelineName: name,
projectId: await this.getProjectId(projectName),
pipelineName: name ?? this.params.name,
});
return pipelines[0].id;
}
public async getProjectId(
projectName?: string,
organizationId?: string,
): Promise<string> {
return await getProjectId(
projectName ?? this.params.projectName,
organizationId ?? this.params.organizationId,
);
}
static async fromDocuments(
params: {
documents: Document[];
@@ -168,6 +178,7 @@ export class LlamaCloudIndex {
});
const project = await ProjectsService.upsertProjectApiV1ProjectsPut({
organizationId: params.organizationId,
requestBody: {
name: params.projectName ?? "default",
},
@@ -11,7 +11,7 @@ import { extractText, wrapEventCaller } from "@llamaindex/core/utils";
import type { BaseRetriever, RetrieveParams } from "../Retriever.js";
import type { ClientParams, CloudConstructorParams } from "./constants.js";
import { DEFAULT_PROJECT_NAME } from "./constants.js";
import { initService } from "./utils.js";
import { getProjectId, initService } from "./utils.js";
export type CloudRetrieveParams = Omit<
RetrievalParams,
@@ -21,6 +21,7 @@ export type CloudRetrieveParams = Omit<
export class LlamaCloudRetriever implements BaseRetriever {
clientParams: ClientParams;
retrieveParams: CloudRetrieveParams;
organizationId?: string;
projectName: string = DEFAULT_PROJECT_NAME;
pipelineName: string;
@@ -49,6 +50,9 @@ export class LlamaCloudRetriever implements BaseRetriever {
if (params.projectName) {
this.projectName = params.projectName;
}
if (params.organizationId) {
this.organizationId = params.organizationId;
}
}
@wrapEventCaller
@@ -57,7 +61,7 @@ export class LlamaCloudRetriever implements BaseRetriever {
preFilters,
}: RetrieveParams): Promise<NodeWithScore[]> {
const pipelines = await PipelinesService.searchPipelinesApiV1PipelinesGet({
projectName: this.projectName,
projectId: await getProjectId(this.projectName, this.organizationId),
pipelineName: this.pipelineName,
});
@@ -8,5 +8,6 @@ export type ClientParams = { apiKey?: string; baseUrl?: string };
export type CloudConstructorParams = {
name: string;
projectName: string;
organizationId?: string;
serviceContext?: ServiceContext;
} & ClientParams;
+1
View File
@@ -1,4 +1,5 @@
export type { CloudConstructorParams } from "./constants.js";
export { LLamaCloudFileService } from "./LLamaCloudFileService.js";
export { LlamaCloudIndex } from "./LlamaCloudIndex.js";
export {
LlamaCloudRetriever,
+29 -1
View File
@@ -1,4 +1,4 @@
import { OpenAPI } from "@llamaindex/cloud/api";
import { OpenAPI, ProjectsService } from "@llamaindex/cloud/api";
import { getEnv } from "@llamaindex/env";
import type { ClientParams } from "./constants.js";
import { DEFAULT_BASE_URL } from "./constants.js";
@@ -20,3 +20,31 @@ export function initService({ apiKey, baseUrl }: ClientParams = {}) {
);
}
}
export async function getProjectId(
projectName: string,
organizationId?: string,
): Promise<string> {
const projects = await ProjectsService.listProjectsApiV1ProjectsGet({
projectName: projectName,
organizationId: organizationId,
});
if (projects.length === 0) {
throw new Error(
`Unknown project name ${projectName}. Please confirm a managed project with this name exists.`,
);
} else if (projects.length > 1) {
throw new Error(
`Multiple projects found with name ${projectName}. Please specify organization_id.`,
);
}
const project = projects[0];
if (!project.id) {
throw new Error(`No project found with name ${projectName}`);
}
return project.id;
}
@@ -4,7 +4,7 @@ import type {
MessageContent,
MessageType,
} from "@llamaindex/core/llms";
import { EngineResponse } from "@llamaindex/core/schema";
import { EngineResponse, MetadataMode } from "@llamaindex/core/schema";
import {
extractText,
streamConverter,
@@ -53,6 +53,7 @@ export class ContextChatEngine extends PromptMixin implements ChatEngine {
contextSystemPrompt: init?.contextSystemPrompt,
nodePostprocessors: init?.nodePostprocessors,
contextRole: init?.contextRole,
metadataMode: MetadataMode.LLM,
});
this.systemPrompt = init.systemPrompt;
}
@@ -1,5 +1,5 @@
import type { MessageContent, MessageType } from "@llamaindex/core/llms";
import { type NodeWithScore } from "@llamaindex/core/schema";
import { MetadataMode, type NodeWithScore } from "@llamaindex/core/schema";
import type { BaseNodePostprocessor } from "../../postprocessors/index.js";
import type { ContextSystemPrompt } from "../../Prompt.js";
import { defaultContextSystemPrompt } from "../../Prompt.js";
@@ -16,12 +16,14 @@ export class DefaultContextGenerator
contextSystemPrompt: ContextSystemPrompt;
nodePostprocessors: BaseNodePostprocessor[];
contextRole: MessageType;
metadataMode?: MetadataMode;
constructor(init: {
retriever: BaseRetriever;
contextSystemPrompt?: ContextSystemPrompt;
nodePostprocessors?: BaseNodePostprocessor[];
contextRole?: MessageType;
metadataMode?: MetadataMode;
}) {
super();
@@ -30,6 +32,7 @@ export class DefaultContextGenerator
init?.contextSystemPrompt ?? defaultContextSystemPrompt;
this.nodePostprocessors = init.nodePostprocessors || [];
this.contextRole = init.contextRole ?? "system";
this.metadataMode = init.metadataMode ?? MetadataMode.NONE;
}
protected _getPrompts(): { contextSystemPrompt: ContextSystemPrompt } {
@@ -75,6 +78,8 @@ export class DefaultContextGenerator
const content = await createMessageContent(
this.contextSystemPrompt,
nodes.map((r) => r.node),
undefined,
this.metadataMode,
);
return {
+7
View File
@@ -17,6 +17,13 @@
*/
export default function withLlamaIndex(config: any) {
config.experimental = config.experimental ?? {};
// copy tiktoken WASM files to the NextJS build
config.experimental.outputFileTracingIncludes =
config.experimental.outputFileTracingIncludes ?? {};
config.experimental.outputFileTracingIncludes["/**/*"] = [
"./node_modules/tiktoken/*.wasm",
];
// needed for transformers, see https://huggingface.co/docs/transformers.js/en/tutorials/next#step-2-install-and-configure-transformersjs
config.experimental.serverComponentsExternalPackages =
config.experimental.serverComponentsExternalPackages ?? [];
config.experimental.serverComponentsExternalPackages.push(
@@ -1,13 +1,19 @@
import type pg from "pg";
import {
FilterCondition,
FilterOperator,
VectorStoreBase,
type IEmbedModel,
type MetadataFilter,
type MetadataFilterValue,
type VectorStoreNoEmbedModel,
type VectorStoreQuery,
type VectorStoreQueryResult,
} from "./types.js";
import { escapeLikeString } from "./utils.js";
import type { BaseNode, Metadata } from "@llamaindex/core/schema";
import { Document, MetadataMode } from "@llamaindex/core/schema";
@@ -246,6 +252,120 @@ export class PGVectorStore
return Promise.resolve();
}
private toPostgresCondition(condition: `${FilterCondition}`) {
if (condition === FilterCondition.AND) {
return "AND";
}
if (condition === FilterCondition.OR) {
return "OR";
}
// fallback to AND
else {
return "AND";
}
}
private toPostgresOperator(operator: `${FilterOperator}`) {
if (operator === FilterOperator.EQ) {
return "=";
}
if (operator === FilterOperator.GT) {
return ">";
}
if (operator === FilterOperator.LT) {
return "<";
}
if (operator === FilterOperator.NE) {
return "!=";
}
if (operator === FilterOperator.GTE) {
return ">=";
}
if (operator === FilterOperator.LTE) {
return "<=";
}
if (operator === FilterOperator.IN) {
return "= ANY";
}
if (operator === FilterOperator.NIN) {
return "!= ANY";
}
if (operator === FilterOperator.CONTAINS) {
return "@>";
}
if (operator === FilterOperator.ANY) {
return "?|";
}
if (operator === FilterOperator.ALL) {
return "?&";
}
// fallback to "="
return "=";
}
private buildFilterClause(
filter: MetadataFilter,
paramIndex: number,
): {
clause: string;
param: string | string[] | number | number[] | undefined;
} {
if (
filter.operator === FilterOperator.IN ||
filter.operator === FilterOperator.NIN
) {
return {
clause: `metadata->>'${filter.key}' ${this.toPostgresOperator(filter.operator)}($${paramIndex})`,
param: filter.value,
};
}
if (
filter.operator === FilterOperator.ALL ||
filter.operator === FilterOperator.ANY
) {
return {
clause: `metadata->'${filter.key}' ${this.toPostgresOperator(filter.operator)} $${paramIndex}::text[]`,
param: filter.value,
};
}
if (filter.operator === FilterOperator.CONTAINS) {
return {
clause: `metadata->'${filter.key}' ${this.toPostgresOperator(filter.operator)} $${paramIndex}::jsonb`,
param: JSON.stringify([filter.value]),
};
}
if (filter.operator === FilterOperator.IS_EMPTY) {
return {
clause: `(NOT (metadata ? '${filter.key}') OR metadata->>'${filter.key}' IS NULL OR metadata->>'${filter.key}' = '' OR metadata->'${filter.key}' = '[]'::jsonb)`,
param: undefined,
};
}
if (filter.operator === FilterOperator.TEXT_MATCH) {
const escapedValue = escapeLikeString(filter.value as string);
return {
clause: `metadata->>'${filter.key}' LIKE $${paramIndex}`,
param: `%${escapedValue}%`,
};
}
// if value is number, coerce metadata value to float
if (typeof filter.value === "number") {
return {
clause: `(metadata->>'${filter.key}')::float ${this.toPostgresOperator(filter.operator)} $${paramIndex}`,
param: filter.value,
};
}
return {
clause: `metadata->>'${filter.key}' ${this.toPostgresOperator(filter.operator)} $${paramIndex}`,
param: filter.value,
};
}
/**
* Query the vector store for the closest matching data to the query embeddings
* @param query The VectorStoreQuery to be used
@@ -265,19 +385,27 @@ export class PGVectorStore
const max = query.similarityTopK ?? 2;
const whereClauses = this.collection.length ? ["collection = $2"] : [];
const params: Array<string | number> = this.collection.length
const params: Array<MetadataFilterValue> = this.collection.length
? [embedding, this.collection]
: [embedding];
const filterClauses: string[] = [];
query.filters?.filters.forEach((filter, index) => {
const paramIndex = params.length + 1;
whereClauses.push(`metadata->>'${filter.key}' = $${paramIndex}`);
// TODO: support filter with other operators
if (!Array.isArray(filter.value) && filter.value) {
params.push(filter.value);
const { clause, param } = this.buildFilterClause(filter, paramIndex);
filterClauses.push(clause);
if (param) {
params.push(param);
}
});
if (filterClauses.length > 0) {
const condition = this.toPostgresCondition(
query.filters?.condition ?? FilterCondition.AND,
);
whereClauses.push(`(${filterClauses.join(` ${condition} `)})`);
}
const where =
whereClauses.length > 0 ? `WHERE ${whereClauses.join(" AND ")}` : "";
@@ -104,3 +104,7 @@ export const parseNumberValue = (value?: MetadataFilterValue): number => {
if (typeof value !== "number") throw new Error("Value must be a number");
return value;
};
export const escapeLikeString = (value: string) => {
return value.replace(/[%_\\]/g, "\\$&");
};
+24 -14
View File
@@ -163,7 +163,7 @@ importers:
version: link:../packages/llamaindex
mongodb:
specifier: ^6.7.0
version: 6.8.0(@aws-sdk/credential-providers@3.613.0)
version: 6.8.0(@aws-sdk/credential-providers@3.613.0(@aws-sdk/client-sso-oidc@3.613.0(@aws-sdk/client-sts@3.613.0)))
pathe:
specifier: ^1.1.2
version: 1.1.2
@@ -382,8 +382,8 @@ importers:
specifier: 5.3.1
version: 5.3.1(typescript@5.5.3)
natural:
specifier: ^7.1.0
version: 7.1.0(@aws-sdk/credential-providers@3.613.0)
specifier: ^8.0.1
version: 8.0.1(@aws-sdk/credential-providers@3.613.0)
packages/core/tests:
devDependencies:
@@ -568,7 +568,7 @@ importers:
version: 2.0.0
mongodb:
specifier: ^6.7.0
version: 6.8.0(@aws-sdk/credential-providers@3.613.0)
version: 6.8.0(@aws-sdk/credential-providers@3.613.0(@aws-sdk/client-sso-oidc@3.613.0(@aws-sdk/client-sts@3.613.0)))
notion-md-crawler:
specifier: ^1.0.0
version: 1.0.0(encoding@0.1.13)
@@ -8099,8 +8099,8 @@ packages:
natural-compare@1.4.0:
resolution: {integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==}
natural@7.1.0:
resolution: {integrity: sha512-GBhiRgF0VUX+zPWahBVir1ajARQDZF1Fe6UpQORNzyQT57JQ2KLKYvubecvjIYh/uDaociusmySeRh+WL5OdxQ==}
natural@8.0.1:
resolution: {integrity: sha512-VVw8O5KrfvwqAFeNZEgBbdgA+AQaBlHcXEootWU7TWDaFWFI0VLfzyKMsRjnfdS3cVCpWmI04xLJonCvEv11VQ==}
engines: {node: '>=0.4.10'}
negotiator@0.6.3:
@@ -12003,7 +12003,7 @@ snapshots:
'@babel/core': 7.24.7
'@babel/helper-compilation-targets': 7.24.7
'@babel/helper-plugin-utils': 7.24.7
debug: 4.3.5
debug: 4.3.6
lodash.debounce: 4.0.8
resolve: 1.22.8
transitivePeerDependencies:
@@ -15604,7 +15604,7 @@ snapshots:
dependencies:
'@typescript-eslint/types': 5.62.0
'@typescript-eslint/visitor-keys': 5.62.0
debug: 4.3.5
debug: 4.3.6
globby: 11.1.0
is-glob: 4.0.3
semver: 7.6.2
@@ -15942,7 +15942,7 @@ snapshots:
agent-base@6.0.2:
dependencies:
debug: 4.3.5
debug: 4.3.6
transitivePeerDependencies:
- supports-color
optional: true
@@ -17742,6 +17742,16 @@ snapshots:
- eslint-import-resolver-webpack
- supports-color
eslint-module-utils@2.8.1(@typescript-eslint/parser@7.16.0(eslint@8.57.0)(typescript@5.5.3))(eslint-import-resolver-node@0.3.9)(eslint@8.57.0):
dependencies:
debug: 3.2.7
optionalDependencies:
'@typescript-eslint/parser': 7.16.0(eslint@8.57.0)(typescript@5.5.3)
eslint: 8.57.0
eslint-import-resolver-node: 0.3.9
transitivePeerDependencies:
- supports-color
eslint-module-utils@2.8.1(@typescript-eslint/parser@7.2.0(eslint@8.57.0)(typescript@5.5.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.6.1(@typescript-eslint/parser@7.2.0(eslint@8.57.0)(typescript@5.5.3))(eslint-import-resolver-node@0.3.9)(eslint-plugin-import@2.29.1)(eslint@8.57.0))(eslint@8.57.0):
dependencies:
debug: 3.2.7
@@ -17763,7 +17773,7 @@ snapshots:
doctrine: 2.1.0
eslint: 8.57.0
eslint-import-resolver-node: 0.3.9
eslint-module-utils: 2.8.1(@typescript-eslint/parser@7.2.0(eslint@8.57.0)(typescript@5.5.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.6.1(@typescript-eslint/parser@7.2.0(eslint@8.57.0)(typescript@5.5.3))(eslint-import-resolver-node@0.3.9)(eslint-plugin-import@2.29.1)(eslint@8.57.0))(eslint@8.57.0)
eslint-module-utils: 2.8.1(@typescript-eslint/parser@7.16.0(eslint@8.57.0)(typescript@5.5.3))(eslint-import-resolver-node@0.3.9)(eslint@8.57.0)
hasown: 2.0.2
is-core-module: 2.14.0
is-glob: 4.0.3
@@ -20463,7 +20473,7 @@ snapshots:
optionalDependencies:
'@aws-sdk/credential-providers': 3.613.0(@aws-sdk/client-sso-oidc@3.613.0(@aws-sdk/client-sts@3.613.0))
mongodb@6.8.0(@aws-sdk/credential-providers@3.613.0):
mongodb@6.8.0(@aws-sdk/credential-providers@3.613.0(@aws-sdk/client-sso-oidc@3.613.0(@aws-sdk/client-sts@3.613.0))):
dependencies:
'@mongodb-js/saslprep': 1.1.7
bson: 6.8.0
@@ -20494,7 +20504,7 @@ snapshots:
mquery@5.0.0:
dependencies:
debug: 4.3.5
debug: 4.3.6
transitivePeerDependencies:
- supports-color
@@ -20532,7 +20542,7 @@ snapshots:
natural-compare@1.4.0: {}
natural@7.1.0(@aws-sdk/credential-providers@3.613.0):
natural@8.0.1(@aws-sdk/credential-providers@3.613.0):
dependencies:
afinn-165: 1.0.4
afinn-165-financialmarketnews: 3.0.0
@@ -22645,7 +22655,7 @@ snapshots:
spdy-transport@3.0.0:
dependencies:
debug: 4.3.5
debug: 4.3.6
detect-node: 2.1.0
hpack.js: 2.1.6
obuf: 1.1.2