export type AuthKind = 'oauth' | 'api_key';

export interface McpServerRecord {
  id: string;
  name: string;
  url: string;
  authKind: AuthKind;
  ownerId: string | null;   // null = global/admin-managed
  oauthClientId: string;
  oauthClientSecret: string; // decrypted, only in-memory (empty string for api_key servers)
  oauthScopes: string | null;
  staticToken: string | null; // decrypted, only in-memory (non-null for api_key servers)
  issuer: string | null;
  authorizationEndpoint: string | null;
  tokenEndpoint: string | null;
  discoveryFingerprint: string | null;
  enabled: boolean;
  createdBy: string | null;
  createdAt: string;
  updatedAt: string;
}

// Server record WITHOUT secrets for API responses
export type McpServerPublic = Omit<McpServerRecord, 'oauthClientSecret' | 'staticToken'>;

export interface UserMcpTokenRecord {
  userId: string;
  serverId: string;
  accessToken: string;       // decrypted
  refreshToken: string | null;
  expiresAt: string | null;
  scope: string | null;
  scopeType: 'user' | 'org';
  scopeId: string | null;
  connectedAt: string;
  updatedAt: string;
}

export interface McpConnectionPublic {
  serverId: string;
  serverName: string;
  connected: boolean;
  connectedAt: string | null;
  expiresAt: string | null;
}

export interface McpCachedTool {
  serverId: string;
  toolName: string;
  description: string | null;
  inputSchema: string | null; // JSON string
  refreshedAt: string;
}

export interface McpDiscoveryMetadata {
  issuer: string;
  authorizationEndpoint: string;
  tokenEndpoint: string;
  fingerprint: string;
}

export interface TokenEndpointResponse {
  access_token: string;
  token_type?: string;
  expires_in?: number;
  refresh_token?: string;
  scope?: string;
  iss?: string;
}

export class McpNotConnectedError extends Error {
  constructor(public readonly serverId: string) {
    super(`User is not connected to MCP server '${serverId}'`);
    this.name = 'McpNotConnectedError';
  }
}

export class McpTokenExpiredError extends Error {
  constructor(public readonly serverId: string) {
    super(`Access token expired and no refresh token available for '${serverId}'`);
    this.name = 'McpTokenExpiredError';
  }
}

export class McpKeyNotConfiguredError extends Error {
  constructor() {
    super('MCP_ENCRYPTION_KEY is not configured; MCP features are disabled');
    this.name = 'McpKeyNotConfiguredError';
  }
}
