Skip to content

Commit 9002682

Browse files
committed
async listners
1 parent a16f3f7 commit 9002682

7 files changed

Lines changed: 121 additions & 95 deletions

File tree

src/client.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,8 @@ export type CreateClientOptions = {
1212
onError?: (error: Error) => void;
1313
};
1414

15+
export type Base44SDK = ReturnType<typeof createClient>;
16+
1517
/**
1618
* Create a Base44 client instance
1719
* @param {Object} config - Client configuration

src/index.ts

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { createClient, createClientFromRequest } from "./client.js";
1+
import { createClient, createClientFromRequest, Base44SDK } from "./client.js";
22
import { Base44Error } from "./utils/axios-client.js";
33
import {
44
getAccessToken,
@@ -16,3 +16,7 @@ export {
1616
removeAccessToken,
1717
getLoginUrl,
1818
};
19+
20+
export type { Base44SDK };
21+
22+
export * from "./types.js";

src/modules/agents.ts

Lines changed: 29 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
1-
import { RoomsSocket, RoomsSocketConfig } from "../utils/socket-utils.js";
2-
import { createAxiosClient } from "../utils/axios-client.js";
3-
import { AgentConversation, AgentMessage } from "./agents.types.js";
1+
import { RoomsSocket } from "../utils/socket-utils.js";
2+
import { AgentConversation, AgentMessage } from "./types.js";
43
import { AxiosInstance } from "axios";
4+
import { ModelFilterParams } from "../types.js";
55

66
export type AgentsModuleConfig = {
77
axios: AxiosInstance;
@@ -14,7 +14,6 @@ export function createAgentsModule({
1414
socket,
1515
appId,
1616
}: AgentsModuleConfig) {
17-
let currentConversation: any = null;
1817
const baseURL = `/apps/${appId}/agents`;
1918

2019
const getConversations = () => {
@@ -27,48 +26,50 @@ export function createAgentsModule({
2726
);
2827
};
2928

30-
const listConversations = (filterParams: any) => {
29+
const listConversations = (filterParams: ModelFilterParams) => {
3130
return axios.get<any, AgentConversation[]>(`${baseURL}/conversations`, {
3231
params: filterParams,
3332
});
3433
};
3534

36-
const createConversation = (conversation: any) => {
35+
const createConversation = (conversation: {
36+
agent_name: string;
37+
metadata?: Record<string, any>;
38+
}) => {
3739
return axios.post<any, AgentConversation>(
3840
`${baseURL}/conversations`,
3941
conversation
4042
);
4143
};
42-
43-
const addMessage = (conversation: any, message: any) => {
44-
// this whole trick with current conversation so that we can call the onUpdateModel with the latest messages
45-
let convLatestMessages = null;
46-
if (currentConversation && currentConversation.id === conversation.id) {
47-
convLatestMessages = currentConversation.messages;
48-
} else {
49-
currentConversation = conversation;
50-
convLatestMessages = conversation.messages;
51-
}
52-
conversation.messages = [...convLatestMessages, message];
53-
socket.handlers.update_model({
54-
room: `/agent-conversations/${conversation.id}`,
55-
data: JSON.stringify(conversation),
56-
});
44+
45+
const addMessage = async (
46+
conversation: AgentConversation,
47+
message: AgentMessage
48+
) => {
49+
const room = `/agent-conversations/${conversation.id}`;
50+
await socket.updateModel(
51+
room,
52+
{
53+
...conversation,
54+
messages: [...(conversation.messages || []), message],
55+
}
56+
);
5757
return axios.post<any, AgentMessage>(
5858
`${baseURL}/conversations/${conversation.id}/messages`,
5959
message
6060
);
6161
};
6262

63-
const subscribeToConversation = (conversationId: string, onUpdate: any) => {
64-
return socket.subscribeToRoom(`/agent-conversations/${conversationId}`, {
63+
const subscribeToConversation = (
64+
conversationId: string,
65+
onUpdate?: (conversation: AgentConversation) => void
66+
) => {
67+
const room = `/agent-conversations/${conversationId}`;
68+
return socket.subscribeToRoom(room, {
6569
connect: () => {},
6670
update_model: ({ data: jsonStr }) => {
67-
const data = JSON.parse(jsonStr) as {} & { id: string };
68-
if (currentConversation && currentConversation.id === data.id) {
69-
currentConversation = data;
70-
}
71-
onUpdate(data);
71+
const conv = JSON.parse(jsonStr) as AgentConversation;
72+
onUpdate?.(conv);
7273
},
7374
});
7475
};

src/modules/agents.types.ts

Lines changed: 0 additions & 48 deletions
This file was deleted.

src/modules/types.ts

Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
export type AgentConversation = {
2+
id: string;
3+
app_id: string;
4+
agent_name: string;
5+
created_by_id: string;
6+
messages: AgentMessage[];
7+
metadata?: Record<string, any>;
8+
};
9+
10+
export type AgentMessage = {
11+
id: string;
12+
role: "user" | "assistant" | "system";
13+
reasoning?: {
14+
start_date: string;
15+
end_date?: string;
16+
content: string;
17+
};
18+
content?: string | Record<string, any> | null;
19+
file_urls?: string[] | null;
20+
tool_calls?:
21+
| {
22+
id: string;
23+
name: string;
24+
arguments_string: string;
25+
status: "running" | "success" | "error" | "stopped";
26+
results?: string | null;
27+
}[]
28+
| null;
29+
30+
usage?: { prompt_tokens?: number; completion_tokens?: number } | null;
31+
hidden?: boolean;
32+
custom_context?:
33+
| { message: string; data: Record<string, any>; type: string }[]
34+
| null;
35+
model?: string | null;
36+
checkpoint_id?: string | null;
37+
metadata?: {
38+
created_date: string;
39+
created_by_email: string;
40+
created_by_full_name: string | null;
41+
};
42+
additional_message_params?: Record<string, any>;
43+
};

src/types.ts

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
export * from "./modules/types.js";
2+
3+
export type ModelFilterParams = {
4+
q?: Record<string, any>;
5+
sort?: string | null;
6+
sort_by?: string | null;
7+
limit?: number | null;
8+
skip?: number | null;
9+
fields?: string[] | null;
10+
};
11+
12+

src/utils/socket-utils.ts

Lines changed: 30 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -14,9 +14,12 @@ export type TJsonStr = string;
1414

1515
type RoomsSocketEventsMap = {
1616
listen: {
17-
connect: () => void;
18-
update_model: (msg: { room: string; data: TJsonStr }) => void;
19-
error: (error: Error) => void;
17+
connect: () => Promise<void> | void;
18+
update_model: (msg: {
19+
room: string;
20+
data: TJsonStr;
21+
}) => Promise<void> | void;
22+
error: (error: Error) => Promise<void> | void;
2023
};
2124
emit: {
2225
join: (room: string) => void;
@@ -26,9 +29,7 @@ type RoomsSocketEventsMap = {
2629

2730
type TEvent = keyof RoomsSocketEventsMap["listen"];
2831

29-
type THandler<E extends TEvent> = (
30-
...args: Parameters<RoomsSocketEventsMap["listen"][E]>
31-
) => void;
32+
type THandler<E extends TEvent> = RoomsSocketEventsMap["listen"][E];
3233

3334
function initializeSocket(
3435
config: RoomsSocketConfig,
@@ -68,6 +69,8 @@ function initializeSocket(
6869
return socket;
6970
}
7071

72+
export type RoomsSocket = ReturnType<typeof RoomsSocket>;
73+
7174
export function RoomsSocket({ config }: { config: RoomsSocketConfig }) {
7275
let currentConfig = { ...config };
7376
const roomsToListeners: Record<
@@ -76,24 +79,28 @@ export function RoomsSocket({ config }: { config: RoomsSocketConfig }) {
7679
> = {};
7780

7881
const handlers: { [k in TEvent]: THandler<k> } = {
79-
connect: () => {
82+
connect: async () => {
83+
const promises: Promise<void>[] = [];
8084
Object.keys(roomsToListeners).forEach((room) => {
8185
joinRoom(room);
82-
getListeners(room)?.forEach(({ connect: connectHandler }) => {
83-
connectHandler?.();
86+
const listeners = getListeners(room);
87+
listeners?.forEach(({ connect }) => {
88+
const promise = async () => connect?.();
89+
promises.push(promise());
8490
});
8591
});
92+
await Promise.all(promises);
8693
},
87-
update_model: (msg) => {
88-
if (roomsToListeners[msg.room]) {
89-
getListeners(msg.room)?.forEach(({ update_model }) => {
90-
update_model?.(msg);
91-
});
92-
}
94+
update_model: async (msg) => {
95+
const listeners = getListeners(msg.room);
96+
const promises = listeners.map((listener) =>
97+
listener.update_model?.(msg)
98+
);
99+
await Promise.all(promises);
93100
},
94-
error: (error) => {
101+
error: async (error) => {
95102
console.error("error", error);
96-
handlers.error?.(error);
103+
await handlers.error?.(error);
97104
},
98105
};
99106

@@ -126,6 +133,11 @@ export function RoomsSocket({ config }: { config: RoomsSocketConfig }) {
126133
socket.emit("leave", room);
127134
}
128135

136+
async function updateModel(room: string, data: any) {
137+
const dataStr = JSON.stringify(data);
138+
return handlers.update_model?.({ room, data: dataStr });
139+
}
140+
129141
function getListeners(room: string) {
130142
return roomsToListeners[room];
131143
}
@@ -152,7 +164,7 @@ export function RoomsSocket({ config }: { config: RoomsSocketConfig }) {
152164
socket,
153165
subscribeToRoom,
154166
updateConfig,
155-
handlers,
167+
updateModel,
156168
disconnect,
157169
};
158170
}

0 commit comments

Comments
 (0)