About Open Apps SDK
Open Apps SDK is an MCP server published by maneeshsandra in the Developer Tools category: build LLM-agnostic conversational apps with custom UI components and MCP servers.
The repository has 3 stars and 0 forks, with the last commit 12 months ago. Six months or more without a commit doesn't mean the server is broken, but check the open issues before depending on it in production.
Install
git clone https://github.com/maneeshsandra/open-apps-sdkThis server has no ConduID identity, so agent calls to it are not receipted. Pin the version you install and review the source before granting it credentials.
Ask AI
Ask AI about Open Apps SDK
Powered by Claude · Grounded in docs
Security checks
Static checks derived from the repository 6 days ago. Heuristics on the source, not an audit.
- ✓README presentThe repository ships documentation.
- ✓License declaredUsable under a stated license.
- ✓Tests presentA test suite exists in the repository.
- ✓Dependencies pinnedA lockfile pins dependency versions.
- ✓No dynamic code executionSource scan found no eval, dynamic Function, or shell execution.
- !Scoped permissionsDoesn't declare a permission scope. Assume it can do anything its process can.
README
Open Apps SDK

Build LLM-agnostic conversational apps with custom UI components and MCP (Model Context Protocol) servers.
🌟 Overview
The Open Apps SDK is a framework for building rich, interactive applications that work with any LLM (Claude, GPT, Gemini, etc.) while maintaining full control over your UI components and data.
Key Features
- ✅ LLM-Agnostic: Works with Claude, GPT, Gemini, or any other LLM
- ✅ Custom UI Components: Build and own your React components
- ✅ MCP Integration: Connect to multiple MCP servers
- ✅ Flexible Loading: Components via registry, URL, or bundled code
- ✅ Type-Safe: Full TypeScript support
- ✅ Bun-Powered: Fast builds and hot reloading
🚀 Quick Start
Setup
# Clone the repository
git clone https://github.com/maneeshsandra/open-apps-sdk.git
cd open-apps-sdk
# Run setup script (installs dependencies and configures environment)
bun run setup
# Start development server
bun run dev
Configuration
The application is configured through two main files:
.env- Environment variables for LLM provider, API keys, etc.mcp.config.json- MCP server configurations
Environment Variables (.env)
# LLM Configuration
LLM_PROVIDER=lmstudio # or openai, anthropic, etc.
LLM_API_KEY=your_api_key_here
LLM_BASE_URL=http://127.0.0.1:1234/v1 # For LM Studio
LLM_MODEL=qwen/qwen3-14b
LLM_MAX_TOKENS=4096
LLM_TEMPERATURE=0.7
# Server Configuration
PORT=3000
MCP Configuration (mcp.config.json)
{
"mcpServers": {
"weather-server": {
"command": "bun",
"args": ["examples/mcp-servers/weather-server.ts"],
"transport": "stdio"
},
"ecommerce-server": {
"command": "bun",
"args": ["examples/mcp-servers/ecommerce-server.ts"],
"transport": "stdio"
}
}
}
Component Configuration
Update components.config.js to register your custom components:
import { MyComponent } from './components/MyComponent';
export const components = {
'my-component': {
component: MyComponent,
tools: ['my_tool_name']
}
};
Create Your First Component
// components/MyComponent.tsx
import { useComponentContext, useCallTool, useToolOutput } from 'open-apps-sdk';
export function MyComponent() {
const { toolOutput, callTool, theme } = useComponentContext();
const output = useToolOutput(); // Alternative hook
const callToolFn = useCallTool(); // Alternative hook
const handleAction = async () => {
// Call MCP tool with authentication headers
await callTool('my_tool', {
param: 'value'
}, {
'Authorization': 'Bearer token',
'X-API-Key': 'api-key'
});
};
return (
<div className={`my-component ${theme}`}>
<h2>{toolOutput?.title || output?.title}</h2>
<button onClick={handleAction}>
Call Tool
</button>
</div>
);
}
Build an MCP Server
// examples/mcp-servers/my-server.ts
import { Server } from '@modelcontextprotocol/sdk/server/index.js';
import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
import { CallToolRequestSchema, ListToolsRequestSchema } from '@modelcontextprotocol/sdk/types.js';
const server = new Server({
name: 'my-server',
version: '1.0.0',
}, {
capabilities: { tools: {} }
});
// Define available tools
server.setRequestHandler(ListToolsRequestSchema, async () => {
return {
tools: [{
name: 'my_tool',
description: 'Description of what this tool does',
inputSchema: {
type: 'object',
properties: {
param: { type: 'string' }
},
required: ['param']
},
_meta: {
componentId: 'my-component', // Links to your React component
componentAccessible: true
}
}]
};
});
// Handle tool calls
server.setRequestHandler(CallToolRequestSchema, async (request) => {
const { name, arguments: args } = request.params;
if (name === 'my_tool') {
// Process the tool call
const result = { title: 'Tool Result', data: args };
return {
content: [{ type: 'text', text: 'Tool executed successfully' }],
structuredContent: result, // Passed to component via useToolOutput
_meta: {
componentId: 'my-component'
}
};
}
});
// Start the server
const transport = new StdioServerTransport();
server.connect(transport).catch(console.error);
🎯 Examples
E-commerce Store
A full-featured shopping experience with product browsing, cart management, and checkout.
# Start the e-commerce MCP server
bun run examples/mcp-servers/ecommerce-server.ts
Features:
- Product catalog with categories
- Shopping cart CRUD operations
- User authentication
- Order management
📸 Screenshots
Example 1: Component Registry

Example 2: E-commerce Store

🧩 Component Hooks
Our SDK provides powerful hooks for building interactive components. See detailed hooks documentation for comprehensive examples and best practices.
Core Hooks
// All-in-one context hook
const {
toolInput, // Arguments passed to the tool
toolOutput, // Structured data from tool responses
componentState, // Persistent component state
theme, // Current theme ('light' | 'dark')
displayMode, // Display mode ('inline' | 'modal' | etc.)
callTool, // Call MCP tools with optional auth headers
setComponentState, // Update persistent state
sendMessage, // Send followup messages to conversation
} = useComponentContext();
// Individual hooks for specific needs
const input = useToolInput(); // Get tool arguments
const output = useToolOutput(); // Get tool response data
const [state, setState] = useComponentState(); // Manage state
const theme = useTheme(); // Get current theme
const callTool = useCallTool(); // Call tools with auth
Authentication & Headers
Pass authentication headers when calling tools:
const callTool = useCallTool();
await callTool('authenticated_tool', {
param: 'value'
}, {
'Authorization': 'Bearer your-token',
'X-API-Key': 'your-api-key',
'Content-Type': 'application/json'
});
State Management
Components can maintain persistent state across interactions:
const [cartItems, setCartItems] = useComponentState([]);
const addToCart = (item) => {
setCartItems(prev => [...prev, item]);
};
🤝 Contributing
We welcome contributions! Please read our contributing guidelines before getting started.
Quick Start:
- Understand the project intent
- Create an issue first
- Create a feature branch
- Make your changes
- Submit a pull request
🐛 Known Issues
See TROUBLESHOOTING.md for common issues and solutions.
📄 License
MIT License - see LICENSE for details.
Built with ❤️ by the Open Apps SDK team
README fetched from the repository 6 days ago. The original is authoritative.