@@ -24,29 +24,34 @@ example.
2424``` ts
2525import { paginationOptsValidator } from " convex/server" ;
2626import { v } from " convex/values" ;
27- import { listUIMessages } from " @convex-dev/agent" ;
27+ import { listMessages } from " @convex-dev/agent" ;
2828import { components } from " ./_generated/api" ;
2929
3030export const listThreadMessages = query ({
3131 args: { threadId: v .string (), paginationOpts: paginationOptsValidator },
3232 handler : async (ctx , args ) => {
3333 await authorizeThreadAccess (ctx , threadId );
3434
35- const paginated = await listUIMessages (ctx , components .agent , args );
35+ const paginated = await listMessages (ctx , components .agent , args );
3636
3737 // Here you could filter out / modify the documents
3838 return paginated ;
3939 },
4040});
4141```
4242
43- Note: Above we used ` listUIMessages ` , which returns UIMessages, specifically the
44- Agent extension that includes some extra fields like order, status, etc.
43+ Note: Above we used ` listMessages ` , which returns MessageDocs: one per stored
44+ message, with fields like order, stepOrder and status. The React hooks below
45+ take this query and assemble the documents into UIMessages on the client.
4546UIMessages combine multiple MessageDocs into a single UIMessage when there are
4647multiple tool calls followed by an assistant message, making it easy to build
4748UIs that work with the various "parts" on the UIMessage.
4849
49- If you want to get MessageDocs, you can use ` listMessages ` instead.
50+ If you need UIMessages on the server, ` listUIMessages ` converts each page
51+ separately. Returning those pages to ` useUIMessages ` is still supported but
52+ legacy: a page boundary can fall inside one UIMessage, and a tool approval
53+ response whose tool call is on another page is lost. Return MessageDocs from
54+ ` listMessages ` instead.
5055
5156## Showing messages in React
5257
@@ -56,8 +61,14 @@ non-streaming example.
5661
5762### ` useUIMessages ` hook
5863
59- The crux is to use the ` useUIMessages ` hook. For streaming, pass in
60- ` stream: true ` to the hook.
64+ The crux is to use the ` useUIMessages ` hook with the query above. For streaming,
65+ pass in ` stream: true ` to the hook.
66+
67+ Pagination can end a page partway through one UIMessage. The hook loads the
68+ rest of the oldest message before it settles (reporting ` LoadingMore ` ), so
69+ ` results ` always start at a whole message, and may hold more rows than
70+ ` initialNumItems ` . Rows of older messages read along the way are shown on the
71+ next ` loadMore ` .
6172
6273``` tsx
6374import { api } from " ../convex/_generated/api" ;
@@ -80,7 +91,7 @@ function MyComponent({ threadId }: { threadId: string }) {
8091```
8192
8293Note: If you want to work with MessageDocs instead of UIMessages, you can use
83- the older ` useThreadMessages ` hook instead . However, working with UIMessages
94+ the older ` useThreadMessages ` hook with the same query . However, working with UIMessages
8495enables richer streaming capabilities, such as status on whether the agent is
8596actively reasoning.
8697
0 commit comments