import { HelpText } from './HelpText';
import { FieldLabel, FieldInput } from './formUtils';
import type { SectionFormProps } from './types';

/**
 * SSH global config editor (`ssh.*` + nested `ssh.console.*`).
 *
 * Edits the `ssh.*` block of config.yaml via the same draft / save-bar flow as
 * other ConfigFormInner sections. Admin sub-tools (global connections /
 * grants / rotation / audit) hit their own per-row endpoints and live in
 * sibling subtabs of `SshForm`.
 */
export function SshConfigForm({ config, onChange, overriddenByEnv: _overriddenByEnv }: SectionFormProps) {
  const ssh = config.ssh ?? {};
  const console_ = ssh.console ?? {};

  return (
    <div className="space-y-5">
      <div>
        <label className="flex items-center gap-2 text-sm text-slate-700">
          <input
            type="checkbox"
            checked={ssh.enabled === true}
            onChange={e => onChange('ssh.enabled', e.target.checked)}
            className="rounded"
          />
          SSH 機能を有効化する
        </label>
        <HelpText>
          OFF の間は SshExec / SshUpload / SshDownload / SshConsole* 全ツールが利用不可になり、
          関連 API も router に登録されない。<code className="font-mono">MCP_ENCRYPTION_KEY</code> 環境変数も
          別途必須 (鍵が無い場合は ON にしても subsystem は disabled で起動)。
        </HelpText>
      </div>

      <div>
        <label className="flex items-center gap-2 text-sm text-slate-700">
          <input
            type="checkbox"
            checked={ssh.allowPrivateAddresses === true}
            onChange={e => onChange('ssh.allowPrivateAddresses', e.target.checked)}
            className="rounded"
          />
          プライベート / loopback アドレスへの接続を許可する
        </label>
        <HelpText>
          self-hosted / LAN 上のサーバーに繋ぐ場合に必要。OFF だと <code className="font-mono">10.x</code>,
          <code className="font-mono">192.168.x</code>, <code className="font-mono">127.0.0.1</code> 等の
          private アドレスへの接続が reject される。
        </HelpText>
      </div>

      <div>
        <label className="flex items-center gap-2 text-sm text-slate-700">
          <input
            type="checkbox"
            checked={ssh.adminBypassesGrants === true}
            onChange={e => onChange('ssh.adminBypassesGrants', e.target.checked)}
            className="rounded"
          />
          Admin は grant 無しでも接続を利用できる
        </label>
        <HelpText>
          ON: admin role の user は per-connection grant 無しでも全接続にアクセス可
          (監査ログには記録される)。OFF: admin もユーザーと同じく明示的 grant 必須。
        </HelpText>
      </div>

      <h3 className="text-sm font-medium text-slate-600 mt-6 pt-3 border-t border-slate-200">
        Limits / Timeouts
      </h3>

      <div>
        <FieldLabel>Call timeout (秒)</FieldLabel>
        <FieldInput
          type="number"
          value={ssh.callTimeoutSeconds ?? 30}
          onChange={v => onChange('ssh.callTimeoutSeconds', Number(v))}
        />
        <HelpText>
          SshExec / SshUpload / SshDownload の wall-clock 上限 (TCP connect + auth + 実行を含む)。
          デフォルト 30。SshConsole* には適用されない (こちらは idle/duration cap 側で管理)。
        </HelpText>
      </div>

      <div>
        <FieldLabel>Max output bytes</FieldLabel>
        <FieldInput
          type="number"
          value={ssh.maxOutputBytes ?? 32768}
          onChange={v => onChange('ssh.maxOutputBytes', Number(v))}
        />
        <HelpText>
          SshExec の stdout/stderr の合計バイト上限。超過分は truncate され
          <code className="font-mono">truncated_stdout: true</code> で返る。デフォルト 32768 (32 KiB)。
        </HelpText>
      </div>

      <div className="grid grid-cols-2 gap-3">
        <div>
          <FieldLabel>Max upload size (MB)</FieldLabel>
          <FieldInput
            type="number"
            value={ssh.maxUploadSizeMb ?? 100}
            onChange={v => onChange('ssh.maxUploadSizeMb', Number(v))}
          />
        </div>
        <div>
          <FieldLabel>Max download size (MB)</FieldLabel>
          <FieldInput
            type="number"
            value={ssh.maxDownloadSizeMb ?? 100}
            onChange={v => onChange('ssh.maxDownloadSizeMb', Number(v))}
          />
        </div>
      </div>
      <HelpText>SshUpload / SshDownload のファイルサイズ上限。超過は転送前に reject。</HelpText>

      <div>
        <FieldLabel>Audit retention (日)</FieldLabel>
        <FieldInput
          type="number"
          value={ssh.auditRetentionDays ?? 90}
          onChange={v => onChange('ssh.auditRetentionDays', Number(v))}
        />
        <HelpText>
          <code className="font-mono">ssh_audit_log</code> テーブルの保持日数。Audit tab の
          "Prune" ボタンでこの値より古い行を削除できる。
        </HelpText>
      </div>

      <h3 className="text-sm font-medium text-slate-600 mt-6 pt-3 border-t border-slate-200">
        Abuse detection
      </h3>
      <HelpText>
        ホスト鍵不一致 / 認証失敗 / コマンド失敗が短時間に集中したら接続を一時ロックする。
        ロック中は同接続が <code className="font-mono">abuse_locked</code> エラーで reject される。
      </HelpText>

      <div className="grid grid-cols-3 gap-3">
        <div>
          <FieldLabel>Window (分)</FieldLabel>
          <FieldInput
            type="number"
            value={ssh.abuseWindowMinutes ?? 10}
            onChange={v => onChange('ssh.abuseWindowMinutes', Number(v))}
          />
        </div>
        <div>
          <FieldLabel>Failure threshold</FieldLabel>
          <FieldInput
            type="number"
            value={ssh.abuseFailureThreshold ?? 5}
            onChange={v => onChange('ssh.abuseFailureThreshold', Number(v))}
          />
        </div>
        <div>
          <FieldLabel>Lock duration (分)</FieldLabel>
          <FieldInput
            type="number"
            value={ssh.abuseLockMinutes ?? 30}
            onChange={v => onChange('ssh.abuseLockMinutes', Number(v))}
          />
        </div>
      </div>

      <h3 className="text-sm font-medium text-slate-600 mt-6 pt-3 border-t border-slate-200">
        Interactive Console (SSH タブ / SshConsole* tools)
      </h3>

      <div>
        <label className="flex items-center gap-2 text-sm text-slate-700">
          <input
            type="checkbox"
            checked={console_.enabled === true}
            onChange={e => onChange('ssh.console.enabled', e.target.checked)}
            className="rounded"
          />
          Console 機能を有効化する
        </label>
        <HelpText>
          OFF だと SshConsole* tools と <code className="font-mono">SSH</code> タブが無効。
          上の "SSH 機能を有効化する" と <code className="font-mono">MCP_ENCRYPTION_KEY</code> も
          別途必須。
        </HelpText>
      </div>

      <div className="grid grid-cols-2 gap-3">
        <div>
          <FieldLabel>Idle timeout (秒)</FieldLabel>
          <FieldInput
            type="number"
            value={console_.idleTimeoutSeconds ?? 1800}
            onChange={v => onChange('ssh.console.idleTimeoutSeconds', Number(v))}
          />
          <HelpText>
            I/O が一定秒無いセッションを auto-close する閾値。人間の入力も AI の入力も
            activity としてカウントする。デフォルト 1800 (30 分)。
          </HelpText>
        </div>
        <div>
          <FieldLabel>Max session duration (秒)</FieldLabel>
          <FieldInput
            type="number"
            value={console_.maxSessionDurationSeconds ?? 14400}
            onChange={v => onChange('ssh.console.maxSessionDurationSeconds', Number(v))}
          />
          <HelpText>
            1 セッションの絶対上限。Idle じゃなくてもこの時間を超えると強制 close。
            デフォルト 14400 (4 時間)。
          </HelpText>
        </div>
      </div>

      <div>
        <FieldLabel>Scrollback bytes</FieldLabel>
        <FieldInput
          type="number"
          value={console_.scrollbackBytes ?? 524288}
          onChange={v => onChange('ssh.console.scrollbackBytes', Number(v))}
        />
        <HelpText>
          サーバー側で保持する PTY 出力履歴のリングバッファ容量。ブラウザ再接続時に
          replay される量。デフォルト 524288 (512 KiB)。
        </HelpText>
      </div>

      <div>
        <FieldLabel>Max sessions per connection</FieldLabel>
        <FieldInput
          type="number"
          value={console_.maxSessionsPerConnection ?? 3}
          onChange={v => onChange('ssh.console.maxSessionsPerConnection', Number(v))}
        />
        <HelpText>
          同じ接続を使う並列セッション数の上限。超えた場合は最も古いセッションが
          <code className="font-mono">session_cap_evict</code> 理由で close される。
        </HelpText>
      </div>

      <div>
        <FieldLabel>Max input bytes per Send</FieldLabel>
        <FieldInput
          type="number"
          value={console_.maxInputBytesPerSend ?? 16384}
          onChange={v => onChange('ssh.console.maxInputBytesPerSend', Number(v))}
        />
        <HelpText>
          1 回の <code className="font-mono">SshConsoleSend</code> で送れる最大バイト数。
          デフォルト 16384 (16 KiB)。
        </HelpText>
      </div>

      <div>
        <FieldLabel>Auto-inject screen lines</FieldLabel>
        <FieldInput
          type="number"
          value={console_.autoInjectScreenLines ?? 24}
          onChange={v => onChange('ssh.console.autoInjectScreenLines', Number(v))}
        />
        <HelpText>
          各 LLM iteration の system prompt 末尾に挿入する screen の末尾行数。
          多いほど AI の状況認識が良くなるが context を消費する。デフォルト 24 行。
        </HelpText>
      </div>

      <div className="grid grid-cols-2 gap-3">
        <div>
          <FieldLabel>Default cols</FieldLabel>
          <FieldInput
            type="number"
            value={console_.defaultCols ?? 120}
            onChange={v => onChange('ssh.console.defaultCols', Number(v))}
          />
        </div>
        <div>
          <FieldLabel>Default rows</FieldLabel>
          <FieldInput
            type="number"
            value={console_.defaultRows ?? 32}
            onChange={v => onChange('ssh.console.defaultRows', Number(v))}
          />
        </div>
      </div>
      <HelpText>
        PTY サイズの初期値。クライアントが resize イベントを送れば上書きされる。
      </HelpText>
    </div>
  );
}
