Signed-off-by: phernandez <paul@basicmachines.co> Co-authored-by: phernandez <paul@basicmachines.co> Co-authored-by: Claude <noreply@anthropic.com>
7.6 KiB
Supabase OAuth Setup for Basic Memory
This guide explains how to set up Supabase as the OAuth provider for Basic Memory MCP server in production.
Prerequisites
- A Supabase project (create one at supabase.com)
- Basic Memory MCP server deployed
- Environment variables configuration
Overview
The Supabase OAuth provider offers:
- Production-ready authentication with persistent storage
- User management through Supabase Auth
- JWT token validation
- Integration with Supabase's security features
- Support for social logins (GitHub, Google, etc.)
Setup Steps
1. Get Supabase Credentials
From your Supabase project dashboard:
- Go to Settings > API
- Copy these values:
Project URL→SUPABASE_URLanon publickey →SUPABASE_ANON_KEYservice_rolekey →SUPABASE_SERVICE_KEY(keep this secret!)- JWT secret →
SUPABASE_JWT_SECRET(under Settings > API > JWT Settings)
2. Configure Environment Variables
Create a .env file:
# Enable OAuth
FASTMCP_AUTH_ENABLED=true
FASTMCP_AUTH_PROVIDER=supabase
# Your MCP server URL
FASTMCP_AUTH_ISSUER_URL=https://your-mcp-server.com
# Supabase configuration
SUPABASE_URL=https://your-project.supabase.co
SUPABASE_ANON_KEY=your-anon-key
SUPABASE_SERVICE_KEY=your-service-key
SUPABASE_JWT_SECRET=your-jwt-secret
# Allowed OAuth clients (comma-separated)
SUPABASE_ALLOWED_CLIENTS=web-app,mobile-app,cli-tool
# Required scopes
FASTMCP_AUTH_REQUIRED_SCOPES=read,write
3. Create OAuth Clients Table (Optional)
For production, create a table to store OAuth clients in Supabase:
CREATE TABLE oauth_clients (
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
client_id TEXT UNIQUE NOT NULL,
client_secret TEXT NOT NULL,
name TEXT,
redirect_uris TEXT[],
allowed_scopes TEXT[],
created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);
-- Create an index for faster lookups
CREATE INDEX idx_oauth_clients_client_id ON oauth_clients(client_id);
-- RLS policies
ALTER TABLE oauth_clients ENABLE ROW LEVEL SECURITY;
-- Only service role can manage clients
CREATE POLICY "Service role can manage clients" ON oauth_clients
FOR ALL USING (auth.jwt()->>'role' = 'service_role');
4. Set Up Auth Flow
The Supabase OAuth provider handles the following flow:
-
Client Authorization Request
GET /authorize?client_id=web-app&redirect_uri=https://app.com/callback -
Redirect to Supabase Auth
- User authenticates with Supabase (email/password, magic link, or social login)
- Supabase redirects back to your MCP server
-
Token Exchange
POST /token Content-Type: application/x-www-form-urlencoded grant_type=authorization_code&code=xxx&client_id=web-app -
Access Protected Resources
GET /mcp Authorization: Bearer <access_token>
5. Enable Social Logins (Optional)
In Supabase dashboard:
- Go to Authentication > Providers
- Enable desired providers (GitHub, Google, etc.)
- Configure OAuth apps for each provider
- Users can now log in via social providers
6. User Management
Supabase provides:
- User registration and login
- Password reset flows
- Email verification
- User metadata storage
- Admin APIs for user management
Access user data in your MCP tools:
# In your MCP tool
async def get_user_info(ctx: Context):
# The token is already validated by the OAuth middleware
user_id = ctx.auth.user_id
email = ctx.auth.email
# Use Supabase client to get more user data if needed
user = await supabase.auth.admin.get_user_by_id(user_id)
return user
7. Production Deployment
-
Environment Security
- Never expose
SUPABASE_SERVICE_KEY - Use environment variables, not hardcoded values
- Rotate keys periodically
- Never expose
-
HTTPS Required
- Always use HTTPS in production
- Configure proper SSL certificates
-
Rate Limiting
- Implement rate limiting for auth endpoints
- Use Supabase's built-in rate limiting
-
Monitoring
- Monitor auth logs in Supabase dashboard
- Set up alerts for suspicious activity
Testing
Local Development
For local testing with Supabase:
# Start MCP server with Supabase auth
FASTMCP_AUTH_ENABLED=true \
FASTMCP_AUTH_PROVIDER=supabase \
SUPABASE_URL=http://localhost:54321 \
SUPABASE_ANON_KEY=your-local-anon-key \
bm mcp --transport streamable-http
Test Authentication Flow
import httpx
import asyncio
async def test_supabase_auth():
# 1. Register/login with Supabase directly
supabase_url = "https://your-project.supabase.co"
# 2. Get MCP authorization URL
response = await httpx.get(
"http://localhost:8000/authorize",
params={
"client_id": "web-app",
"redirect_uri": "http://localhost:3000/callback",
"response_type": "code",
}
)
# 3. User logs in via Supabase
# 4. Exchange code for MCP tokens
# 5. Access protected resources
asyncio.run(test_supabase_auth())
Advanced Configuration
Custom User Metadata
Store additional user data in Supabase:
-- Add custom fields to auth.users
ALTER TABLE auth.users
ADD COLUMN IF NOT EXISTS metadata JSONB DEFAULT '{}';
-- Or create a separate profiles table
CREATE TABLE profiles (
id UUID REFERENCES auth.users PRIMARY KEY,
username TEXT UNIQUE,
avatar_url TEXT,
bio TEXT,
created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);
Row Level Security (RLS)
Protect user data with RLS:
-- Users can only access their own data
CREATE POLICY "Users can view own profile" ON profiles
FOR SELECT USING (auth.uid() = id);
CREATE POLICY "Users can update own profile" ON profiles
FOR UPDATE USING (auth.uid() = id);
Custom Claims
Add custom claims to JWT tokens:
-- Function to add custom claims
CREATE OR REPLACE FUNCTION custom_jwt_claims()
RETURNS JSON AS $$
BEGIN
RETURN json_build_object(
'user_role', current_setting('request.jwt.claims')::json->>'user_role',
'permissions', current_setting('request.jwt.claims')::json->>'permissions'
);
END;
$$ LANGUAGE plpgsql;
Troubleshooting
Common Issues
-
Invalid JWT Secret
- Ensure
SUPABASE_JWT_SECRETmatches your Supabase project - Check Settings > API > JWT Settings in Supabase dashboard
- Ensure
-
CORS Errors
- Configure CORS in your MCP server
- Add allowed origins in Supabase dashboard
-
Token Validation Fails
- Verify tokens are being passed correctly
- Check token expiration times
- Ensure scopes match requirements
-
User Not Found
- Confirm user exists in Supabase Auth
- Check if email is verified (if required)
- Verify client permissions
Debug Mode
Enable debug logging:
export FASTMCP_LOG_LEVEL=DEBUG
export SUPABASE_LOG_LEVEL=debug
Security Best Practices
- Secure Keys: Never commit secrets to version control
- Least Privilege: Use minimal required scopes
- Token Rotation: Implement refresh token rotation
- Audit Logs: Monitor authentication events
- Rate Limiting: Protect against brute force attacks
- HTTPS Only: Always use encrypted connections
Migration from Basic Auth
To migrate from the basic auth provider:
- Export existing user data
- Import users into Supabase Auth
- Update client applications to use new auth flow
- Gradually transition users to Supabase login
Next Steps
- Set up email templates in Supabase
- Configure password policies
- Implement MFA (multi-factor authentication)
- Add social login providers
- Create admin dashboard for user management