MCP Server
Click on "Install Server".
Wait a few minutes for the server to deploy. Once ready, it will show a "Started" state.
In the chat, type
@followed by the MCP server name and your instructions, e.g., "@MCP Serverget the latest 5 users with their order counts"
That's it! The server will respond to your query, and you can continue using it as needed.
Here is a step-by-step guide with screenshots.
MCP - Architecture Simple et Efficace
đŻ Vue d'ensemble
Architecture ultra-simple qui garde toute l'efficacité de votre stack :
Supabase + Redis centralisés dans le MCP Server
NestJS backend + Remix frontend utilisent uniquement l'API MCP
Shadcn UI + Zustand + TypeScript + Zod validation
Une seule rĂšgle : Tout passe par l'API MCP
đ Quick Start
# Installation
cd
npm run install:all
# Démarrage (avec Redis local)
npm run dev
# URLs
- Frontend: http://localhost:3000
- MCP Server: http://localhost:3001
- API Docs: http://localhost:3001/docs
- Backend: http://localhost:3002đ Structure
v2/
âââ mcp-server/ # Source unique (Fastify + Supabase + Redis)
âââ web/ # Remix + Shadcn UI + Zustand
âââ backend/ # NestJS (jobs, services, CRON)
âââ shared/ # Types auto-gĂ©nĂ©rĂ©s
âââ docker-compose.ymlđ§ Configuration
1. Variables d'environnement
# mcp-server/.env
PORT=3001
SUPABASE_URL=https://your-project.supabase.co
SUPABASE_KEY=your-anon-key
REDIS_URL=redis://localhost:63792. Base de données Supabase
Créez ces tables dans Supabase :
-- Users table
CREATE TABLE users (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
email TEXT UNIQUE NOT NULL,
name TEXT NOT NULL,
role TEXT DEFAULT 'user',
avatar_url TEXT,
created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);
-- Orders table
CREATE TABLE orders (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
user_id UUID REFERENCES users(id) ON DELETE CASCADE,
items JSONB NOT NULL,
total DECIMAL(10,2) NOT NULL,
status TEXT DEFAULT 'pending',
created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);đ» DĂ©veloppement
â Utilisation correcte (Frontend/Backend)
import { api } from '../shared/api';
import type { User, CreateUser } from '../shared/types';
// Récupérer des données
const { data: users } = await api.get<User[]>('/users');
// Créer
const { data: user } = await api.post<User>('/users', userData);
// Modifier
const { data: updated } = await api.patch<User>(`/users/${id}`, changes);â Utilisation interdite
// đ« INTERDIT - AccĂšs direct (bloquĂ© par ESLint)
import { createClient } from '@supabase/supabase-js';
import Redis from 'ioredis';đ Types auto-gĂ©nĂ©rĂ©s
# Générer les types depuis le MCP Server
npm run generate
# Les types sont créés dans shared/types.ts et shared/api.tsđš Frontend (Remix + Shadcn UI)
Installation Shadcn UI
cd web/
npx shadcn-ui@latest init
npx shadcn-ui@latest add button card form input label toastExemple de composant
import { useLoaderData } from "@remix-run/react";
import { Button } from "~/components/ui/button";
import { Card } from "~/components/ui/card";
import { api } from "../../shared/api";
export async function loader() {
const { data: users } = await api.get('/users');
return { users };
}
export default function Users() {
const { users } = useLoaderData<typeof loader>();
return (
<div className="container mx-auto p-6">
<h1 className="text-3xl font-bold mb-6">Users</h1>
<div className="grid gap-4 md:grid-cols-2 lg:grid-cols-3">
{users.map((user) => (
<Card key={user.id} className="p-4">
<h3 className="font-semibold">{user.name}</h3>
<p className="text-sm text-muted-foreground">{user.email}</p>
<Button variant="outline" size="sm" className="mt-2">
View Profile
</Button>
</Card>
))}
</div>
</div>
);
}đïž Backend (NestJS)
Exemple de service
import { Injectable } from '@nestjs/common';
import { Cron } from '@nestjs/schedule';
import { api } from '../../shared/api';
@Injectable()
export class OrderService {
async processOrder(userId: string) {
// Récupérer user via MCP
const { data: user } = await api.get(`/users/${userId}`);
if (user.role !== 'admin') {
throw new Error('Unauthorized');
}
// Créer commande via MCP
const { data: order } = await api.post('/orders', {
user_id: userId,
items: [],
total: 0,
status: 'processing'
});
return order;
}
@Cron('0 */10 * * * *') // Toutes les 10 minutes
async cleanupOrders() {
const { data: orders } = await api.get('/orders?status=pending');
// Cleanup logic...
}
}đĄïž SĂ©curitĂ©
ESLint Rule (Une seule rĂšgle pour tous)
module.exports = {
rules: {
'no-restricted-imports': ['error', {
patterns: [
'@supabase/supabase-js',
'ioredis',
'redis',
'@prisma/client',
'pg',
'mysql*',
'mongodb'
],
message: 'đ« AccĂšs data uniquement via l\'API MCP sur :3001'
}]
}
};đł Production (Docker)
# Build et démarrage
docker-compose up --build
# Environnement complet avec Redis inclusđ Monitoring
Health Check
curl http://localhost:3001/healthAPI Documentation
http://localhost:3001/docsLogs centralisés
Tous les logs sont dans le MCP Server avec Pino.
đŻ Avantages de cette approche
â SimplicitĂ© maximale
3 dossiers au lieu de 15 packages
1 rĂšgle : tout passe par l'API MCP
Setup en 10 minutes
â Stack complĂšte prĂ©servĂ©e
Supabase + Redis + NestJS + Remix + Shadcn UI
Performance cache Redis intégrée
Types TypeScript auto-générés
Validation Zod partout
â SĂ©curitĂ© robuste
AccĂšs DB/Cache impossible en dehors du MCP Server
ESLint bloque les imports directs
API centralisée avec rate limiting
â Developer Experience
Documentation Swagger auto-générée
Types partagés automatiques
Hot reload sur tous les services
Debugging facilité
Cette architecture simple est prĂȘte pour la production ! đ
This server cannot be installed
Resources
Unclaimed servers have limited discoverability.
Looking for Admin?
If you are the server author, to access and configure the admin panel.
Latest Blog Posts
MCP directory API
We provide all the information about MCP servers via our MCP API.
curl -X GET 'https://glama.ai/api/mcp/v1/servers/ak125/mcp'
If you have feedback or need assistance with the MCP directory API, please join our Discord server