Skip to content

Commit

Permalink
bump: code interpreter v1 (#469)
Browse files Browse the repository at this point in the history
  • Loading branch information
thucpn authored Dec 26, 2024
1 parent a7a6592 commit fc5e56e
Show file tree
Hide file tree
Showing 11 changed files with 147 additions and 147 deletions.
5 changes: 5 additions & 0 deletions .changeset/stale-berries-hear.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"create-llama": patch
---

bump: code interpreter v1
4 changes: 2 additions & 2 deletions helpers/env-variables.ts
Original file line number Diff line number Diff line change
Expand Up @@ -470,11 +470,11 @@ const getSystemPromptEnv = (
});

const systemPrompt =
"'" +
'"' +
DEFAULT_SYSTEM_PROMPT +
(dataSources?.length ? `\n${DATA_SOURCES_PROMPT}` : "") +
(toolSystemPrompt ? `\n${toolSystemPrompt}` : "") +
"'";
'"';

systemPromptEnv.push({
name: "SYSTEM_PROMPT",
Expand Down
4 changes: 2 additions & 2 deletions helpers/tools.ts
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,7 @@ For better results, you can specify the region parameter to get results from a s
dependencies: [
{
name: "e2b_code_interpreter",
version: "0.0.11b38",
version: "1.0.3",
},
],
supportedFrameworks: ["fastapi", "express", "nextjs"],
Expand Down Expand Up @@ -155,7 +155,7 @@ For better results, you can specify the region parameter to get results from a s
dependencies: [
{
name: "e2b_code_interpreter",
version: "0.0.11b38",
version: "1.0.3",
},
],
supportedFrameworks: ["fastapi", "express", "nextjs"],
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
from typing import List, Optional

from app.services.file import DocumentFile, FileService
from e2b_code_interpreter import CodeInterpreter
from e2b_code_interpreter import Sandbox
from e2b_code_interpreter.models import Logs
from llama_index.core.tools import FunctionTool
from pydantic import BaseModel
Expand Down Expand Up @@ -61,7 +61,7 @@ def _init_interpreter(self, sandbox_files: List[str] = []):
Lazily initialize the interpreter.
"""
logger.info(f"Initializing interpreter with {len(sandbox_files)} files")
self.interpreter = CodeInterpreter(api_key=self.api_key)
self.interpreter = Sandbox(api_key=self.api_key)
if len(sandbox_files) > 0:
for file_path in sandbox_files:
file_name = os.path.basename(file_path)
Expand Down Expand Up @@ -159,11 +159,11 @@ def interpret(
if self.interpreter is None:
self._init_interpreter(sandbox_files)

if self.interpreter and self.interpreter.notebook:
if self.interpreter:
logger.info(
f"\n{'='*50}\n> Running following AI-generated code:\n{code}\n{'='*50}"
)
exec = self.interpreter.notebook.exec_cell(code)
exec = self.interpreter.run_code(code)

if exec.error:
error_message = f"The code failed to execute successfully. Error: {exec.error}. Try to fix the code and run again."
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -103,6 +103,7 @@ export class CodeGeneratorTool implements BaseTool<CodeGeneratorParameter> {
const artifact = await this.generateArtifact(
input.requirement,
input.oldCode,
input.sandboxFiles, // help the generated code use exact files
);
if (input.sandboxFiles) {
artifact.files = input.sandboxFiles;
Expand All @@ -117,10 +118,12 @@ export class CodeGeneratorTool implements BaseTool<CodeGeneratorParameter> {
async generateArtifact(
query: string,
oldCode?: string,
attachments?: string[],
): Promise<CodeArtifact> {
const userMessage = `
${query}
${oldCode ? `The existing code is: \n\`\`\`${oldCode}\`\`\`` : ""}
${attachments ? `The attachments are: \n${attachments.join("\n")}` : ""}
`;
const messages: ChatMessage[] = [
{ role: "system", content: CODE_GENERATION_PROMPT },
Expand Down
39 changes: 20 additions & 19 deletions templates/components/engines/typescript/agent/tools/interpreter.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { CodeInterpreter, Logs, Result } from "@e2b/code-interpreter";
import { Logs, Result, Sandbox } from "@e2b/code-interpreter";
import type { JSONSchemaType } from "ajv";
import fs from "fs";
import { BaseTool, ToolMetadata } from "llamaindex";
Expand Down Expand Up @@ -82,7 +82,7 @@ export class InterpreterTool implements BaseTool<InterpreterParameter> {
private apiKey?: string;
private fileServerURLPrefix?: string;
metadata: ToolMetadata<JSONSchemaType<InterpreterParameter>>;
codeInterpreter?: CodeInterpreter;
codeInterpreter?: Sandbox;

constructor(params?: InterpreterToolParams) {
this.metadata = params?.metadata || DEFAULT_META_DATA;
Expand All @@ -104,26 +104,27 @@ export class InterpreterTool implements BaseTool<InterpreterParameter> {

public async initInterpreter(input: InterpreterParameter) {
if (!this.codeInterpreter) {
this.codeInterpreter = await CodeInterpreter.create({
this.codeInterpreter = await Sandbox.create({
apiKey: this.apiKey,
});
}
// upload files to sandbox
if (input.sandboxFiles) {
console.log(`Uploading ${input.sandboxFiles.length} files to sandbox`);
try {
for (const filePath of input.sandboxFiles) {
const fileName = path.basename(filePath);
const localFilePath = path.join(this.uploadedFilesDir, fileName);
const content = fs.readFileSync(localFilePath);

const arrayBuffer = new Uint8Array(content).buffer;
await this.codeInterpreter?.files.write(filePath, arrayBuffer);
// upload files to sandbox when it's initialized
if (input.sandboxFiles) {
console.log(`Uploading ${input.sandboxFiles.length} files to sandbox`);
try {
for (const filePath of input.sandboxFiles) {
const fileName = path.basename(filePath);
const localFilePath = path.join(this.uploadedFilesDir, fileName);
const content = fs.readFileSync(localFilePath);

const arrayBuffer = new Uint8Array(content).buffer;
await this.codeInterpreter?.files.write(filePath, arrayBuffer);
}
} catch (error) {
console.error("Got error when uploading files to sandbox", error);
}
} catch (error) {
console.error("Got error when uploading files to sandbox", error);
}
}

return this.codeInterpreter;
}

Expand All @@ -150,7 +151,7 @@ export class InterpreterTool implements BaseTool<InterpreterParameter> {
`\n${"=".repeat(50)}\n> Running following AI-generated code:\n${input.code}\n${"=".repeat(50)}`,
);
const interpreter = await this.initInterpreter(input);
const exec = await interpreter.notebook.execCell(input.code);
const exec = await interpreter.runCode(input.code);
if (exec.error) console.error("[Code Interpreter error]", exec.error);
const extraResult = await this.getExtraResult(exec.results[0]);
const result: InterpreterToolOutput = {
Expand All @@ -169,7 +170,7 @@ export class InterpreterTool implements BaseTool<InterpreterParameter> {
}

async close() {
await this.codeInterpreter?.close();
await this.codeInterpreter?.kill();
}

private async getExtraResult(
Expand Down
53 changes: 25 additions & 28 deletions templates/components/routers/python/sandbox.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,11 +17,11 @@
import os
import uuid
from dataclasses import asdict
from typing import Any, Dict, List, Optional, Union
from typing import Any, Dict, List, Optional

from app.engine.tools.artifact import CodeArtifact
from app.services.file import FileService
from e2b_code_interpreter import CodeInterpreter, Sandbox # type: ignore
from e2b_code_interpreter import Sandbox # type: ignore
from fastapi import APIRouter, HTTPException, Request
from pydantic import BaseModel

Expand Down Expand Up @@ -60,6 +60,14 @@ class FileUpload(BaseModel):
name: str


SUPPORTED_TEMPLATES = [
"nextjs-developer",
"vue-developer",
"streamlit-developer",
"gradio-developer",
]


@sandbox_router.post("")
async def create_sandbox(request: Request):
request_data = await request.json()
Expand All @@ -79,33 +87,22 @@ async def create_sandbox(request: Request):
status_code=400, detail="Could not create artifact from the request data"
)

sbx = None

# Create an interpreter or a sandbox
if artifact.template == "code-interpreter-multilang":
sbx = CodeInterpreter(api_key=os.getenv("E2B_API_KEY"), timeout=SANDBOX_TIMEOUT)
logger.debug(f"Created code interpreter {sbx}")
else:
sbx = Sandbox(
api_key=os.getenv("E2B_API_KEY"),
template=artifact.template,
metadata={"template": artifact.template, "user_id": "default"},
timeout=SANDBOX_TIMEOUT,
)
logger.debug(f"Created sandbox {sbx}")
sbx = Sandbox(
api_key=os.getenv("E2B_API_KEY"),
template=(
None if artifact.template not in SUPPORTED_TEMPLATES else artifact.template
),
metadata={"template": artifact.template, "user_id": "default"},
timeout=SANDBOX_TIMEOUT,
)
logger.debug(f"Created sandbox {sbx}")

# Install packages
if artifact.has_additional_dependencies:
if isinstance(sbx, CodeInterpreter):
sbx.notebook.exec_cell(artifact.install_dependencies_command)
logger.debug(
f"Installed dependencies: {', '.join(artifact.additional_dependencies)} in code interpreter {sbx}"
)
elif isinstance(sbx, Sandbox):
sbx.commands.run(artifact.install_dependencies_command)
logger.debug(
f"Installed dependencies: {', '.join(artifact.additional_dependencies)} in sandbox {sbx}"
)
sbx.commands.run(artifact.install_dependencies_command)
logger.debug(
f"Installed dependencies: {', '.join(artifact.additional_dependencies)} in sandbox {sbx}"
)

# Copy files
if len(sandbox_files) > 0:
Expand All @@ -122,7 +119,7 @@ async def create_sandbox(request: Request):

# Execute code or return a URL to the running sandbox
if artifact.template == "code-interpreter-multilang":
result = sbx.notebook.exec_cell(artifact.code or "")
result = sbx.run_code(artifact.code or "")
output_urls = _download_cell_results(result.results)
runtime_error = asdict(result.error) if result.error else None
return ExecutionResult(
Expand All @@ -145,7 +142,7 @@ async def create_sandbox(request: Request):


def _upload_files(
sandbox: Union[CodeInterpreter, Sandbox],
sandbox: Sandbox,
sandbox_files: List[str] = [],
) -> None:
for file_path in sandbox_files:
Expand Down
2 changes: 1 addition & 1 deletion templates/types/streaming/express/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@
"llamaindex": "0.8.2",
"pdf2json": "3.0.5",
"ajv": "^8.12.0",
"@e2b/code-interpreter": "0.0.9-beta.3",
"@e2b/code-interpreter": "1.0.4",
"got": "^14.4.1",
"@apidevtools/swagger-parser": "^10.1.0",
"formdata-node": "^6.0.3",
Expand Down
Loading

0 comments on commit fc5e56e

Please sign in to comment.