Compare commits

..

9 Commits

Author SHA1 Message Date
yisding 4431ec7a5e changeset 2023-11-14 20:53:42 -08:00
yisding 9542026d70 Merge pull request #196 from run-llama/ms/fix-label-for-simple-chat
fix: label for simple chat
2023-11-14 20:49:27 -08:00
Marcus Schiesser cc4c5b64c0 fix: label for simple chat 2023-11-15 11:06:26 +07:00
yisding 82c2aac4a0 update replicate version 2023-11-14 16:41:57 -08:00
yisding a143e0f0f1 new replicate models 2023-11-14 16:40:36 -08:00
yisding db9775dc32 sync examples 2023-11-14 16:20:57 -08:00
yisding 538c0b0740 hopefully fix prettier issue 2023-11-14 16:17:53 -08:00
yisding 21cd88caf6 prettier 2023-11-14 16:06:18 -08:00
yisding 0660d9e2a5 create-llama 0.0.5 2023-11-14 15:04:41 -08:00
42 changed files with 1318 additions and 701 deletions
-5
View File
@@ -1,5 +0,0 @@
---
"create-llama": patch
---
Fix issue where it doesn't find OpenAI Key when running npm run generate (#182) (thanks @RayFernando1337)
+5
View File
@@ -0,0 +1,5 @@
---
"create-llama": patch
---
Label bug fix
+1
View File
@@ -2,3 +2,4 @@
. "$(dirname -- "$0")/_/husky.sh"
pnpm lint
npx lint-staged
+1 -1
View File
@@ -89,7 +89,7 @@ Check out our NextJS playground at https://llama-playground.vercel.app/. The sou
If you're using NextJS App Router, you'll need to use the NodeJS runtime (default) and add the follow config to your next.config.js to have it use imports/exports in the same way Node does.
```js
export const runtime = "nodejs" // default
export const runtime = "nodejs"; // default
```
```js
+1 -1
View File
@@ -11,7 +11,7 @@ LlamaIndex currently officially supports NodeJS 18 and NodeJS 20.
If you're using NextJS App Router route handlers/serverless functions, you'll need to use the NodeJS mode:
```js
export const runtime = "nodejs" // default
export const runtime = "nodejs"; // default
```
and you'll need to add an exception for pdf-parse in your next.config.js
+1 -1
View File
@@ -6,7 +6,7 @@ import readline from "node:readline/promises";
import { ChatMessage, LlamaDeuce, OpenAI } from "llamaindex";
(async () => {
const gpt4 = new OpenAI({ model: "gpt-4-vision-preview", temperature: 0.9 });
const gpt4 = new OpenAI({ model: "gpt-4", temperature: 0.9 });
const l2 = new LlamaDeuce({
model: "Llama-2-70b-chat-4bit",
temperature: 0.9,
+2 -2
View File
@@ -1,7 +1,7 @@
import { ChatMessage, OpenAI, SimpleChatEngine } from "llamaindex";
import {Anthropic} from "../../packages/core/src/llm/LLM";
import { ChatMessage, SimpleChatEngine } from "llamaindex";
import { stdin as input, stdout as output } from "node:process";
import readline from "node:readline/promises";
import { Anthropic } from "../../packages/core/src/llm/LLM";
async function main() {
const query: string = `
+1 -1
View File
@@ -1,6 +1,6 @@
import { MongoClient } from "mongodb";
import { VectorStoreIndex } from "../../packages/core/src/indices";
import { Document } from "../../packages/core/src/Node";
import { VectorStoreIndex } from "../../packages/core/src/indices";
import { SimpleMongoReader } from "../../packages/core/src/readers/SimpleMongoReader";
import { stdin as input, stdout as output } from "node:process";
+11 -11
View File
@@ -1,23 +1,23 @@
import { Portkey } from "llamaindex";
(async () => {
const llms = [{
}]
const llms = [{}];
const portkey = new Portkey({
mode: "single",
llms: [{
provider:"anyscale",
virtual_key:"anyscale-3b3c04",
model: "meta-llama/Llama-2-13b-chat-hf",
max_tokens: 2000
}]
llms: [
{
provider: "anyscale",
virtual_key: "anyscale-3b3c04",
model: "meta-llama/Llama-2-13b-chat-hf",
max_tokens: 2000,
},
],
});
const result = portkey.stream_chat([
{ role: "system", content: "You are a helpful assistant." },
{ role: "user", content: "Tell me a joke." }
{ role: "user", content: "Tell me a joke." },
]);
for await (const res of result) {
process.stdout.write(res)
process.stdout.write(res);
}
})();
+24
View File
@@ -0,0 +1,24 @@
import { SimpleDirectoryReader } from "llamaindex";
function callback(
category: string,
name: string,
status: any,
message?: string,
): boolean {
console.log(category, name, status, message);
if (name.endsWith(".pdf")) {
console.log("I DON'T WANT PDF FILES!");
return false;
}
return true;
}
async function main() {
// Load page
const reader = new SimpleDirectoryReader(callback);
const params = { directoryPath: "./data" };
await reader.loadData(params);
}
main().catch(console.error);
+21
View File
@@ -0,0 +1,21 @@
import { HTMLReader, VectorStoreIndex } from "llamaindex";
async function main() {
// Load page
const reader = new HTMLReader();
const documents = await reader.loadData("data/18-1_Changelog.html");
// Split text and create embeddings. Store them in a VectorStoreIndex
const index = await VectorStoreIndex.fromDocuments(documents);
// Query the index
const queryEngine = index.asQueryEngine();
const response = await queryEngine.query(
"What were the notable changes in 18.1?",
);
// Output response
console.log(response.toString());
}
main().catch(console.error);
+47
View File
@@ -0,0 +1,47 @@
import { ChatMessage, SimpleChatEngine } from "llamaindex";
import { stdin as input, stdout as output } from "node:process";
import readline from "node:readline/promises";
import { Anthropic } from "../../packages/core/src/llm/LLM";
async function main() {
const query: string = `
Where is Istanbul?
`;
// const llm = new OpenAI({ model: "gpt-3.5-turbo", temperature: 0.1 });
const llm = new Anthropic();
const message: ChatMessage = { content: query, role: "user" };
//TODO: Add callbacks later
//Stream Complete
//Note: Setting streaming flag to true or false will auto-set your return type to
//either an AsyncGenerator or a Response.
// Omitting the streaming flag automatically sets streaming to false
const chatEngine: SimpleChatEngine = new SimpleChatEngine({
chatHistory: undefined,
llm: llm,
});
const rl = readline.createInterface({ input, output });
while (true) {
const query = await rl.question("Query: ");
if (!query) {
break;
}
//Case 1: .chat(query, undefined, true) => Stream
//Case 2: .chat(query, undefined, false) => Response object
//Case 3: .chat(query, undefined) => Response object
const chatStream = await chatEngine.chat(query, undefined, true);
var accumulated_result = "";
for await (const part of chatStream) {
accumulated_result += part;
process.stdout.write(part);
}
}
}
main();
+68
View File
@@ -0,0 +1,68 @@
import { MongoClient } from "mongodb";
import { Document } from "../../packages/core/src/Node";
import { VectorStoreIndex } from "../../packages/core/src/indices";
import { SimpleMongoReader } from "../../packages/core/src/readers/SimpleMongoReader";
import { stdin as input, stdout as output } from "node:process";
import readline from "node:readline/promises";
async function main() {
//Dummy test code
const query: object = { _id: "waldo" };
const options: object = {};
const projections: object = { embedding: 0 };
const limit: number = Infinity;
const uri: string = process.env.MONGODB_URI ?? "fake_uri";
const client: MongoClient = new MongoClient(uri);
//Where the real code starts
const MR = new SimpleMongoReader(client);
const documents: Document[] = await MR.loadData(
"data",
"posts",
1,
{},
options,
projections,
);
//
//If you need to look at low-level details of
// a queryEngine (for example, needing to check each individual node)
//
// Split text and create embeddings. Store them in a VectorStoreIndex
// var storageContext = await storageContextFromDefaults({});
// var serviceContext = serviceContextFromDefaults({});
// const docStore = storageContext.docStore;
// for (const doc of documents) {
// docStore.setDocumentHash(doc.id_, doc.hash);
// }
// const nodes = serviceContext.nodeParser.getNodesFromDocuments(documents);
// console.log(nodes);
//
//Making Vector Store from documents
//
const index = await VectorStoreIndex.fromDocuments(documents);
// Create query engine
const queryEngine = index.asQueryEngine();
const rl = readline.createInterface({ input, output });
while (true) {
const query = await rl.question("Query: ");
if (!query) {
break;
}
const response = await queryEngine.query(query);
// Output response
console.log(response.toString());
}
}
main();
+11 -11
View File
@@ -1,23 +1,23 @@
import { Portkey } from "llamaindex";
(async () => {
const llms = [{
}]
const llms = [{}];
const portkey = new Portkey({
mode: "single",
llms: [{
provider:"anyscale",
virtual_key:"anyscale-3b3c04",
model: "meta-llama/Llama-2-13b-chat-hf",
max_tokens: 2000
}]
llms: [
{
provider: "anyscale",
virtual_key: "anyscale-3b3c04",
model: "meta-llama/Llama-2-13b-chat-hf",
max_tokens: 2000,
},
],
});
const result = portkey.stream_chat([
{ role: "system", content: "You are a helpful assistant." },
{ role: "user", content: "Tell me a joke." }
{ role: "user", content: "Tell me a joke." },
]);
for await (const res of result) {
process.stdout.write(res)
process.stdout.write(res);
}
})();
+10 -1
View File
@@ -3,6 +3,7 @@ import {
OpenAI,
RetrieverQueryEngine,
serviceContextFromDefaults,
SimilarityPostprocessor,
VectorStoreIndex,
} from "llamaindex";
import essay from "./essay";
@@ -21,8 +22,16 @@ async function main() {
const retriever = index.asRetriever();
retriever.similarityTopK = 5;
const nodePostprocessor = new SimilarityPostprocessor({
similarityCutoff: 0.7,
});
// TODO: cannot pass responseSynthesizer into retriever query engine
const queryEngine = new RetrieverQueryEngine(retriever);
const queryEngine = new RetrieverQueryEngine(
retriever,
undefined,
undefined,
[nodePostprocessor],
);
const response = await queryEngine.query(
"What did the author do growing up?",
+197
View File
@@ -0,0 +1,197 @@
import {
OpenAI,
ResponseSynthesizer,
RetrieverQueryEngine,
serviceContextFromDefaults,
TextNode,
TreeSummarize,
VectorIndexRetriever,
VectorStore,
VectorStoreIndex,
VectorStoreQuery,
VectorStoreQueryResult,
} from "llamaindex";
import { Index, Pinecone, RecordMetadata } from "@pinecone-database/pinecone";
/**
* Please do not use this class in production; it's only for demonstration purposes.
*/
class PineconeVectorStore<T extends RecordMetadata = RecordMetadata>
implements VectorStore
{
storesText = true;
isEmbeddingQuery = false;
indexName!: string;
pineconeClient!: Pinecone;
index!: Index<T>;
constructor({ indexName, client }: { indexName: string; client: Pinecone }) {
this.indexName = indexName;
this.pineconeClient = client;
this.index = client.index<T>(indexName);
}
client() {
return this.pineconeClient;
}
async query(
query: VectorStoreQuery,
kwargs?: any,
): Promise<VectorStoreQueryResult> {
let queryEmbedding: number[] = [];
if (query.queryEmbedding) {
if (typeof query.alpha === "number") {
const alpha = query.alpha;
queryEmbedding = query.queryEmbedding.map((v) => v * alpha);
} else {
queryEmbedding = query.queryEmbedding;
}
}
// Current LlamaIndexTS implementation only support exact match filter, so we use kwargs instead.
const filter = kwargs?.filter || {};
const response = await this.index.query({
filter,
vector: queryEmbedding,
topK: query.similarityTopK,
includeValues: true,
includeMetadata: true,
});
console.log(
`Numbers of vectors returned by Pinecone after preFilters are applied: ${
response?.matches?.length || 0
}.`,
);
const topKIds: string[] = [];
const topKNodes: TextNode[] = [];
const topKScores: number[] = [];
const metadataToNode = (metadata?: T): Partial<TextNode> => {
if (!metadata) {
throw new Error("metadata is undefined.");
}
const nodeContent = metadata["_node_content"];
if (!nodeContent) {
throw new Error("nodeContent is undefined.");
}
if (typeof nodeContent !== "string") {
throw new Error("nodeContent is not a string.");
}
return JSON.parse(nodeContent);
};
if (response.matches) {
for (const match of response.matches) {
const node = new TextNode({
...metadataToNode(match.metadata),
embedding: match.values,
});
topKIds.push(match.id);
topKNodes.push(node);
topKScores.push(match.score ?? 0);
}
}
const result = {
ids: topKIds,
nodes: topKNodes,
similarities: topKScores,
};
return result;
}
add(): Promise<string[]> {
return Promise.resolve([]);
}
delete(): Promise<void> {
throw new Error("Method `delete` not implemented.");
}
persist(): Promise<void> {
throw new Error("Method `persist` not implemented.");
}
}
/**
* The goal of this example is to show how to use Pinecone as a vector store
* for LlamaIndexTS with(out) preFilters.
*
* It should not be used in production like that,
* as you might want to find a proper PineconeVectorStore implementation.
*/
async function main() {
process.env.PINECONE_API_KEY = "Your Pinecone API Key.";
process.env.PINECONE_ENVIRONMENT = "Your Pinecone Environment.";
process.env.PINECONE_PROJECT_ID = "Your Pinecone Project ID.";
process.env.PINECONE_INDEX_NAME = "Your Pinecone Index Name.";
process.env.OPENAI_API_KEY = "Your OpenAI API Key.";
process.env.OPENAI_API_ORGANIZATION = "Your OpenAI API Organization.";
const getPineconeVectorStore = async () => {
return new PineconeVectorStore({
indexName: process.env.PINECONE_INDEX_NAME || "index-name",
client: new Pinecone(),
});
};
const getServiceContext = () => {
const openAI = new OpenAI({
model: "gpt-4",
apiKey: process.env.OPENAI_API_KEY,
});
return serviceContextFromDefaults({
llm: openAI,
});
};
const getQueryEngine = async (filter: unknown) => {
const vectorStore = await getPineconeVectorStore();
const serviceContext = getServiceContext();
const vectorStoreIndex = await VectorStoreIndex.fromVectorStore(
vectorStore,
serviceContext,
);
const retriever = new VectorIndexRetriever({
index: vectorStoreIndex,
similarityTopK: 500,
});
const responseSynthesizer = new ResponseSynthesizer({
serviceContext,
responseBuilder: new TreeSummarize(serviceContext),
});
return new RetrieverQueryEngine(retriever, responseSynthesizer, {
filter,
});
};
// whatever is a key from your metadata
const queryEngine = await getQueryEngine({
whatever: {
$gte: 1,
$lte: 100,
},
});
const response = await queryEngine.query("How many results do you have?");
console.log(response.toString());
}
main().catch(console.error);
+15
View File
@@ -0,0 +1,15 @@
import { OpenAI } from "llamaindex";
(async () => {
const llm = new OpenAI({ model: "gpt-4-vision-preview", temperature: 0.1 });
// complete api
const response1 = await llm.complete("How are you?");
console.log(response1.message.content);
// chat api
const response2 = await llm.chat([
{ content: "Tell me a joke!", role: "user" },
]);
console.log(response2.message.content);
})();
+11 -9
View File
@@ -3,7 +3,7 @@
"scripts": {
"build": "turbo run build",
"dev": "turbo run dev",
"format": "prettier --write \"**/*.{ts,tsx,md}\"",
"format": "prettier --write \"**/*.{js,jsx,ts,tsx,md}\"",
"lint": "turbo run lint",
"prepare": "husky install",
"test": "turbo run test",
@@ -11,25 +11,27 @@
"publish-snapshot": "turbo run build lint test && changeset version --snapshot && changeset publish"
},
"devDependencies": {
"@changesets/cli": "^2.26.2",
"@turbo/gen": "^1.10.16",
"@types/jest": "^29.5.6",
"eslint": "^8.52.0",
"@types/jest": "^29.5.8",
"eslint": "^8.53.0",
"eslint-config-custom": "workspace:*",
"husky": "^8.0.3",
"jest": "^29.7.0",
"prettier": "^3.0.3",
"prettier-plugin-organize-imports": "^3.2.3",
"lint-staged": "^15.1.0",
"prettier": "^3.1.0",
"prettier-plugin-organize-imports": "^3.2.4",
"ts-jest": "^29.1.1",
"turbo": "^1.10.16"
},
"packageManager": "pnpm@8.10.4+sha256.df3202c6c8fd345be5ba6a4199297582d5bebf8963822aa3344f4cd2b8be8d43",
"dependencies": {
"@changesets/cli": "^2.26.2"
},
"packageManager": "pnpm@8.10.5+sha256.a4bd9bb7b48214bbfcd95f264bd75bb70d100e5d4b58808f5cd6ab40c6ac21c5",
"pnpm": {
"overrides": {
"trim": "1.0.1",
"@babel/traverse": "7.23.2"
}
},
"lint-staged": {
"*.{js,jsx,ts,tsx,md}": "prettier --write"
}
}
+1 -1
View File
@@ -16,7 +16,7 @@
"pdf-parse": "^1.1.1",
"portkey-ai": "^0.1.16",
"rake-modified": "^1.0.8",
"replicate": "^0.20.1",
"replicate": "^0.21.1",
"string-strip-html": "^13.4.3",
"uuid": "^9.0.1",
"wink-nlp": "^1.14.3"
+5 -5
View File
@@ -1,4 +1,4 @@
import { encodingForModel, TiktokenModel } from "js-tiktoken";
import { encodingForModel } from "js-tiktoken";
import { v4 as uuidv4 } from "uuid";
import { Event, EventTag, EventType } from "./callbacks/CallbackManager";
@@ -27,7 +27,7 @@ class GlobalsHelper {
const numberArray = Array.from(tokens);
const text = encoding.decode(numberArray);
const uint8Array = new TextEncoder().encode(text);
return new TextDecoder().decode(uint8Array);
return new TextDecoder().decode(uint8Array);
},
};
}
@@ -39,10 +39,10 @@ class GlobalsHelper {
if (!this.defaultTokenizer) {
this.initDefaultTokenizer();
}
return this.defaultTokenizer!.encode.bind(this.defaultTokenizer);
}
tokenizerDecoder(encoding?: string) {
if (encoding && encoding !== Tokenizers.CL100K_BASE) {
throw new Error(`Tokenizer encoding ${encoding} not yet supported`);
@@ -50,7 +50,7 @@ class GlobalsHelper {
if (!this.defaultTokenizer) {
this.initDefaultTokenizer();
}
return this.defaultTokenizer!.decode.bind(this.defaultTokenizer);
}
+2 -2
View File
@@ -1,6 +1,4 @@
import { v4 as uuidv4 } from "uuid";
import { Event } from "./callbacks/CallbackManager";
import { BaseNodePostprocessor } from "./indices/BaseNodePostprocessor";
import { NodeWithScore, TextNode } from "./Node";
import {
BaseQuestionGenerator,
@@ -12,6 +10,8 @@ import { CompactAndRefine, ResponseSynthesizer } from "./ResponseSynthesizer";
import { BaseRetriever } from "./Retriever";
import { ServiceContext, serviceContextFromDefaults } from "./ServiceContext";
import { QueryEngineTool, ToolMetadata } from "./Tool";
import { Event } from "./callbacks/CallbackManager";
import { BaseNodePostprocessor } from "./indices/BaseNodePostprocessor";
/**
* A query engine is a question answerer that can use one or more steps.
+12 -12
View File
@@ -1,11 +1,7 @@
export * from "./callbacks/CallbackManager";
export * from "./ChatEngine";
export * from "./ChatHistory";
export * from "./constants";
export * from "./Embedding";
export * from "./GlobalsHelper";
export * from "./indices";
export * from "./llm/LLM";
export * from "./Node";
export * from "./NodeParser";
export * from "./OutputParser";
@@ -13,17 +9,21 @@ export * from "./Prompt";
export * from "./PromptHelper";
export * from "./QueryEngine";
export * from "./QuestionGenerator";
export * from "./readers/base";
export * from "./readers/CSVReader";
export * from "./readers/MarkdownReader";
export * from "./readers/NotionReader";
export * from "./readers/PDFReader";
export * from "./readers/HTMLReader";
export * from "./readers/SimpleDirectoryReader";
export * from "./Response";
export * from "./ResponseSynthesizer";
export * from "./Retriever";
export * from "./ServiceContext";
export * from "./storage";
export * from "./TextSplitter";
export * from "./Tool";
export * from "./callbacks/CallbackManager";
export * from "./constants";
export * from "./indices";
export * from "./llm/LLM";
export * from "./readers/CSVReader";
export * from "./readers/HTMLReader";
export * from "./readers/MarkdownReader";
export * from "./readers/NotionReader";
export * from "./readers/PDFReader";
export * from "./readers/SimpleDirectoryReader";
export * from "./readers/base";
export * from "./storage";
@@ -10,11 +10,11 @@ import {
ServiceContext,
serviceContextFromDefaults,
} from "../../ServiceContext";
import { BaseDocumentStore, RefDocInfo } from "../../storage/docStore/types";
import {
StorageContext,
storageContextFromDefaults,
} from "../../storage/StorageContext";
import { BaseDocumentStore, RefDocInfo } from "../../storage/docStore/types";
import {
BaseIndex,
BaseIndexInit,
@@ -32,7 +32,11 @@ export class VectorIndexRetriever implements BaseRetriever {
this.similarityTopK = similarityTopK ?? DEFAULT_SIMILARITY_TOP_K;
}
async retrieve(query: string, parentEvent?: Event, preFilters?: unknown): Promise<NodeWithScore[]> {
async retrieve(
query: string,
parentEvent?: Event,
preFilters?: unknown,
): Promise<NodeWithScore[]> {
const queryEmbedding =
await this.serviceContext.embedModel.getQueryEmbedding(query);
+38 -13
View File
@@ -377,10 +377,10 @@ export const ALL_AVAILABLE_LLAMADEUCE_MODELS = {
"Llama-2-70b-chat-4bit": {
contextWindow: 4096,
replicateApi:
"replicate/llama70b-v2-chat:2c1608e18606fad2812020dc541930f2d0495ce32eee50074220b87300bc16e1",
"meta/llama-2-70b-chat:02e509c789964a7ea8736978a43525956ef40397be9033abf9fd2badfe68c9e3",
//^ Model is based off of exllama 4bit.
},
"Llama-2-13b-chat": {
"Llama-2-13b-chat-old": {
contextWindow: 4096,
replicateApi:
"a16z-infra/llama13b-v2-chat:df7690f1994d94e96ad9d568eac121aecf50684a0b0963b25a41cc40061269e5",
@@ -389,9 +389,9 @@ export const ALL_AVAILABLE_LLAMADEUCE_MODELS = {
"Llama-2-13b-chat-4bit": {
contextWindow: 4096,
replicateApi:
"a16z-infra/llama13b-v2-chat:2a7f981751ec7fdf87b5b91ad4db53683a98082e9ff7bfd12c8cd5ea85980a52",
"meta/llama-2-13b-chat:f4e2de70d66816a838a89eeeb621910adffb0dd0baba3976c96980970978018d",
},
"Llama-2-7b-chat": {
"Llama-2-7b-chat-old": {
contextWindow: 4096,
replicateApi:
"a16z-infra/llama7b-v2-chat:4f0a4744c7295c024a1de15e1a63c880d3da035fa1f49bfd344fe076074c8eea",
@@ -403,7 +403,7 @@ export const ALL_AVAILABLE_LLAMADEUCE_MODELS = {
"Llama-2-7b-chat-4bit": {
contextWindow: 4096,
replicateApi:
"a16z-infra/llama7b-v2-chat:4f0b260b6a13eb53a6b1891f089d57c08f41003ae79458be5011303d81a394dc",
"meta/llama-2-7b-chat:13c3cdee13ee059ab779f0291d29054dab00a47dad8261375654de5540165fb0",
},
};
@@ -415,6 +415,8 @@ export enum DeuceChatStrategy {
// Unfortunately any string only API won't support these properly.
REPLICATE4BIT = "replicate4bit",
//^ To satisfy Replicate's 4 bit models' requirements where they also insert some INST tags
REPLICATE4BITWNEWLINES = "replicate4bitwnewlines",
//^ Replicate's documentation recommends using newlines: https://replicate.com/blog/how-to-prompt-llama
}
/**
@@ -434,7 +436,7 @@ export class LlamaDeuce implements LLM {
this.chatStrategy =
init?.chatStrategy ??
(this.model.endsWith("4bit")
? DeuceChatStrategy.REPLICATE4BIT // With the newer A16Z/Replicate models they do the system message themselves.
? DeuceChatStrategy.REPLICATE4BITWNEWLINES // With the newer Replicate models they do the system message themselves.
: DeuceChatStrategy.METAWBOS); // With BOS and EOS seems to work best, although they all have problems past a certain point
this.temperature = init?.temperature ?? 0.1; // minimum temperature is 0.01 for Replicate endpoint
this.topP = init?.topP ?? 1;
@@ -468,7 +470,15 @@ export class LlamaDeuce implements LLM {
} else if (this.chatStrategy === DeuceChatStrategy.METAWBOS) {
return this.mapMessagesToPromptMeta(messages, { withBos: true });
} else if (this.chatStrategy === DeuceChatStrategy.REPLICATE4BIT) {
return this.mapMessagesToPromptMeta(messages, { replicate4Bit: true });
return this.mapMessagesToPromptMeta(messages, {
replicate4Bit: true,
withNewlines: true,
});
} else if (this.chatStrategy === DeuceChatStrategy.REPLICATE4BITWNEWLINES) {
return this.mapMessagesToPromptMeta(messages, {
replicate4Bit: true,
withNewlines: true,
});
} else {
return this.mapMessagesToPromptMeta(messages);
}
@@ -503,9 +513,17 @@ export class LlamaDeuce implements LLM {
mapMessagesToPromptMeta(
messages: ChatMessage[],
opts?: { withBos?: boolean; replicate4Bit?: boolean },
opts?: {
withBos?: boolean;
replicate4Bit?: boolean;
withNewlines?: boolean;
},
) {
const { withBos = false, replicate4Bit = false } = opts ?? {};
const {
withBos = false,
replicate4Bit = false,
withNewlines = false,
} = opts ?? {};
const DEFAULT_SYSTEM_PROMPT = `You are a helpful, respectful and honest assistant. Always answer as helpfully as possible, while being safe. Your answers should not include any harmful, unethical, racist, sexist, toxic, dangerous, or illegal content. Please ensure that your responses are socially unbiased and positive in nature.
If a question does not make any sense, or is not factually coherent, explain why instead of answering something not correct. If you don't know the answer to a question, please don't share false information.`;
@@ -553,11 +571,18 @@ If a question does not make any sense, or is not factually coherent, explain why
return {
prompt: messages.reduce((acc, message, index) => {
if (index % 2 === 0) {
return `${acc}${
withBos ? BOS : ""
}${B_INST} ${message.content.trim()} ${E_INST}`;
return (
`${acc}${
withBos ? BOS : ""
}${B_INST} ${message.content.trim()} ${E_INST}` +
(withNewlines ? "\n" : "")
);
} else {
return `${acc} ${message.content.trim()} ` + (withBos ? EOS : ""); // Yes, the EOS comes after the space. This is not a mistake.
return (
`${acc} ${message.content.trim()}` +
(withNewlines ? "\n" : " ") +
(withBos ? EOS : "")
); // Yes, the EOS comes after the space. This is not a mistake.
}
}, ""),
systemPrompt,
+11 -9
View File
@@ -1,9 +1,12 @@
import _ from "lodash";
import { LLMOptions, Portkey } from "portkey-ai";
export const readEnv = (env: string, default_val?: string): string | undefined => {
if (typeof process !== 'undefined') {
return process.env?.[env] ?? default_val;
export const readEnv = (
env: string,
default_val?: string,
): string | undefined => {
if (typeof process !== "undefined") {
return process.env?.[env] ?? default_val;
}
return default_val;
};
@@ -12,23 +15,23 @@ interface PortkeyOptions {
apiKey?: string;
baseURL?: string;
mode?: string;
llms?: [LLMOptions] | null
llms?: [LLMOptions] | null;
}
export class PortkeySession {
portkey: Portkey;
constructor(options:PortkeyOptions = {}) {
constructor(options: PortkeyOptions = {}) {
if (!options.apiKey) {
options.apiKey = readEnv('PORTKEY_API_KEY')
options.apiKey = readEnv("PORTKEY_API_KEY");
}
if (!options.baseURL) {
options.baseURL = readEnv('PORTKEY_BASE_URL', "https://api.portkey.ai")
options.baseURL = readEnv("PORTKEY_BASE_URL", "https://api.portkey.ai");
}
this.portkey = new Portkey({});
this.portkey.llms = [{}]
this.portkey.llms = [{}];
if (!options.apiKey) {
throw new Error("Set Portkey ApiKey in PORTKEY_API_KEY env variable");
}
@@ -59,4 +62,3 @@ export function getPortkeySession(options: PortkeyOptions = {}) {
}
return session;
}
+1 -1
View File
@@ -1,7 +1,7 @@
import mammoth from "mammoth";
import { Document } from "../Node";
import { DEFAULT_FS } from "../storage/constants";
import { GenericFileSystem } from "../storage/FileSystem";
import { DEFAULT_FS } from "../storage/constants";
import { BaseReader } from "./base";
export class DocxReader implements BaseReader {
+6
View File
@@ -1,5 +1,11 @@
# create-llama
## 0.0.5
### Patch Changes
- 25257f4: Fix issue where it doesn't find OpenAI Key when running npm run generate (#182) (thanks @RayFernando1337)
## 0.0.4
### Patch Changes
+1 -1
View File
@@ -31,7 +31,7 @@ You will be asked for the name of your project, along with other configuration o
Here is an example:
```bash
>> npm create llama
>> npm create llama@latest
Need to install the following packages:
create-llama@latest
Ok to proceed? (y) y
+10 -10
View File
@@ -79,10 +79,10 @@ const program = new Commander.Command(packageJson.name)
const packageManager = !!program.useNpm
? "npm"
: !!program.usePnpm
? "pnpm"
: !!program.useYarn
? "yarn"
: getPkgManager();
? "pnpm"
: !!program.useYarn
? "yarn"
: getPkgManager();
async function run(): Promise<void> {
const conf = new Conf({ projectName: "create-llama" });
@@ -235,8 +235,8 @@ async function run(): Promise<void> {
program.framework === "express"
? "Express "
: program.framework === "fastapi"
? "FastAPI (Python) "
: "",
? "FastAPI (Python) "
: "",
);
const { frontend } = await prompts({
onState: onPromptState,
@@ -290,8 +290,8 @@ async function run(): Promise<void> {
choices: [
{ title: "ContextChatEngine", value: "context" },
{
title: "SimpleChatEngine",
value: "simple (no data, just chat)",
title: "SimpleChatEngine (no data, just chat)",
value: "simple",
},
],
initial: 0,
@@ -364,8 +364,8 @@ async function notifyUpdate(): Promise<void> {
packageManager === "yarn"
? "yarn global add create-llama@latest"
: packageManager === "pnpm"
? "pnpm add -g create-llama@latest"
: "npm i -g create-llama@latest";
? "pnpm add -g create-llama@latest"
: "npm i -g create-llama@latest";
console.log(
yellow(bold("A new version of `create-llama` is available!")) +
+1 -1
View File
@@ -1,6 +1,6 @@
{
"name": "create-llama",
"version": "0.0.4",
"version": "0.0.5",
"keywords": [
"rag",
"llamaindex",
@@ -1,23 +1,23 @@
"use client"
"use client";
import React, { FC, memo } from "react"
import { Check, Copy, Download } from "lucide-react"
import { Prism, SyntaxHighlighterProps } from "react-syntax-highlighter"
import { coldarkDark } from "react-syntax-highlighter/dist/cjs/styles/prism"
import { Check, Copy, Download } from "lucide-react";
import { FC, memo } from "react";
import { Prism, SyntaxHighlighterProps } from "react-syntax-highlighter";
import { coldarkDark } from "react-syntax-highlighter/dist/cjs/styles/prism";
import { Button } from "../button"
import { useCopyToClipboard } from "./use-copy-to-clipboard"
import { Button } from "../button";
import { useCopyToClipboard } from "./use-copy-to-clipboard";
// TODO: Remove this when @type/react-syntax-highlighter is updated
const SyntaxHighlighter = Prism as unknown as FC<SyntaxHighlighterProps>
const SyntaxHighlighter = Prism as unknown as FC<SyntaxHighlighterProps>;
interface Props {
language: string
value: string
language: string;
value: string;
}
interface languageMap {
[key: string]: string | undefined
[key: string]: string | undefined;
}
export const programmingLanguages: languageMap = {
@@ -45,52 +45,52 @@ export const programmingLanguages: languageMap = {
html: ".html",
css: ".css",
// add more file extensions here, make sure the key is same as language prop in CodeBlock.tsx component
}
};
export const generateRandomString = (length: number, lowercase = false) => {
const chars = "ABCDEFGHJKLMNPQRSTUVWXY3456789" // excluding similar looking characters like Z, 2, I, 1, O, 0
let result = ""
const chars = "ABCDEFGHJKLMNPQRSTUVWXY3456789"; // excluding similar looking characters like Z, 2, I, 1, O, 0
let result = "";
for (let i = 0; i < length; i++) {
result += chars.charAt(Math.floor(Math.random() * chars.length))
result += chars.charAt(Math.floor(Math.random() * chars.length));
}
return lowercase ? result.toLowerCase() : result
}
return lowercase ? result.toLowerCase() : result;
};
const CodeBlock: FC<Props> = memo(({ language, value }) => {
const { isCopied, copyToClipboard } = useCopyToClipboard({ timeout: 2000 })
const { isCopied, copyToClipboard } = useCopyToClipboard({ timeout: 2000 });
const downloadAsFile = () => {
if (typeof window === "undefined") {
return
return;
}
const fileExtension = programmingLanguages[language] || ".file"
const fileExtension = programmingLanguages[language] || ".file";
const suggestedFileName = `file-${generateRandomString(
3,
true
)}${fileExtension}`
const fileName = window.prompt("Enter file name" || "", suggestedFileName)
true,
)}${fileExtension}`;
const fileName = window.prompt("Enter file name" || "", suggestedFileName);
if (!fileName) {
// User pressed cancel on prompt.
return
return;
}
const blob = new Blob([value], { type: "text/plain" })
const url = URL.createObjectURL(blob)
const link = document.createElement("a")
link.download = fileName
link.href = url
link.style.display = "none"
document.body.appendChild(link)
link.click()
document.body.removeChild(link)
URL.revokeObjectURL(url)
}
const blob = new Blob([value], { type: "text/plain" });
const url = URL.createObjectURL(blob);
const link = document.createElement("a");
link.download = fileName;
link.href = url;
link.style.display = "none";
document.body.appendChild(link);
link.click();
document.body.removeChild(link);
URL.revokeObjectURL(url);
};
const onCopy = () => {
if (isCopied) return
copyToClipboard(value)
}
if (isCopied) return;
copyToClipboard(value);
};
return (
<div className="codeblock relative w-full bg-zinc-950 font-sans">
@@ -132,8 +132,8 @@ const CodeBlock: FC<Props> = memo(({ language, value }) => {
{value}
</SyntaxHighlighter>
</div>
)
})
CodeBlock.displayName = "CodeBlock"
);
});
CodeBlock.displayName = "CodeBlock";
export { CodeBlock }
export { CodeBlock };
@@ -2,4 +2,4 @@ import ChatInput from "./chat-input";
import ChatMessages from "./chat-messages";
export { type ChatHandler, type Message } from "./chat.interface";
export { ChatMessages, ChatInput };
export { ChatInput, ChatMessages };
@@ -1,16 +1,16 @@
import { FC, memo } from "react"
import ReactMarkdown, { Options } from "react-markdown"
import remarkGfm from "remark-gfm"
import remarkMath from "remark-math"
import { FC, memo } from "react";
import ReactMarkdown, { Options } from "react-markdown";
import remarkGfm from "remark-gfm";
import remarkMath from "remark-math";
import { CodeBlock } from "./codeblock"
import { CodeBlock } from "./codeblock";
const MemoizedReactMarkdown: FC<Options> = memo(
ReactMarkdown,
(prevProps, nextProps) =>
prevProps.children === nextProps.children &&
prevProps.className === nextProps.className
)
prevProps.className === nextProps.className,
);
export default function Markdown({ content }: { content: string }) {
return (
@@ -19,27 +19,27 @@ export default function Markdown({ content }: { content: string }) {
remarkPlugins={[remarkGfm, remarkMath]}
components={{
p({ children }) {
return <p className="mb-2 last:mb-0">{children}</p>
return <p className="mb-2 last:mb-0">{children}</p>;
},
code({ node, inline, className, children, ...props }) {
if (children.length) {
if (children[0] == "▍") {
return (
<span className="mt-1 animate-pulse cursor-default"></span>
)
);
}
children[0] = (children[0] as string).replace("`▍`", "▍")
children[0] = (children[0] as string).replace("`▍`", "▍");
}
const match = /language-(\w+)/.exec(className || "")
const match = /language-(\w+)/.exec(className || "");
if (inline) {
return (
<code className={className} {...props}>
{children}
</code>
)
);
}
return (
@@ -49,11 +49,11 @@ export default function Markdown({ content }: { content: string }) {
value={String(children).replace(/\n$/, "")}
{...props}
/>
)
);
},
}}
>
{content}
</MemoizedReactMarkdown>
)
);
}
@@ -1,33 +1,33 @@
'use client'
"use client";
import * as React from 'react'
import * as React from "react";
export interface useCopyToClipboardProps {
timeout?: number
timeout?: number;
}
export function useCopyToClipboard({
timeout = 2000
timeout = 2000,
}: useCopyToClipboardProps) {
const [isCopied, setIsCopied] = React.useState<Boolean>(false)
const [isCopied, setIsCopied] = React.useState<Boolean>(false);
const copyToClipboard = (value: string) => {
if (typeof window === 'undefined' || !navigator.clipboard?.writeText) {
return
if (typeof window === "undefined" || !navigator.clipboard?.writeText) {
return;
}
if (!value) {
return
return;
}
navigator.clipboard.writeText(value).then(() => {
setIsCopied(true)
setIsCopied(true);
setTimeout(() => {
setIsCopied(false)
}, timeout)
})
}
setIsCopied(false);
}, timeout);
});
};
return { isCopied, copyToClipboard }
return { isCopied, copyToClipboard };
}
@@ -3,4 +3,4 @@ import ChatMessages from "./chat-messages";
export type { ChatInputProps } from "./chat-input";
export type { Message } from "./chat-messages";
export { ChatMessages, ChatInput };
export { ChatInput, ChatMessages };
@@ -1,8 +1,8 @@
/** @type {import('next').NextConfig} */
const nextConfig = {
experimental: {
serverComponentsExternalPackages: ["llamaindex"],
},
}
serverComponentsExternalPackages: ["llamaindex"],
},
};
module.exports = nextConfig
module.exports = nextConfig;
@@ -3,4 +3,4 @@ module.exports = {
tailwindcss: {},
autoprefixer: {},
},
}
};
@@ -3,4 +3,4 @@ import ChatMessages from "./chat-messages";
export type { ChatInputProps } from "./chat-input";
export type { Message } from "./chat-messages";
export { ChatMessages, ChatInput };
export { ChatInput, ChatMessages };
@@ -1,8 +1,8 @@
/** @type {import('next').NextConfig} */
const nextConfig = {
experimental: {
serverComponentsExternalPackages: ["llamaindex"],
},
}
serverComponentsExternalPackages: ["llamaindex"],
},
};
module.exports = nextConfig
module.exports = nextConfig;
@@ -3,4 +3,4 @@ module.exports = {
tailwindcss: {},
autoprefixer: {},
},
}
};
+714 -518
View File
File diff suppressed because it is too large Load Diff