- API client with Clover REST API v3 integration (OAuth2 + API key auth) - 50+ comprehensive tools across 10 categories: * Orders: list, get, create, update, delete, add/remove line items, discounts, payments, fire order * Inventory: items, categories, modifiers, stock management * Customers: CRUD, search, addresses, payment cards * Employees: CRUD, roles, shifts, clock in/out * Payments: list, get, refunds * Merchants: settings, devices, tender types * Discounts: CRUD operations * Taxes: CRUD, tax rates * Reports: sales summary, revenue by item/category, employee performance * Cash: cash drawer tracking and events - 18 React MCP apps with full UI: * Order management: dashboard, detail, grid * Inventory: dashboard, detail, category manager * Customer: detail, grid * Employee: dashboard, schedule * Payment history * Analytics: sales dashboard, revenue by item, revenue by category * Configuration: discount manager, tax manager, device manager * Cash drawer - Complete TypeScript types for Clover API - Pagination support with automatic result fetching - Comprehensive error handling - Full README with examples and setup guide
89 lines
2.7 KiB
TypeScript
89 lines
2.7 KiB
TypeScript
import React, { useState, useEffect } from 'react';
|
|
import { Folder, Plus, Edit, Trash2 } from 'lucide-react';
|
|
|
|
export default function CategoryManager() {
|
|
const [categories, setCategories] = useState<any[]>([]);
|
|
const [loading, setLoading] = useState(true);
|
|
|
|
useEffect(() => {
|
|
fetchCategories();
|
|
}, []);
|
|
|
|
const fetchCategories = async () => {
|
|
setLoading(true);
|
|
try {
|
|
const result = await window.mcp.callTool('clover_list_categories', {
|
|
expand: 'items',
|
|
});
|
|
setCategories(result.categories || []);
|
|
} catch (error) {
|
|
console.error('Failed to fetch categories:', error);
|
|
} finally {
|
|
setLoading(false);
|
|
}
|
|
};
|
|
|
|
const createCategory = async () => {
|
|
const name = prompt('Category name:');
|
|
if (!name) return;
|
|
|
|
try {
|
|
await window.mcp.callTool('clover_create_category', { name });
|
|
fetchCategories();
|
|
} catch (error) {
|
|
alert('Failed to create category');
|
|
}
|
|
};
|
|
|
|
return (
|
|
<div className="p-6 bg-gray-50 min-h-screen">
|
|
<div className="flex justify-between items-center mb-6">
|
|
<h1 className="text-3xl font-bold text-gray-900">Category Manager</h1>
|
|
<button
|
|
onClick={createCategory}
|
|
className="px-4 py-2 bg-blue-600 text-white rounded-lg hover:bg-blue-700 flex items-center gap-2"
|
|
>
|
|
<Plus className="w-5 h-5" />
|
|
New Category
|
|
</button>
|
|
</div>
|
|
|
|
{loading ? (
|
|
<div className="text-center py-12 text-gray-500">
|
|
Loading categories...
|
|
</div>
|
|
) : (
|
|
<div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-6">
|
|
{categories.map((category) => (
|
|
<div key={category.id} className="bg-white rounded-lg shadow p-6">
|
|
<div className="flex items-start justify-between mb-4">
|
|
<div className="flex items-center gap-3">
|
|
<Folder className="w-8 h-8 text-blue-600" />
|
|
<div>
|
|
<h3 className="text-lg font-semibold text-gray-900">
|
|
{category.name}
|
|
</h3>
|
|
<p className="text-sm text-gray-600">
|
|
{category.items?.length || 0} items
|
|
</p>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<div className="flex gap-2">
|
|
<button
|
|
onClick={() => alert('Edit feature coming soon')}
|
|
className="flex-1 px-3 py-2 bg-blue-100 text-blue-700 rounded hover:bg-blue-200 flex items-center justify-center gap-2"
|
|
>
|
|
<Edit className="w-4 h-4" />
|
|
Edit
|
|
</button>
|
|
</div>
|
|
</div>
|
|
))}
|
|
</div>
|
|
)}
|
|
</div>
|
|
);
|
|
}
|