usePipecatConversation
Hook that derives a clean, ordered conversation stream from RTVI events.
Overview
usePipecatConversation
provides access to conversation state managed by the ConversationProvider
. The provider is automatically included when using PipecatAppBase
and handles all Pipecat RTVI events to produce a clean message list suitable for rendering a chat transcript. It handles streaming text, placeholder messages, finalization, and merging of consecutive messages from the same role.
Setup
The ConversationProvider
is automatically included when you use PipecatAppBase
, so no additional setup is required:
import { PipecatAppBase, usePipecatConversation } from "@pipecat-ai/voice-ui-kit";
export default function App() {
return (
<PipecatAppBase
transportType="smallwebrtc"
connectParams={{ webrtcUrl: "/api/offer" }}
>
<YourApp />
</PipecatAppBase>
);
}
Usage
Basic
import { usePipecatConversation } from "@pipecat-ai/voice-ui-kit";
export function ConversationList() {
const { messages } = usePipecatConversation();
return (
<ul>
{messages.map((m, i) => (
<li key={i}>
<strong>{m.role}:</strong> {typeof m.content === "string" ? m.content : "[component]"}
</li>
))}
</ul>
);
}
With callback
const { messages } = usePipecatConversation({
onMessageAdded: (message) => console.log("New message:", message),
});
Full example
import React, { useEffect, useRef } from "react";
import { usePipecatConversation } from "@pipecat-ai/voice-ui-kit";
export function ConversationExample() {
const { messages } = usePipecatConversation();
const endRef = useRef<HTMLDivElement>(null);
useEffect(() => {
endRef.current?.scrollIntoView({ behavior: "smooth" });
}, [messages]);
return (
<div style={{ height: 300, overflow: "auto", fontFamily: "monospace", fontSize: 12 }}>
{messages.map((m, i) => (
<div key={i}>
<strong>[{m.role}]</strong> {typeof m.content === "string" ? m.content : "[component]"}
<span style={{ opacity: 0.6, marginLeft: 8 }}>
{new Date(m.createdAt).toLocaleTimeString()}
</span>
</div>
))}
<div ref={endRef} />
</div>
);
}
Injecting messages
You can inject messages directly via the hook, or by using ConsoleTemplate
callbacks.
import React from "react";
import { usePipecatConversation } from "@pipecat-ai/voice-ui-kit";
export function InjectViaHook() {
const { injectMessage } = usePipecatConversation();
return (
<button
onClick={() =>
injectMessage({ role: "system", content: "Hello from the system" })
}
>
Inject message
</button>
);
}