Skip to content

Connected Accounts

Connected Accounts is the OpenEdge credential and authorization center. It lets users connect external providers once and reuse those connections from service instances.

Why It Exists

Without Connected Accounts, every service would need to store its own provider key, webhook token, or OAuth token. That is harder to secure, harder to rotate, and harder for customers to understand.

Connected Accounts centralizes:

  • Provider catalog.
  • Encrypted API key storage.
  • Connection status.
  • Scopes and provider metadata.
  • Testing and audit events.
  • OAuth authorization flows.

Supported Providers

ProviderAuth typeStatusUsed by
OpenAI-compatibleAPI keyAvailableAI Model Gateway
OpenRouterAPI keyAvailableAI Model Gateway
DeepSeekAPI keyAvailableAI Model Gateway
Custom API KeyAPI keyAvailableAI, Webhook Push, plugins
Telegram BotAPI keyAvailableWebhook Push
SlackOAuth/webhookPlannedWebhook Push
GitHubOAuthPlannedDeveloper automation
DiscordOAuthAvailableCommunity automation identity grants

Console Flow

  1. Open the Console.
  2. Go to Connections.
  3. Choose a provider.
  4. Enter a display name and API key.
  5. Optionally enter a provider base URL.
  6. Save and test the connection.
  7. Reuse it from AI Model Gateway or Webhook Push service configuration.

For Discord, choose Connect from the provider catalog. OpenEdge redirects the user to Discord, validates the OAuth state on callback, encrypts the returned tokens, and stores the Discord user id/name as provider metadata.

API Routes

Console routes require an authenticated console session:

http
GET    /console/connections/providers
GET    /console/connections
POST   /console/connections/api-key
POST   /console/connections/:id/test
DELETE /console/connections/:id
GET    /console/connections/:provider/start
GET    /oauth/connections/:provider/callback

Example API key connection request:

json
{
  "provider": "openrouter",
  "display_name": "OpenRouter Production",
  "credentials": {
    "api_key": "sk-or-..."
  },
  "config": {
    "base_url": "https://openrouter.ai/api/v1"
  },
  "scopes": ["chat"]
}

Responses never include the raw secret:

json
{
  "success": true,
  "data": {
    "id": "conn_...",
    "provider": "openrouter",
    "auth_type": "api_key",
    "display_name": "OpenRouter Production",
    "status": "active",
    "credentials": {
      "api_key": "configured...[REDACTED]"
    }
  }
}

Discord OAuth setup requires these Worker secrets/config values:

text
DISCORD_CLIENT_ID
DISCORD_CLIENT_SECRET
CONFIG_ENCRYPTION_KEY
FRONTEND_URL

Register this redirect URL in the Discord Developer Portal, unless DISCORD_OAUTH_REDIRECT_URI is set to a custom value:

text
https://api.open4x.com/oauth/connections/discord/callback

Service References

Services reference a connection with:

json
{
  "connected_account_id": "conn_..."
}

At runtime, OpenEdge checks:

  • The connection belongs to the authenticated user.
  • The connection is active.
  • The provider is allowed for the calling service.
  • The encrypted credential can be decrypted.
  • Provider configuration such as base_url passes URL safety checks.

Security Requirements

  • Raw API keys exist only in request memory.
  • Encrypted credentials are stored in D1.
  • The encryption key must be configured as CONFIG_ENCRYPTION_KEY.
  • OAuth callbacks use one-time states stored in connection_oauth_states.
  • Deleted or inactive connections cannot be used by service calls.
  • Connection test results store summaries, not full upstream responses.