-- User license and authorization schema CREATE TABLE IF NOT EXISTS user_licenses ( user_id TEXT PRIMARY KEY, email TEXT, license_type TEXT NOT NULL CHECK (license_type IN ('free', 'pro', 'enterprise')), features JSONB NOT NULL DEFAULT '{ "maxIndicators": 5, "maxStrategies": 3, "maxBacktestDays": 30, "realtimeData": false, "customExecutors": false, "apiAccess": false }', resource_limits JSONB NOT NULL DEFAULT '{ "maxConcurrentSessions": 1, "maxMessagesPerDay": 100, "maxTokensPerMessage": 4096, "rateLimitPerMinute": 10 }', mcp_server_url TEXT NOT NULL, preferred_model JSONB DEFAULT NULL, expires_at TIMESTAMP WITH TIME ZONE, created_at TIMESTAMP WITH TIME ZONE NOT NULL DEFAULT NOW(), updated_at TIMESTAMP WITH TIME ZONE NOT NULL DEFAULT NOW() ); COMMENT ON COLUMN user_licenses.preferred_model IS 'Optional model preference: {"provider": "anthropic", "model": "claude-3-5-sonnet-20241022", "temperature": 0.7}'; CREATE INDEX idx_user_licenses_expires_at ON user_licenses(expires_at) WHERE expires_at IS NOT NULL; -- Channel linking for multi-channel support CREATE TABLE IF NOT EXISTS user_channel_links ( id SERIAL PRIMARY KEY, user_id TEXT NOT NULL REFERENCES user_licenses(user_id) ON DELETE CASCADE, channel_type TEXT NOT NULL CHECK (channel_type IN ('telegram', 'slack', 'discord', 'websocket')), channel_user_id TEXT NOT NULL, metadata JSONB, created_at TIMESTAMP WITH TIME ZONE NOT NULL DEFAULT NOW(), UNIQUE(channel_type, channel_user_id) ); CREATE INDEX idx_user_channel_links_user_id ON user_channel_links(user_id); CREATE INDEX idx_user_channel_links_channel ON user_channel_links(channel_type, channel_user_id); -- Example data for development INSERT INTO user_licenses (user_id, email, license_type, mcp_server_url, features, resource_limits, preferred_model) VALUES ( 'dev-user-001', 'dev@example.com', 'pro', 'http://localhost:8080/mcp', '{ "maxIndicators": 50, "maxStrategies": 20, "maxBacktestDays": 365, "realtimeData": true, "customExecutors": true, "apiAccess": true }', '{ "maxConcurrentSessions": 5, "maxMessagesPerDay": 1000, "maxTokensPerMessage": 8192, "rateLimitPerMinute": 60 }', '{ "provider": "anthropic", "model": "claude-3-5-sonnet-20241022", "temperature": 0.7 }' ) ON CONFLICT (user_id) DO NOTHING; -- Example Telegram link INSERT INTO user_channel_links (user_id, channel_type, channel_user_id) VALUES ('dev-user-001', 'telegram', '123456789') ON CONFLICT (channel_type, channel_user_id) DO NOTHING;