Skip to content

Commit

Permalink
feat: basic working remix web app
Browse files Browse the repository at this point in the history
  • Loading branch information
robert-bo-davis committed Mar 12, 2024
1 parent fae7d4e commit 25dcc98
Show file tree
Hide file tree
Showing 39 changed files with 2,074 additions and 3,546 deletions.
41 changes: 40 additions & 1 deletion .eslintrc.cjs
Original file line number Diff line number Diff line change
Expand Up @@ -15,12 +15,40 @@ const config = {
'plugin:typescript-sort-keys/recommended',
],
ignorePatterns: [
'**/build/**',
'**/dist/**',
'**/coverage/**',
'node_modules/**',
'**/node_modules/**',
],
overrides: [
// React
{
extends: [
'plugin:react/recommended',
'plugin:react/jsx-runtime',
'plugin:react-hooks/recommended',
'plugin:jsx-a11y/recommended',
],
files: ['**/*.{js,jsx,ts,tsx}'],
plugins: ['react', 'jsx-a11y'],
settings: {
formComponents: ['Form'],
'import/resolver': {
typescript: {
project: './tsconfig.eslint.json',
},
},
linkComponents: [
{ linkAttribute: 'to', name: 'Link' },
{ linkAttribute: 'to', name: 'NavLink' },
],
react: {
version: 'detect',
},
},
},

{
env: {
node: true,
Expand All @@ -33,13 +61,18 @@ const config = {
],
parser: '@typescript-eslint/parser',
parserOptions: {
ecmaFeatures: {
jsx: true,
},
ecmaVersion: 'latest',
project: './tsconfig.eslint.json',
sourceType: 'module',
},
plugins: [
'@typescript-eslint',
'import',
'jsx-a11y',
'react',
'sonarjs',
'sort-destructure-keys',
'sort-keys-fix',
Expand All @@ -60,6 +93,8 @@ const config = {
'**/tests/**',
'**/*.test.{ts,tsx}',
'**/.eslintrc.cjs',
'**/vite.config.{js,ts}',
'**/tailwind.config.{js,ts}',
],
optionalDependencies: false,
packageDir: [
Expand All @@ -78,7 +113,11 @@ const config = {
settings: {
'import/resolver': {
typescript: {
project: ['cli/tsconfig.json', 'codellm/tsconfig.json'],
project: [
'cli/tsconfig.json',
'codellm/tsconfig.json',
'remix/tsconfig.json',
],
},
},
},
Expand Down
22 changes: 15 additions & 7 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -31,9 +31,7 @@ The system is composed of a few main components. It is designed to be extensible

The system currently supports [ollama](https://ollama.com/) and [openai](https://platform.openai.com/docs/quickstart?context=python) providers. You will need to have ollama running locally or configure an API key for openai.

## CLI Quickstart

The CLI is a simple way to interact with the system. It is
## Quickstart

### Setup

Expand Down Expand Up @@ -72,34 +70,44 @@ By default it will import ts code from this repository. You can change the `CODE
npm run start:import
```

### Ollama
### Run the cli agent

#### Ollama

This assumes you have ollama running locally on the default port.

```bash
npm start
```

### Anthropic (Claude)
#### Anthropic (Claude)

This assumes you have an API key for anthropic set as an environment variable: `ANTHROPIC_API_KEY`.

```bash
CODELLM_PROVIDER=anthropic npm start
```

### Mistral
#### Mistral

This assumes you have an API key for mistral set as an environment variable: `MISTRAL_API_KEY`.

```bash
CODELLM_PROVIDER=mistral npm start
```

### OpenAI
#### OpenAI

This assumes you have an API key for openai set as an environment variable: `OPENAI_API_KEY`.

```bash
CODELLM_PROVIDER=openai npm start
```

### Run the dev remix agent

The remix agent is a simple agent that takes a query and returns a remix of the query. It is a simple example of how to build a web based agent.

```bash
npm run dev
```
1 change: 0 additions & 1 deletion core/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@
},
"dependencies": {
"@langchain/core": "^0.1.40",
"crypto": "^1.0.1",
"globby": "^14.0.1",
"js-yaml": "^4.1.0",
"lodash": "^4.17.21",
Expand Down
14 changes: 13 additions & 1 deletion core/src/agent/chat.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import { getLlm } from '@/llm/index.js';
import { log } from '@/log/index.js';
import { newPrompt } from '@/prompt/index.js';
import { AGENT_RECURSION_DEPTH_MAX } from './constants.js';
import { addToHistory } from './history.js';
import * as agentTypes from './types.js';
import { handleToolResponse } from './handleToolResponse.js';

Expand Down Expand Up @@ -93,13 +94,19 @@ export const handleQuestionRecursive = async ({
}

if (agentTypes.isAgentResponseResponse(response)) {
addToHistory(response);
return response;
}

if (depth >= AGENT_RECURSION_DEPTH_MAX) {
return new CodeLlmError({
const e = new CodeLlmError({
code: 'agent:maxDepthExceeded',
});
addToHistory({
content: `error: ${e.message} - ${e.cause}`,
type: 'response',
});
return e;
}

const toolResponse = await handleToolResponse({
Expand Down Expand Up @@ -130,6 +137,11 @@ export const chat = async (question: string) => {
const agentLlm = getLlm('agent');
if (isError(agentLlm)) return agentLlm;

addToHistory({
content: question,
role: 'user',
});

return handleQuestionRecursive({
agentLlm,
question,
Expand Down
3 changes: 3 additions & 0 deletions core/src/agent/constants.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,7 @@
export const AGENT_ERRORS = {
'agent:addHistory': {
message: 'Error adding to agent history',
},
'agent:decodeResponse': {
message: 'Error decoding agent response',
},
Expand Down
31 changes: 31 additions & 0 deletions core/src/agent/history.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import type { AgentHistory, AgentHistoryAddParams } from '@/.';
import {
agentResponseResponseSchema,
isAgentHistoryUserItem,
} from '@/agent/types.js';
import { CodeLlmError } from '@/error/index.js';

const agentHistory: AgentHistory = [];

export const getHistory = () => agentHistory;

export const addToHistory = (params: AgentHistoryAddParams) => {
try {
const validAgentResponse = agentResponseResponseSchema.parse(params);
const { code, content, reason } = validAgentResponse;
return agentHistory.push({
code,
content,
reason,
role: 'assistant',
});
} catch (error) {
// ignore
}

if (!isAgentHistoryUserItem(params)) {
return new CodeLlmError({ code: 'agent:addHistory', meta: { params } });
}

return agentHistory.push(params);
};
2 changes: 2 additions & 0 deletions core/src/agent/newAgent.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import { log } from '@/log/index.js';
import { initPrompts } from '@/prompt/index.js';
import { initTools } from '@/tool/index.js';
import chat from './chat.js';
import { getHistory } from './history.js';

/**
* Create a new agent which is the primary interface to interact with the LLMs
Expand Down Expand Up @@ -43,6 +44,7 @@ export const newAgent = async (configParam: PartialConfig) => {

return {
chat,
getHistory: () => getHistory(),
} as Agent;
};

Expand Down
45 changes: 36 additions & 9 deletions core/src/agent/types.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import type { CodeLlmError, LlmClient } from '@/.';

import { z } from 'zod';

import { isError } from '@/error/index.js';
import { toolRunParamsParamSchema } from '@/tool/types.js';

export const agentResponseResponseSchema = z.object({
Expand All @@ -21,9 +21,9 @@ export const agentResponseResponseSchema = z.object({
export type AgentResponseResponse = z.infer<typeof agentResponseResponseSchema>;

export const isAgentResponseResponse = (
i: AgentSelectToolResponse,
i: AgentSelectToolResponse | CodeLlmError,
): i is AgentResponseResponse => {
return i.type === 'response';
return !isError(i) && i.type === 'response';
};

export const agentToolResponseSchema = z.object({
Expand All @@ -36,9 +36,9 @@ export const agentToolResponseSchema = z.object({
export type AgentToolResponse = z.infer<typeof agentToolResponseSchema>;

export const isAgentToolResponse = (
i: AgentSelectToolResponse,
i: AgentSelectToolResponse | CodeLlmError,
): i is AgentToolResponse => {
return i.type === 'tool';
return !isError(i) && i.type === 'tool';
};

export const agentLlmResponseSchema = z.union([
Expand All @@ -48,10 +48,6 @@ export const agentLlmResponseSchema = z.union([

export type AgentLlmResponse = z.infer<typeof agentLlmResponseSchema>;

export type Agent = {
chat: (message: string) => Promise<AgentResponse>;
};

export type AgentResponseCodeItem = {
code: string;
language: string;
Expand Down Expand Up @@ -82,3 +78,34 @@ export type AgentHandleToolResponseParams = {
response: AgentSelectToolResponse;
toolResponses: AgentToolResponses;
};

export type AgentHistoryUserItem = {
content: string;
role: 'user';
};

export type AgentHistoryAssistantItem = {
code: AgentResponseResponse['code'] | undefined;
content: AgentResponseResponse['content'];
reason: AgentToolResponse['reason'] | undefined;
role: 'assistant';
};

export type AgentHistoryItem = AgentHistoryUserItem | AgentHistoryAssistantItem;

export type AgentHistory = AgentHistoryItem[];

export type AgentHistoryAddParams =
| AgentResponseResponse
| AgentHistoryUserItem;

export const isAgentHistoryUserItem = (
i: AgentHistoryAddParams,
): i is AgentHistoryUserItem => {
return 'role' in i && i.role === 'user';
};

export type Agent = {
chat: (message: string) => Promise<AgentResponse>;
getHistory: () => AgentHistory;
};
3 changes: 2 additions & 1 deletion core/src/llm/conversation/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,8 @@ const conversationHistory: ConversationHistory = SERVICES.reduce(
{} as ConversationHistory,
);

export const getHistory = (service: Service) => conversationHistory[service];
export const getHistory = (service: Service) =>
conversationHistory[service] as MessageList;

export const addMessages = (service: Service, messages: MessageList) => {
conversationHistory[service] = [...conversationHistory[service], ...messages];
Expand Down
Loading

0 comments on commit 25dcc98

Please # to comment.