'use strict';

const os = require('node:os');

function getLiveCapabilities(opts = {}) {
  const now = opts.now || (() => new Date().toISOString());
  const platform = opts.platform || process.platform;
  const warnings = [];
  const errors = [];
  const slack = inspectSlack(opts.slackMcp, warnings, errors);
  const googleWorkspace = inspectGoogleWorkspace(opts.gwsSetup, warnings, errors);
  const macos = inspectMacos(platform);
  const gmail = {
    available: googleWorkspace.usableAccounts > 0,
    provider: 'google_workspace',
    readTools: ['mail_messages', 'mail_search', 'mail_read'],
    writeTools: ['mail_send', 'mail_reply'],
    usableAccounts: googleWorkspace.usableAccounts,
    connectedAccounts: googleWorkspace.connectedAccounts,
    note: googleWorkspace.usableAccounts > 0
      ? 'Gmail/Google Workspace tools are available through local Wall-E tools.'
      : 'No usable Google Workspace mail account was detected.',
  };
  const calendar = {
    available: macos.available || googleWorkspace.usableAccounts > 0,
    readTools: ['calendar_events', 'calendar_list'],
    writeTools: ['calendar_create'],
    sources: [
      macos.available ? 'macos' : null,
      googleWorkspace.usableAccounts > 0 ? 'google_workspace' : null,
    ].filter(Boolean),
  };

  return {
    ok: errors.length === 0,
    generatedAt: now(),
    host: {
      platform,
      arch: process.arch,
      hostname: safeHostname(opts.hostname || os.hostname()),
    },
    capabilities: {
      slack,
      googleWorkspace,
      gmail,
      calendar,
      macos,
    },
    summary: summarizeLiveCapabilities({
      capabilities: { slack, googleWorkspace, gmail, calendar, macos },
      warnings,
      errors,
    }),
    warnings,
    errors,
  };
}

function inspectSlack(injectedSlackMcp, warnings, errors) {
  try {
    const slackMcp = injectedSlackMcp || require('../tools/slack-mcp');
    const token = slackMcp.loadToken?.() || null;
    const connected = Boolean(token?.access_token);
    return {
      available: connected,
      connected,
      team: token?.team_name || null,
      teamIdPresent: Boolean(token?.team_id),
      userIdPresent: Boolean(token?.user_id),
      expiresAt: token?.expiresAt ? new Date(Number(token.expiresAt)).toISOString() : null,
      readTools: ['slack_search', 'slack_read_channel'],
      writeTools: ['slack_send_message'],
      note: connected
        ? 'Slack MCP token is present. Use read tools first; sending requires policy approval.'
        : 'Slack MCP token was not found.',
    };
  } catch (err) {
    errors.push({ capability: 'slack', message: err.message });
    return {
      available: false,
      connected: false,
      readTools: ['slack_search', 'slack_read_channel'],
      writeTools: ['slack_send_message'],
      note: 'Could not inspect Slack MCP status.',
    };
  }
}

function inspectGoogleWorkspace(injectedGwsSetup, warnings, errors) {
  try {
    const gwsSetup = injectedGwsSetup || require('../skills/_bundled/gws-workspace/setup');
    const accounts = typeof gwsSetup.listAccounts === 'function' ? gwsSetup.listAccounts() : [];
    const profiles = typeof gwsSetup.getGwsProfiles === 'function' ? gwsSetup.getGwsProfiles() : [];
    let installed = false;
    try { installed = typeof gwsSetup.isGwsInstalled === 'function' ? Boolean(gwsSetup.isGwsInstalled()) : false; } catch {}
    const accountSummaries = accounts.map(account => summarizeGoogleAccount(account));
    const usableAccounts = accountSummaries.filter(account => account.usable).length;
    const connectedAccounts = accountSummaries.filter(account => account.connected).length;
    const hasClientSecret = profiles.length
      ? profiles.some(profile => profile.hasClientSecret)
      : Boolean(gwsSetup.getClientCredentials?.());
    return {
      available: usableAccounts > 0,
      installed,
      hasClientSecret,
      profiles: profiles.map(profile => ({
        id: profile.id || '',
        label: profile.label || '',
        source: profile.source || '',
        hasClientSecret: Boolean(profile.hasClientSecret),
      })),
      accounts: accountSummaries,
      connectedAccounts,
      usableAccounts,
      readTools: ['mail_messages', 'mail_search', 'mail_read', 'calendar_events', 'calendar_list'],
      writeTools: ['mail_send', 'mail_reply', 'calendar_create'],
    };
  } catch (err) {
    errors.push({ capability: 'google_workspace', message: err.message });
    return {
      available: false,
      installed: false,
      hasClientSecret: false,
      profiles: [],
      accounts: [],
      connectedAccounts: 0,
      usableAccounts: 0,
      readTools: ['mail_messages', 'mail_search', 'mail_read', 'calendar_events', 'calendar_list'],
      writeTools: ['mail_send', 'mail_reply', 'calendar_create'],
    };
  }
}

function summarizeGoogleAccount(account = {}) {
  const connected = Boolean(account.hasAccessToken || account.hasRefreshToken);
  const usable = connected && !account.reauthRequired;
  return {
    account: maskEmail(account.email),
    domain: emailDomain(account.email),
    kind: account.accountKind || 'google',
    label: account.accountLabel || account.profileLabel || '',
    profileId: account.profileId || null,
    profileSource: account.profileSource || null,
    active: Boolean(account.active),
    connected,
    usable,
    reauthRequired: Boolean(account.reauthRequired),
    authIssue: account.lastRefreshError ? 'credential_needs_attention' : null,
  };
}

function inspectMacos(platform) {
  return {
    available: platform === 'darwin',
    platform,
    calendar: platform === 'darwin',
    mailFallback: platform === 'darwin',
    note: platform === 'darwin'
      ? 'macOS native Calendar/Mail fallbacks may be available depending on app permissions.'
      : 'macOS native app fallbacks are unavailable on this platform.',
  };
}

function summarizeLiveCapabilities(input = {}) {
  const capabilities = input.capabilities || input;
  const slack = capabilities.slack || {};
  const gmail = capabilities.gmail || {};
  const googleWorkspace = capabilities.googleWorkspace || {};
  const calendar = capabilities.calendar || {};
  return {
    slack: slack.available ? 'available' : 'unavailable',
    gmail: gmail.available ? `available:${gmail.usableAccounts || 0}` : 'unavailable',
    google_workspace: googleWorkspace.available ? `available:${googleWorkspace.usableAccounts || 0}` : 'unavailable',
    calendar: calendar.available ? 'available' : 'unavailable',
    warnings: (input.warnings || []).map(w => w.code || w.message || String(w)),
    errors: (input.errors || []).map(e => e.capability || e.message || String(e)),
  };
}

function maskEmail(value) {
  const email = String(value || '').trim().toLowerCase();
  const match = email.match(/^([^@]+)@([^@]+)$/);
  if (!match) return '';
  const [, local, domain] = match;
  const prefix = local.slice(0, 1);
  const suffix = local.length > 2 ? local.slice(-1) : '';
  return `${prefix}***${suffix}@${domain}`;
}

function emailDomain(value) {
  const email = String(value || '').trim().toLowerCase();
  const at = email.lastIndexOf('@');
  return at >= 0 ? email.slice(at + 1) : '';
}

function safeHostname(value) {
  return String(value || '').split('.')[0].slice(0, 80);
}

module.exports = {
  getLiveCapabilities,
  summarizeLiveCapabilities,
  maskEmail,
};
