streamchatblocks
v0.2.0
Published
A React component library for building AI chat interfaces with SSE streaming support and FastAPI compatibility
Maintainers
Readme
StreamChatBlocks
A React component library for building AI chat interfaces with Server-Sent Events (SSE) streaming support and FastAPI compatibility.
Features
- SSE Streaming: Real-time streaming responses from your backend
- FastAPI Ready: Designed to work seamlessly with FastAPI backends - no separate frontend server needed!
- Extensible: Easy-to-use plugin system for custom block types
- Community Components: Share and use community-contributed components
- TypeScript: Full TypeScript support with comprehensive type definitions
- Storybook: Interactive component documentation and development
- Customizable: Themeable components with sensible defaults
- Production Ready: Built for production use with modern tooling
Installation
npm install streamchatblocksQuick Start
Option 1: FastAPI with Integrated UI (Recommended)
No separate frontend server needed! FastAPI serves both the UI and API.
Using Make (easiest):
make setup-example && make run-exampleOr manually:
npm install
npm run build
./examples/fastapi-backend/setup.sh
cd examples/fastapi-backend
uv run uvicorn main:app --reloadThen open http://localhost:8000 - Done!
See the FastAPI example for complete setup.
Option 2: As a React Component
Use StreamChatBlocks in your existing React app:
import { ChatWindow } from 'streamchatblocks';
import 'streamchatblocks/dist/style.css';
function App() {
return (
<ChatWindow
config={{
apiConfig: {
baseUrl: 'http://localhost:8000',
},
}}
title="AI Assistant"
/>
);
}
export default App;FastAPI Backend (for both options)
from fastapi import FastAPI
from fastapi.responses import StreamingResponse
import json
app = FastAPI()
async def generate_response(message: str):
# Stream tokens
for char in "Hello! How can I help you?":
yield f"data: {json.dumps({'type': 'token', 'content': char})}\n\n"
# Send completion
yield f"data: {json.dumps({'type': 'done'})}\n\n"
@app.post("/stream")
async def stream_chat(request: dict):
return StreamingResponse(
generate_response(request["message"]),
media_type="text/event-stream"
)See the FastAPI example for a complete implementation.
Core Components
ChatWindow
The main chat interface component.
<ChatWindow
config={{
apiConfig: {
baseUrl: 'http://localhost:8000',
streamEndpoint: '/stream',
feedbackEndpoint: '/feedback',
},
theme: {
primaryColor: '#007bff',
backgroundColor: '#ffffff',
},
features: {
feedback: true,
markdown: true,
},
}}
title="Chat"
initialMessages={[]}
onMessageSent={(msg) => console.log('Sent:', msg)}
onError={(err) => console.error('Error:', err)}
/>Built-in Block Types
StreamChatBlocks includes several built-in block types:
DrugBlock
Display medication information with dosage, warnings, and interactions.
{
"type": "block",
"block": {
"type": "drug",
"data": {
"name": "Aspirin",
"dosage": "325-650 mg every 4-6 hours",
"warnings": ["May cause stomach bleeding"],
"interactions": ["Blood thinners"]
}
}
}FeedbackBlock
Collect user feedback with predefined options or custom input.
{
"type": "block",
"block": {
"type": "feedback",
"data": {
"question": "Was this helpful?",
"options": ["Yes", "No"],
"allowCustom": true
}
}
}TextBlock
Display formatted text content.
{
"type": "block",
"block": {
"type": "text",
"data": {
"content": "Additional information here"
}
}
}Community Components
Extend StreamChatBlocks with custom components for your use case.
Using Community Components
import { ChatWindow, TableBlock, ChartBlock } from 'streamchatblocks';
const customRenderers = new Map();
customRenderers.set('TableBlock', (block) => (
<TableBlock block={block} />
));
customRenderers.set('ChartBlock', (block) => (
<ChartBlock block={block} />
));
function App() {
return (
<ChatWindow
config={{
apiConfig: { baseUrl: 'http://localhost:8000' },
customRenderers,
}}
/>
);
}Creating Custom Components
import React from 'react';
import { CommunityComponentProps } from 'streamchatblocks';
export const MyCustomBlock: React.FC<CommunityComponentProps> = ({ block, onAction }) => {
return (
<div style={{ border: '1px solid #ddd', padding: '12px' }}>
<h4>{block.data.title}</h4>
<p>{block.data.description}</p>
<button onClick={() => onAction?.('click', { id: block.data.id })}>
Action
</button>
</div>
);
};See CONTRIBUTING.md for detailed guidelines on creating community components.
API Configuration
Default Endpoints
{
chatEndpoint: '/chat', // POST endpoint for sending messages
streamEndpoint: '/stream', // POST endpoint for SSE streaming
feedbackEndpoint: '/feedback', // POST endpoint for feedback
}Custom Configuration
<ChatWindow
config={{
apiConfig: {
baseUrl: 'https://api.example.com',
chatEndpoint: '/api/chat',
streamEndpoint: '/api/stream',
feedbackEndpoint: '/api/feedback',
headers: {
'Authorization': 'Bearer token',
},
},
}}
/>SSE Event Format
Your backend should send events in this format:
Token Event (Streaming Text)
{
"type": "token",
"content": "word or character"
}Block Event (Structured Data)
{
"type": "block",
"block": {
"type": "drug",
"data": { ... }
}
}Done Event (Completion)
{
"type": "done"
}Error Event
{
"type": "error",
"error": "Error message"
}Theming
Customize the appearance of your chat interface:
<ChatWindow
config={{
apiConfig: { baseUrl: 'http://localhost:8000' },
theme: {
primaryColor: '#28a745',
backgroundColor: '#f8f9fa',
messageBackgroundColor: '#e9ecef',
fontFamily: 'Arial, sans-serif',
},
}}
/>Development
Quick Commands with Make
make help # Show all available commands
make install # Install npm dependencies
make build # Build the library
make storybook # Run Storybook (interactive docs)
make lint # Run ESLint
make clean # Clean build artifacts
# FastAPI Example
make setup-example # Build library and setup example
make run-example # Run FastAPI serverOr use npm directly
npm install # Install dependencies
npm run build # Build library
npm run storybook # Run Storybook
npm run lint # Lint codeProject Structure
streamchatblocks/
├── src/
│ ├── components/ # Core components
│ ├── community/ # Community components
│ ├── hooks/ # React hooks
│ ├── utils/ # Utilities
│ ├── types/ # TypeScript types
│ └── config/ # Default configs
├── examples/ # Usage examples
└── dist/ # Build outputExamples
Check out the examples directory for complete implementations:
- FastAPI Backend - Complete FastAPI integration with SSE
Publishing to npm
Once you're ready to publish:
- Update version in
package.json - Build the library:
npm run build - Login to npm:
npm login - Publish:
npm publish
For local development in another project:
# In streamchatblocks directory
npm link
# In your project directory
npm link streamchatblocksTypeScript Support
StreamChatBlocks is written in TypeScript and includes comprehensive type definitions.
import type { ChatConfig, Message, ResponseBlock } from 'streamchatblocks';
const config: ChatConfig = {
apiConfig: {
baseUrl: 'http://localhost:8000',
},
};
const message: Message = {
id: '1',
role: 'user',
content: 'Hello',
timestamp: new Date(),
};Contributing
We welcome contributions! Please see CONTRIBUTING.md for guidelines.
Ways to Contribute
- Add Community Components: Share reusable components
- Report Bugs: Open issues for bugs you find
- Suggest Features: Propose new features or improvements
- Improve Documentation: Help us improve our docs
- Write Tests: Help us increase test coverage
License
MIT
Support
- Documentation: Check this README and CONTRIBUTING.md
- Examples: See the examples directory
- Issues: GitHub Issues
- Storybook: Run
npm run storybookfor interactive component docs
Roadmap
- [ ] Add more built-in block types (images, videos, code)
- [ ] Markdown support in messages
- [ ] Code syntax highlighting
- [ ] Message persistence
- [ ] File upload support
- [ ] Voice input support
- [ ] Multi-language support
- [ ] Accessibility improvements
- [ ] Unit and integration tests
Credits
Built with:
- React
- TypeScript
- Vite
- Storybook
Made for the community by developers who love clean, reusable components.
