Testing
@threadplane/ag-ui gives you two test doubles, smallest scope first:
provideFakeAgent()โ a one-call fake backend that runs the real adapter pipeline and streams canned tokens. No server, no LLM.mockAgent()(from@threadplane/chat) โ a writable-signal mock for component/unit tests. The ag-ui agent is the neutralAgentcontract, so there is no ag-ui-specific mock โ use the neutral one directly.
See Choosing an adapter โ Testing for when to use each test double.
#Fake backend: provideFakeAgent()
provideFakeAgent({ tokens, reasoningTokens, delayMs }) wires a fake backend into Angular DI in one call. It exercises the real adapter pipeline โ injectAgent(), status transitions, message accumulation โ but the wire events are canned, so there's no server and no LLM. Use it for adapter-integration tests, in-browser demos, and offline development.
It drops in exactly where provideAgent() would go โ the call shape matches the LangGraph adapter:
The component is byte-identical to production โ only the provider changes. FakeAgentConfig ({ tokens?, reasoningTokens?, delayMs? }) lives in @threadplane/chat/testing:
| Option | Type | Notes |
|---|---|---|
tokens | string[] | Emitted as streamed text deltas, in order. |
reasoningTokens | string[] | Emitted before text deltas to exercise reasoning UI. |
delayMs | number | Delay between streamed events. |
For the underlying FakeAgent class and its canned event sequence, see Fake Agent.
#Contract mock: mockAgent()
For component and unit tests where you don't need a streaming pipeline at all, use the neutral mockAgent(initial) from @threadplane/chat. It returns an Agent whose state surface is exposed as writable signals โ set state directly and assert your component reacts. Nothing is real.
The ag-ui adapter exposes exactly the neutral Agent contract, so there is no ag-ui-specific mock โ mockAgent() is the right tool.