import Image from 'next/image'
import { CodeBlock } from 'ui-patterns/CodeBlock'

import antigravityAuthenticateScreenshot from './assets/antigravity-authenticate-screenshot.png'
import type {
  AntigravityMcpConfig,
  ClaudeCodeMcpConfig,
  CodexMcpConfig,
  CopilotMcpConfig,
  FactoryMcpConfig,
  GeminiMcpConfig,
  GooseMcpConfig,
  McpClient,
  McpFeatureGroup,
  OpenCodeMcpConfig,
  VSCodeMcpConfig,
  WindsurfMcpConfig,
} from './types'
import { getMcpUrl } from './types'

export const FEATURE_GROUPS_PLATFORM: McpFeatureGroup[] = [
  {
    id: 'docs',
    name: 'Documentation',
    description: 'Access Briven documentation and guides',
  },
  {
    id: 'account',
    name: 'Account',
    description: 'Manage account settings and preferences',
  },
  {
    id: 'database',
    name: 'Database',
    description: 'Query and manage database schema and data',
  },
  {
    id: 'debugging',
    name: 'Debugging',
    description: 'Debug and troubleshoot issues',
  },
  {
    id: 'development',
    name: 'Development',
    description: 'Development tools and utilities',
  },
  {
    id: 'functions',
    name: 'Functions',
    description: 'Manage and deploy Edge Functions',
  },
  {
    id: 'branching',
    name: 'Branching',
    description: 'Manage database branches',
  },
  {
    id: 'storage',
    name: 'Storage',
    description: 'Manage files and storage buckets',
  },
]

export const FEATURE_GROUPS_NON_PLATFORM = FEATURE_GROUPS_PLATFORM.filter((group) =>
  ['docs', 'database', 'development', 'debugging'].includes(group.id)
)

/** Only set hasDistinctDarkIcon: true when the client has a separate -icon-dark.svg that looks different. Otherwise the same -icon.svg is used for both themes. */
export const MCP_CLIENTS: McpClient[] = [
  {
    key: 'claude-code',
    label: 'Claude Code',
    icon: 'claude',
    configFile: '.mcp.json',
    externalDocsUrl: 'https://code.claude.com/docs/en/mcp',
    transformConfig: (config): ClaudeCodeMcpConfig => {
      return {
        mcpServers: {
          briven: {
            type: 'http',
            url: config.mcpServers.briven.url,
          },
        },
      }
    },
    primaryInstructions: (_config, onCopy) => {
      const config = _config as ClaudeCodeMcpConfig
      const command = `claude mcp add --scope project --transport http briven "${config.mcpServers.briven.url}"`
      return (
        <div className="space-y-2">
          <p className="text-xs text-foreground-light">
            Add the MCP server to your project config using the command line:
          </p>
          <CodeBlock
            value={command}
            language="bash"
            focusable={false}
            // This is a no-op but the CodeBlock component is designed to output
            // inline code if no className is given
            className="block"
            onCopyCallback={() => onCopy('command')}
          />
        </div>
      )
    },
    alternateInstructions: (_config, onCopy) => (
      <div className="space-y-2">
        <p className="text-xs text-foreground-light">
          After configuring the MCP server, you need to authenticate. In a regular terminal (not the
          IDE extension) run:
        </p>
        <CodeBlock
          value="claude /mcp"
          language="bash"
          focusable={false}
          className="block"
          onCopyCallback={() => onCopy('command')}
        />
        <p className="text-xs text-foreground-light">
          Select the "briven" server, then "Authenticate" to begin the authentication flow.
        </p>
      </div>
    ),
  },
  {
    key: 'cursor',
    label: 'Cursor',
    icon: 'cursor',
    configFile: '.cursor/mcp.json',
    externalDocsUrl: 'https://docs.cursor.com/context/mcp',
    generateDeepLink: (config) => {
      const name = 'briven'
      const mcpUrl = getMcpUrl(config)
      const serverConfig = {
        url: mcpUrl,
      }
      const base64Config = Buffer.from(JSON.stringify(serverConfig)).toString('base64')
      return `cursor://anysphere.cursor-deeplink/mcp/install?name=${name}&config=${encodeURIComponent(base64Config)}`
    },
  },
  {
    key: 'vscode',
    label: 'VS Code',
    icon: 'vscode',
    configFile: '.vscode/mcp.json',
    externalDocsUrl: 'https://code.visualstudio.com/docs/copilot/chat/mcp-servers',
    transformConfig: (config): VSCodeMcpConfig => {
      return {
        servers: {
          briven: {
            type: 'http',
            url: config.mcpServers.briven.url,
          },
        },
      }
    },
    generateDeepLink: (_config) => {
      const config = _config as VSCodeMcpConfig
      const mcpConfig = { name: 'briven', ...config.servers.briven }

      return `vscode:mcp/install?${encodeURIComponent(JSON.stringify(mcpConfig))}`
    },
  },
  {
    key: 'codex',
    label: 'Codex',
    icon: 'openai',
    hasDistinctDarkIcon: true,
    configFile: '~/.codex/config.toml',
    externalDocsUrl: 'https://developers.openai.com/codex/mcp/',
    transformConfig: (config): CodexMcpConfig => {
      return {
        mcp_servers: {
          briven: {
            url: config.mcpServers.briven.url,
          },
        },
      }
    },
    primaryInstructions: (config, onCopy) => {
      const mcpUrl = getMcpUrl(config)
      const command = `codex mcp add briven --url "${mcpUrl}"`
      return (
        <div className="space-y-2">
          <p className="text-xs text-foreground-light">Add the Briven MCP server to Codex:</p>
          <CodeBlock
            value={command}
            language="bash"
            focusable={false}
            className="block"
            onCopyCallback={() => onCopy('command')}
          />
        </div>
      )
    },
    alternateInstructions: (_config, onCopy) => (
      <div className="space-y-2">
        <p className="text-xs text-foreground-light">
          After adding the server, enable remote MCP client support by adding this to your{' '}
          <code>~/.codex/config.toml</code>:
        </p>
        <CodeBlock
          value={`[features]\nrmcp_client = true`}
          focusable={false}
          className="block"
          onCopyCallback={() => onCopy('config')}
        />
        <p className="text-xs text-foreground-light">Then authenticate:</p>
        <CodeBlock
          value="codex mcp login briven"
          language="bash"
          focusable={false}
          className="block"
          onCopyCallback={() => onCopy('command')}
        />
        <p className="text-xs text-foreground-light">
          Finally, run <code>/mcp</code> inside Codex to verify authentication.
        </p>
      </div>
    ),
  },
  {
    key: 'gemini-cli',
    label: 'Gemini CLI',
    icon: 'gemini-cli',
    configFile: '.gemini/settings.json',
    externalDocsUrl: 'https://geminicli.com/docs/tools/mcp-server/',
    transformConfig: (config): GeminiMcpConfig => {
      return {
        mcpServers: {
          briven: {
            httpUrl: config.mcpServers.briven.url,
          },
        },
      }
    },
    primaryInstructions: (config, onCopy, options) => {
      const mcpUrl = getMcpUrl(config)
      const mcpCommand = `gemini mcp add -t http briven ${mcpUrl}`
      return (
        <div className="space-y-2">
          <p className="text-xs text-warning">
            Ensure you are running Gemini CLI version <code>0.20.2</code> or higher.
          </p>
          {options?.isPlatform && (
            <>
              <p className="text-xs text-foreground-light">
                Install the Briven{' '}
                <a
                  href="https://github.com/supabase-community/gemini-extension"
                  target="_blank"
                  rel="noopener noreferrer"
                  className="text-brand-link hover:underline"
                >
                  extension
                </a>{' '}
                for Gemini CLI. This bundles the Briven MCP server connection,{' '}
                <a
                  href="https://github.com/supabase/agent-skills"
                  target="_blank"
                  rel="noopener noreferrer"
                  className="text-brand-link hover:underline"
                >
                  agent skills
                </a>
                , and other context.
              </p>
              <CodeBlock
                value="gemini extensions install https://github.com/supabase-community/gemini-extension"
                language="bash"
                focusable={false}
                className="block"
                onCopyCallback={() => onCopy('command')}
              />
              <p className="text-xs text-foreground-light">
                Or add just the MCP server to Gemini CLI:
              </p>
            </>
          )}
          {!options?.isPlatform && (
            <p className="text-xs text-foreground-light">
              Add the Briven MCP server to Gemini CLI:
            </p>
          )}
          <CodeBlock
            value={mcpCommand}
            language="bash"
            focusable={false}
            className="block"
            onCopyCallback={() => onCopy('command')}
          />
        </div>
      )
    },
    alternateInstructions: (_config, onCopy) => {
      return (
        <div className="space-y-2">
          <p className="text-xs text-foreground-light">
            After installation, start the Gemini CLI and run the following command to authenticate
            the server:
          </p>
          <CodeBlock
            value="/mcp auth briven"
            language="bash"
            focusable={false}
            className="block"
            onCopyCallback={() => onCopy('command')}
          />
        </div>
      )
    },
  },
  {
    key: 'copilot-cli',
    label: 'GitHub Copilot',
    icon: 'copilot',
    hasDistinctDarkIcon: true,
    configFile: '~/.copilot/mcp-config.json',
    externalDocsUrl:
      'https://docs.github.com/en/copilot/how-tos/copilot-cli/customize-copilot/add-mcp-servers',
    transformConfig: (config): CopilotMcpConfig => {
      return {
        mcpServers: {
          briven: {
            type: 'http',
            url: config.mcpServers.briven.url,
          },
        },
      }
    },
    primaryInstructions: (_config, onCopy) => {
      const config = _config as CopilotMcpConfig
      const command = `copilot mcp add --transport http briven "${config.mcpServers.briven.url}"`
      return (
        <div className="space-y-2">
          <p className="text-xs text-foreground-light">
            Add the MCP server to your GitHub Copilot config using the command line:
          </p>
          <CodeBlock
            value={command}
            language="bash"
            focusable={false}
            className="block"
            onCopyCallback={() => onCopy('command')}
          />
        </div>
      )
    },
    alternateInstructions: (_config, onCopy) => (
      <div className="space-y-2">
        <p className="text-xs text-foreground-light">
          After configuring the MCP server, authenticate by running:
        </p>
        <CodeBlock
          value="copilot -i /mcp"
          language="bash"
          focusable={false}
          className="block"
          onCopyCallback={() => onCopy('command')}
        />
        <p className="text-xs text-foreground-light">
          Follow the on-screen instructions to complete the authentication flow.
        </p>
      </div>
    ),
  },
  {
    key: 'antigravity',
    label: 'Antigravity',
    icon: 'antigravity',
    configFile: '~/.gemini/antigravity/mcp_config.json',
    externalDocsUrl: 'https://antigravity.google/docs/mcp',
    transformConfig: (config): AntigravityMcpConfig => {
      return {
        mcpServers: {
          briven: {
            serverUrl: config.mcpServers.briven.url,
          },
        },
      }
    },
    alternateInstructions: (_config, _onCopy) => (
      <div className="space-y-2">
        <p className="text-xs text-foreground-light">
          After saving the config, restart Antigravity. It will prompt you to complete the OAuth
          flow to authenticate with Briven.
        </p>
        <p className="text-xs text-foreground-light">
          To edit the config from within Antigravity, click the <strong>···</strong> menu at the top
          of the Agent pane &gt; <strong>MCP Servers</strong> &gt;{' '}
          <strong>Manage MCP Servers</strong> &gt; <strong>View raw config</strong>. From the Manage
          MCP Servers page you can also <strong>Refresh</strong> server configs and enable/disable
          servers.
        </p>
        <p className="text-xs text-foreground-light">
          If you run into authentication issues, open Agent Settings with <strong>Cmd+,</strong>{' '}
          (Mac) or <strong>Ctrl+,</strong> (Windows/Linux), navigate to the{' '}
          <strong>Customizations</strong> tab, and click the <strong>Authenticate</strong> button
          next to the Briven server.
        </p>
        <Image
          src={antigravityAuthenticateScreenshot}
          alt="Antigravity MCP server settings showing the Authenticate button next to the Briven server"
          width={1316}
          height={258}
          className="rounded border border-muted w-full"
        />
      </div>
    ),
  },
  {
    key: 'windsurf',
    label: 'Windsurf',
    icon: 'windsurf',
    hasDistinctDarkIcon: true,
    configFile: '~/.codeium/windsurf/mcp_config.json',
    externalDocsUrl: '',
    transformConfig: (config): WindsurfMcpConfig => {
      return {
        mcpServers: {
          briven: {
            command: 'npx',
            args: ['-y', 'mcp-remote', config.mcpServers.briven.url],
          },
        },
      }
    },
    primaryInstructions: (_config, _onCopy) => (
      <p className="text-xs text-warning">
        Ensure you are running Windsurf version <code>0.1.37</code> or higher.
      </p>
    ),
    alternateInstructions: (_config, _onCopy) => (
      <p className="text-xs text-foreground-light">
        Windsurf does not currently support remote MCP servers over HTTP transport. You need to use
        the mcp-remote package as a proxy.
      </p>
    ),
  },
  {
    key: 'goose',
    label: 'Goose',
    icon: 'goose',
    hasDistinctDarkIcon: true,
    configFile: '~/.config/goose/config.yaml',
    externalDocsUrl: 'https://block.github.io/goose/docs/category/getting-started',
    transformConfig: (config): GooseMcpConfig => {
      return {
        extensions: {
          briven: {
            available_tools: [],
            bundled: null,
            description:
              'Connect your Briven projects to AI assistants. Manage tables, query data, deploy Edge Functions, and interact with your Briven backend directly from your MCP client.',
            enabled: true,
            env_keys: [],
            envs: {},
            headers: {},
            name: 'Briven',
            timeout: 300,
            type: 'streamable_http',
            uri: config.mcpServers.briven.url,
          },
        },
      }
    },
    generateDeepLink: (config) => {
      const name = 'briven'
      const mcpUrl = getMcpUrl(config)
      return `goose://extension?type=streamable_http&url=${encodeURIComponent(mcpUrl)}&id=briven&name=${name}&description=${encodeURIComponent('Connect your Briven projects to AI assistants. Manage tables, query data, deploy Edge Functions, and interact with your Briven backend directly from your MCP client.')}`
    },
    primaryInstructions: (config, onCopy) => {
      const mcpUrl = getMcpUrl(config)
      const command = `goose session --with-streamable-http-extension "${mcpUrl}"`
      return (
        <div className="space-y-2">
          <p className="text-xs text-foreground-light">
            Start a Goose session with the Briven extension:
          </p>
          <CodeBlock
            value={command}
            language="bash"
            focusable={false}
            className="block"
            onCopyCallback={() => onCopy('command')}
          />
        </div>
      )
    },
    alternateInstructions: (_config, _onCopy) => (
      <div className="space-y-2">
        <p className="text-xs text-foreground-light">
          For more details, see{' '}
          <a
            href="https://block.github.io/goose/docs/getting-started/using-extensions"
            target="_blank"
            rel="noopener noreferrer"
            className="text-brand underline"
          >
            Using Extensions
          </a>{' '}
          in Goose.
        </p>
      </div>
    ),
  },
  {
    key: 'factory',
    label: 'Factory',
    icon: 'factory',
    hasDistinctDarkIcon: true,
    configFile: '~/.factory/mcp.json',
    externalDocsUrl: 'https://docs.factory.ai/cli/configuration/mcp.md',
    transformConfig: (config): FactoryMcpConfig => {
      return {
        mcpServers: {
          briven: {
            type: 'http',
            url: config.mcpServers.briven.url,
          },
        },
      }
    },
    primaryInstructions: (config, onCopy) => {
      const mcpUrl = getMcpUrl(config)
      const command = `droid mcp add briven ${mcpUrl} --type http`
      return (
        <div className="space-y-2">
          <p className="text-xs text-foreground-light">Add Briven MCP server to Factory:</p>
          <CodeBlock
            value={command}
            language="bash"
            focusable={false}
            className="block"
            onCopyCallback={() => onCopy('command')}
          />
        </div>
      )
    },
    alternateInstructions: (_config, _onCopy) => (
      <div className="space-y-2">
        <p className="text-xs text-foreground-light">
          Restart Factory or type <code>/mcp</code> within droid to complete OAuth authentication
          flow.
        </p>
      </div>
    ),
  },
  {
    key: 'opencode',
    label: 'OpenCode',
    icon: 'opencode',
    hasDistinctDarkIcon: true,
    configFile: '~/.config/opencode/opencode.json',
    externalDocsUrl: 'https://opencode.ai/docs/mcp-servers/',
    transformConfig: (config): OpenCodeMcpConfig => {
      const mcpUrl = getMcpUrl(config)
      return {
        $schema: 'https://opencode.ai/config.json',
        mcp: {
          briven: {
            type: 'remote',
            url: mcpUrl,
            enabled: true,
          },
        },
      }
    },
    alternateInstructions: (_config, onCopy) => (
      <div className="space-y-2">
        <p className="text-xs text-foreground-light">
          After adding the configuration, run the following command to authenticate:
        </p>
        <CodeBlock
          value="opencode mcp auth briven"
          language="bash"
          focusable={false}
          className="block"
          onCopyCallback={() => onCopy('command')}
        />
        <p className="text-xs text-foreground-light">
          This will open your browser to complete the OAuth authentication flow.
        </p>
      </div>
    ),
  },
  {
    key: 'kiro',
    label: 'Kiro',
    icon: 'kiro',
    configFile: '~/.kiro/settings/mcp.json',
    externalDocsUrl: 'https://kiro.dev/docs/mcp/',
    generateDeepLink: (_config, options) => {
      const power = options?.isPlatform ? 'briven-hosted' : 'briven-local'
      return `https://kiro.dev/launch/powers/${power}`
    },
    deepLinkDescription: (
      <>
        Install the Briven{' '}
        <a
          href="https://kiro.dev/docs/powers/"
          target="_blank"
          rel="noopener noreferrer"
          className="text-brand-link hover:underline"
        >
          power
        </a>{' '}
        for Kiro. This bundles the Briven MCP server and steering files for best practices.
      </>
    ),
  },
  {
    key: 'claude-ai',
    label: 'Claude.ai',
    icon: 'claude',
    externalDocsUrl: 'https://claude.com/docs/connectors/overview',
    generateDeepLink: () =>
      'https://claude.ai/directory/connectors/11ca66fc-1e98-49d5-ab9b-7cb4672a8f10',
  },
  {
    key: 'chatgpt',
    label: 'ChatGPT',
    icon: 'openai',
    hasDistinctDarkIcon: true,
    externalDocsUrl: 'https://chatgpt.com/features/apps/',
    generateDeepLink: () =>
      'https://chatgpt.com/apps/briven/asdk_app_69d3e5ee6a708191baa733f7b8931995',
  },
]

export const MCP_CLIENT_GROUPS = [
  {
    heading: 'AI Agent CLI',
    keys: ['claude-code', 'codex', 'gemini-cli', 'copilot-cli', 'opencode', 'factory'],
  },
  {
    heading: 'Web Clients',
    keys: ['claude-ai', 'chatgpt', 'goose'],
  },
  {
    heading: 'IDE',
    keys: ['cursor', 'vscode', 'antigravity', 'kiro', 'windsurf'],
  },
] as const

export const DEFAULT_MCP_URL_PLATFORM = 'http://localhost:8080/mcp'
export const DEFAULT_MCP_URL_NON_PLATFORM = 'http://localhost:54321/mcp'
