Skip to content

Commit 7575a1c

Browse files
committed
Merge branch 'develop' into pr-1955
2 parents 2d2aa0a + 8f05667 commit 7575a1c

File tree

88 files changed

+5531
-477
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

88 files changed

+5531
-477
lines changed

.env.example

+12
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@
22
CACHE_STORE=database # Defaults to database. Other available cache store: redis and filesystem
33
REDIS_URL= # Redis URL - could be a local redis instance or cloud hosted redis. Also support rediss:// urls
44

5+
PGLITE_DATA_DIR= #../pgLite/ if selecting a directory --- or memory:// if selecting in memory
6+
57
# Discord Configuration
68
DISCORD_APPLICATION_ID=
79
DISCORD_API_TOKEN= # Bot token
@@ -298,6 +300,10 @@ MEDIUM_VENICE_MODEL= # Default: llama-3.3-70b
298300
LARGE_VENICE_MODEL= # Default: llama-3.1-405b
299301
IMAGE_VENICE_MODEL= # Default: fluently-xl
300302

303+
# Coin Price Configuration
304+
COINMARKETCAP_API_KEY=
305+
COINGECKO_API_KEY=
306+
301307
# Akash Chat API Configuration docs: https://chatapi.akash.network/documentation
302308
AKASH_CHAT_API_KEY= # Get from https://chatapi.akash.network/
303309
SMALL_AKASH_CHAT_API_MODEL= # Default: Meta-Llama-3-2-3B-Instruct
@@ -401,6 +407,12 @@ FUEL_WALLET_PRIVATE_KEY=
401407
TOKENIZER_MODEL= # Specify the tokenizer model to be used.
402408
TOKENIZER_TYPE= # Options: tiktoken (for OpenAI models) or auto (AutoTokenizer from Hugging Face for non-OpenAI models). Default: tiktoken.
403409

410+
411+
# Spheron
412+
SPHERON_PRIVATE_KEY=
413+
SPHERON_PROVIDER_PROXY_URL=
414+
SPHERON_WALLET_ADDRESS=
415+
404416
# Stargaze NFT marketplace from Cosmos (You can use https://graphql.mainnet.stargaze-apis.com/graphql)
405417
STARGAZE_ENDPOINT=
406418

.gitignore

+1
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ packages/plugin-buttplug/intiface-engine
1515
dist/
1616
# Allow models directory but ignore model files
1717
models/*.gguf
18+
pgLite/
1819

1920
cookies.json
2021

agent/package.json

+2
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
"@elizaos/adapter-postgres": "workspace:*",
2222
"@elizaos/adapter-redis": "workspace:*",
2323
"@elizaos/adapter-sqlite": "workspace:*",
24+
"@elizaos/adapter-pglite": "workspace:*",
2425
"@elizaos/client-auto": "workspace:*",
2526
"@elizaos/client-direct": "workspace:*",
2627
"@elizaos/client-discord": "workspace:*",
@@ -39,6 +40,7 @@
3940
"@ai16z/plugin-cosmos": "workspace:*",
4041
"@elizaos/plugin-intiface": "workspace:*",
4142
"@elizaos/plugin-coinbase": "workspace:*",
43+
"@elizaos/plugin-coinprice": "workspace:*",
4244
"@elizaos/plugin-conflux": "workspace:*",
4345
"@elizaos/plugin-evm": "workspace:*",
4446
"@elizaos/plugin-echochambers": "workspace:*",

agent/src/index.ts

+13-8
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
import { PostgresDatabaseAdapter } from "@elizaos/adapter-postgres";
22
import { RedisClient } from "@elizaos/adapter-redis";
33
import { SqliteDatabaseAdapter } from "@elizaos/adapter-sqlite";
4+
import { PGLiteDatabaseAdapter } from "@elizaos/adapter-pglite";
45
import { AutoClientInterface } from "@elizaos/client-auto";
56
import { DiscordClientInterface } from "@elizaos/client-discord";
67
import { FarcasterAgentClient } from "@elizaos/client-farcaster";
@@ -48,6 +49,7 @@ import {
4849
tradePlugin,
4950
webhookPlugin,
5051
} from "@elizaos/plugin-coinbase";
52+
import { coinPricePlugin } from "@elizaos/plugin-coinprice";
5153
import { confluxPlugin } from "@elizaos/plugin-conflux";
5254
import { cronosZkEVMPlugin } from "@elizaos/plugin-cronoszkevm";
5355
import { echoChambersPlugin } from "@elizaos/plugin-echochambers";
@@ -373,7 +375,7 @@ export function getTokenForProvider(
373375
}
374376
}
375377

376-
function initializeDatabase(dataDir: string) {
378+
async function initializeDatabase(dataDir: string) {
377379
if (process.env.POSTGRES_URL) {
378380
elizaLogger.info("Initializing PostgreSQL connection...");
379381
const db = new PostgresDatabaseAdapter({
@@ -392,6 +394,13 @@ function initializeDatabase(dataDir: string) {
392394
elizaLogger.error("Failed to connect to PostgreSQL:", error);
393395
});
394396

397+
return db;
398+
} else if (process.env.PGLITE_DATA_DIR) {
399+
elizaLogger.info("Initializing PgLite adapter...");
400+
// `dataDir: memory://` for in memory pg
401+
const db = new PGLiteDatabaseAdapter({
402+
dataDir: process.env.PGLITE_DATA_DIR,
403+
});
395404
return db;
396405
} else {
397406
const filePath =
@@ -506,11 +515,7 @@ export async function createAgent(
506515
cache: ICacheManager,
507516
token: string
508517
): Promise<AgentRuntime> {
509-
elizaLogger.success(
510-
elizaLogger.successesTitle,
511-
"Creating runtime for character",
512-
character.name
513-
);
518+
elizaLogger.log(`Creating runtime for character ${character.name}`);
514519

515520
nodePlugin ??= createNodePlugin();
516521

@@ -562,6 +567,7 @@ export async function createAgent(
562567
? confluxPlugin
563568
: null,
564569
nodePlugin,
570+
coinPricePlugin,
565571
getSecret(character, "TAVILY_API_KEY") ? webSearchPlugin : null,
566572
getSecret(character, "SOLANA_PUBLIC_KEY") ||
567573
(getSecret(character, "WALLET_PUBLIC_KEY") &&
@@ -759,10 +765,9 @@ async function startAgent(
759765
fs.mkdirSync(dataDir, { recursive: true });
760766
}
761767

762-
db = initializeDatabase(dataDir) as IDatabaseAdapter &
768+
db = await initializeDatabase(dataDir) as IDatabaseAdapter &
763769
IDatabaseCacheAdapter;
764770

765-
await db.init();
766771

767772
const cache = initializeCache(
768773
process.env.CACHE_STORE ?? CacheStore.DATABASE,

docs/docs/packages/adapters.md

+36
Original file line numberDiff line numberDiff line change
@@ -78,10 +78,17 @@ classDiagram
7878
+inMemoryOperations()
7979
}
8080
81+
class PGLiteDatabaseAdapter {
82+
-db: PGlite
83+
+searchMemoriesByEmbedding()
84+
+createMemory()
85+
}
86+
8187
DatabaseAdapter <|-- PostgresDatabaseAdapter
8288
DatabaseAdapter <|-- SqliteDatabaseAdapter
8389
DatabaseAdapter <|-- SupabaseDatabaseAdapter
8490
DatabaseAdapter <|-- SqlJsDatabaseAdapter
91+
DatabaseAdapter <|-- PgLiteDatabaseAdapter
8592
8693
class AgentRuntime {
8794
-databaseAdapter: DatabaseAdapter
@@ -149,6 +156,9 @@ pnpm add @elizaos/adapter-sqljs sql.js
149156

150157
# Supabase
151158
pnpm add @elizaos/adapter-supabase @supabase/supabase-js
159+
160+
# PgLite
161+
pnpm add @elizaos/adapter-pglite @electric-sql/pglite
152162
```
153163

154164
---
@@ -198,6 +208,32 @@ const db = new SupabaseDatabaseAdapter(
198208
);
199209
```
200210

211+
```typescript
212+
import { SqliteDatabaseAdapter } from "@elizaos/adapter-sqlite";
213+
import Database from "better-sqlite3";
214+
215+
const db = new SqliteDatabaseAdapter(
216+
new Database("./db.sqlite", {
217+
// SQLite options
218+
memory: false,
219+
readonly: false,
220+
fileMustExist: false,
221+
}),
222+
);
223+
```
224+
225+
### PgLite Setup
226+
227+
```typescript
228+
import { PGLiteDatabaseAdapter } from "@elizaos/adapter-pglite";
229+
230+
const db = new PGLiteDatabaseAdapter(
231+
new PGLite({
232+
dataDir: "./db"
233+
})
234+
);
235+
```
236+
201237
---
202238

203239
## Core Features

packages/adapter-pglite/.npmignore

+6
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
*
2+
3+
!dist/**
4+
!package.json
5+
!readme.md
6+
!tsup.config.ts
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
import eslintGlobalConfig from "../../eslint.config.mjs";
2+
3+
export default [...eslintGlobalConfig];

packages/adapter-pglite/package.json

+36
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
{
2+
"name": "@elizaos/adapter-pglite",
3+
"version": "0.1.7-alpha.2",
4+
"type": "module",
5+
"main": "dist/index.js",
6+
"module": "dist/index.js",
7+
"types": "dist/index.d.ts",
8+
"exports": {
9+
"./package.json": "./package.json",
10+
".": {
11+
"import": {
12+
"@elizaos/source": "./src/index.ts",
13+
"types": "./dist/index.d.ts",
14+
"default": "./dist/index.js"
15+
}
16+
}
17+
},
18+
"files": [
19+
"dist"
20+
],
21+
"dependencies": {
22+
"@electric-sql/pglite": "^0.2.15",
23+
"@elizaos/core": "workspace:*"
24+
},
25+
"devDependencies": {
26+
"tsup": "8.3.5"
27+
},
28+
"scripts": {
29+
"build": "tsup --format esm --dts",
30+
"dev": "tsup --format esm --dts --watch",
31+
"lint": "eslint --fix --cache ."
32+
},
33+
"peerDependencies": {
34+
"whatwg-url": "7.1.0"
35+
}
36+
}

packages/adapter-pglite/schema.sql

+140
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,140 @@
1+
-- Enable pgvector extension
2+
3+
-- -- Drop existing tables and extensions
4+
-- DROP EXTENSION IF EXISTS vector CASCADE;
5+
-- DROP TABLE IF EXISTS relationships CASCADE;
6+
-- DROP TABLE IF EXISTS participants CASCADE;
7+
-- DROP TABLE IF EXISTS logs CASCADE;
8+
-- DROP TABLE IF EXISTS goals CASCADE;
9+
-- DROP TABLE IF EXISTS memories CASCADE;
10+
-- DROP TABLE IF EXISTS rooms CASCADE;
11+
-- DROP TABLE IF EXISTS accounts CASCADE;
12+
13+
14+
CREATE EXTENSION IF NOT EXISTS vector;
15+
CREATE EXTENSION IF NOT EXISTS fuzzystrmatch;
16+
17+
-- Create a function to determine vector dimension
18+
CREATE OR REPLACE FUNCTION get_embedding_dimension()
19+
RETURNS INTEGER AS $$
20+
BEGIN
21+
-- Check for OpenAI first
22+
IF current_setting('app.use_openai_embedding', TRUE) = 'true' THEN
23+
RETURN 1536; -- OpenAI dimension
24+
-- Then check for Ollama
25+
ELSIF current_setting('app.use_ollama_embedding', TRUE) = 'true' THEN
26+
RETURN 1024; -- Ollama mxbai-embed-large dimension
27+
-- Then check for GAIANET
28+
ELSIF current_setting('app.use_gaianet_embedding', TRUE) = 'true' THEN
29+
RETURN 768; -- Gaianet nomic-embed dimension
30+
ELSE
31+
RETURN 384; -- BGE/Other embedding dimension
32+
END IF;
33+
END;
34+
$$ LANGUAGE plpgsql;
35+
36+
BEGIN;
37+
38+
CREATE TABLE IF NOT EXISTS accounts (
39+
"id" UUID PRIMARY KEY,
40+
"createdAt" TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP,
41+
"name" TEXT,
42+
"username" TEXT,
43+
"email" TEXT NOT NULL,
44+
"avatarUrl" TEXT,
45+
"details" JSONB DEFAULT '{}'::jsonb
46+
);
47+
48+
CREATE TABLE IF NOT EXISTS rooms (
49+
"id" UUID PRIMARY KEY,
50+
"createdAt" TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP
51+
);
52+
53+
DO $$
54+
DECLARE
55+
vector_dim INTEGER;
56+
BEGIN
57+
vector_dim := get_embedding_dimension();
58+
59+
EXECUTE format('
60+
CREATE TABLE IF NOT EXISTS memories (
61+
"id" UUID PRIMARY KEY,
62+
"type" TEXT NOT NULL,
63+
"createdAt" TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP,
64+
"content" JSONB NOT NULL,
65+
"embedding" vector(%s),
66+
"userId" UUID REFERENCES accounts("id"),
67+
"agentId" UUID REFERENCES accounts("id"),
68+
"roomId" UUID REFERENCES rooms("id"),
69+
"unique" BOOLEAN DEFAULT true NOT NULL,
70+
CONSTRAINT fk_room FOREIGN KEY ("roomId") REFERENCES rooms("id") ON DELETE CASCADE,
71+
CONSTRAINT fk_user FOREIGN KEY ("userId") REFERENCES accounts("id") ON DELETE CASCADE,
72+
CONSTRAINT fk_agent FOREIGN KEY ("agentId") REFERENCES accounts("id") ON DELETE CASCADE
73+
)', vector_dim);
74+
END $$;
75+
76+
CREATE TABLE IF NOT EXISTS goals (
77+
"id" UUID PRIMARY KEY,
78+
"createdAt" TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP,
79+
"userId" UUID REFERENCES accounts("id"),
80+
"name" TEXT,
81+
"status" TEXT,
82+
"description" TEXT,
83+
"roomId" UUID REFERENCES rooms("id"),
84+
"objectives" JSONB DEFAULT '[]'::jsonb NOT NULL,
85+
CONSTRAINT fk_room FOREIGN KEY ("roomId") REFERENCES rooms("id") ON DELETE CASCADE,
86+
CONSTRAINT fk_user FOREIGN KEY ("userId") REFERENCES accounts("id") ON DELETE CASCADE
87+
);
88+
89+
CREATE TABLE IF NOT EXISTS logs (
90+
"id" UUID PRIMARY KEY DEFAULT gen_random_uuid(),
91+
"createdAt" TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP,
92+
"userId" UUID NOT NULL REFERENCES accounts("id"),
93+
"body" JSONB NOT NULL,
94+
"type" TEXT NOT NULL,
95+
"roomId" UUID NOT NULL REFERENCES rooms("id"),
96+
CONSTRAINT fk_room FOREIGN KEY ("roomId") REFERENCES rooms("id") ON DELETE CASCADE,
97+
CONSTRAINT fk_user FOREIGN KEY ("userId") REFERENCES accounts("id") ON DELETE CASCADE
98+
);
99+
100+
CREATE TABLE IF NOT EXISTS participants (
101+
"id" UUID PRIMARY KEY,
102+
"createdAt" TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP,
103+
"userId" UUID REFERENCES accounts("id"),
104+
"roomId" UUID REFERENCES rooms("id"),
105+
"userState" TEXT,
106+
"last_message_read" TEXT,
107+
UNIQUE("userId", "roomId"),
108+
CONSTRAINT fk_room FOREIGN KEY ("roomId") REFERENCES rooms("id") ON DELETE CASCADE,
109+
CONSTRAINT fk_user FOREIGN KEY ("userId") REFERENCES accounts("id") ON DELETE CASCADE
110+
);
111+
112+
CREATE TABLE IF NOT EXISTS relationships (
113+
"id" UUID PRIMARY KEY,
114+
"createdAt" TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP,
115+
"userA" UUID NOT NULL REFERENCES accounts("id"),
116+
"userB" UUID NOT NULL REFERENCES accounts("id"),
117+
"status" TEXT,
118+
"userId" UUID NOT NULL REFERENCES accounts("id"),
119+
CONSTRAINT fk_user_a FOREIGN KEY ("userA") REFERENCES accounts("id") ON DELETE CASCADE,
120+
CONSTRAINT fk_user_b FOREIGN KEY ("userB") REFERENCES accounts("id") ON DELETE CASCADE,
121+
CONSTRAINT fk_user FOREIGN KEY ("userId") REFERENCES accounts("id") ON DELETE CASCADE
122+
);
123+
124+
CREATE TABLE IF NOT EXISTS cache (
125+
"key" TEXT NOT NULL,
126+
"agentId" TEXT NOT NULL,
127+
"value" JSONB DEFAULT '{}'::jsonb,
128+
"createdAt" TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
129+
"expiresAt" TIMESTAMP,
130+
PRIMARY KEY ("key", "agentId")
131+
);
132+
133+
-- Indexes
134+
CREATE INDEX IF NOT EXISTS idx_memories_embedding ON memories USING hnsw ("embedding" vector_cosine_ops);
135+
CREATE INDEX IF NOT EXISTS idx_memories_type_room ON memories("type", "roomId");
136+
CREATE INDEX IF NOT EXISTS idx_participants_user ON participants("userId");
137+
CREATE INDEX IF NOT EXISTS idx_participants_room ON participants("roomId");
138+
CREATE INDEX IF NOT EXISTS idx_relationships_users ON relationships("userA", "userB");
139+
140+
COMMIT;

0 commit comments

Comments
 (0)