import { useState } from 'react'
import {
  Button,
  Field,
  SpinButton,
  Caption1,
  makeStyles,
  tokens,
  shorthands
} from '@fluentui/react-components'
import { DeleteRegular, ArrowUpRegular } from '@fluentui/react-icons'
import { useSources } from '../store/sources'
import { toast } from '../store/toasts'
import { SPACE } from './ui/tokens'

const useStyles = makeStyles({
  root: {
    display: 'flex',
    flexDirection: 'column',
    gap: '8px',
    padding: SPACE.cozy,
    backgroundColor: tokens.colorNeutralBackground2,
    ...shorthands.borderRadius(tokens.borderRadiusLarge),
    border: `1px solid ${tokens.colorNeutralStroke2}`
  },
  heading: { fontWeight: tokens.fontWeightSemibold },
  controls: { display: 'flex', alignItems: 'flex-end', gap: '12px', flexWrap: 'wrap' },
  spacer: { flexGrow: 1 },
  muted: { color: tokens.colorNeutralForeground3 },
  narrow: { width: '120px' }
})

/**
 * Retention / quality-upgrade panel for one Library source (PINCHFLAT stretch).
 * Two opt-in maintenance actions:
 *
 *   - Prune: keep only the N most-recent (and/or last-D-days) downloaded files;
 *     delete the older ones' files (the download archive stops them silently
 *     re-downloading). Destructive, so it shows a dry-run count and a two-step
 *     confirm before any file is deleted.
 *   - Upgrade: re-download items that were fetched below the source's current
 *     target quality (from its profile or the global default).
 *
 * The policy inputs are ephemeral (per-open) — this is an on-demand tidy, not a
 * persisted schedule, keeping retention to a desktop-app-sized scope.
 */
export function SourceRetention({ sourceId }: { sourceId: string }): React.JSX.Element {
  const styles = useStyles()
  const prunePreview = useSources((s) => s.prunePreview)
  const pruneItems = useSources((s) => s.pruneItems)
  const upgradePreview = useSources((s) => s.upgradePreview)
  const upgradeItems = useSources((s) => s.upgradeItems)

  const [maxCount, setMaxCount] = useState(25)
  const [confirmIds, setConfirmIds] = useState<string[] | null>(null)

  function onPrune(): void {
    const candidates = prunePreview(sourceId, { maxCount })
    if (candidates.length === 0) {
      toast(`Nothing to prune — the source has ${maxCount} or fewer downloaded files.`, 'info')
      return
    }
    setConfirmIds(candidates.map((c) => c.id))
  }

  async function onConfirmPrune(): Promise<void> {
    if (!confirmIds) return
    const deleted = await pruneItems(sourceId, confirmIds)
    toast(`Pruned ${deleted} file${deleted === 1 ? '' : 's'}.`, 'info')
    setConfirmIds(null)
  }

  function onUpgrade(): void {
    const candidates = upgradePreview(sourceId)
    if (candidates.length === 0) {
      toast('Nothing to upgrade — every downloaded video is already at the target quality.', 'info')
      return
    }
    const n = upgradeItems(sourceId, candidates)
    toast(`Re-queued ${n} video${n === 1 ? '' : 's'} to upgrade quality.`, 'info')
  }

  return (
    <div className={styles.root}>
      <Caption1 className={styles.heading}>Retention &amp; quality</Caption1>
      {confirmIds ? (
        <div className={styles.controls}>
          <Caption1 className={styles.muted}>
            Delete {confirmIds.length} older downloaded file{confirmIds.length === 1 ? '' : 's'}?
            The videos stay indexed and won&apos;t re-download.
          </Caption1>
          <div className={styles.spacer} />
          <Button
            size="small"
            appearance="primary"
            icon={<DeleteRegular />}
            onClick={onConfirmPrune}
          >
            Delete {confirmIds.length}
          </Button>
          <Button size="small" appearance="subtle" onClick={() => setConfirmIds(null)}>
            Cancel
          </Button>
        </div>
      ) : (
        <div className={styles.controls}>
          <Field label="Keep newest">
            <SpinButton
              className={styles.narrow}
              value={maxCount}
              min={1}
              max={9999}
              onChange={(_, d) => {
                const v = d.value ?? Number(d.displayValue)
                if (typeof v === 'number' && Number.isFinite(v))
                  setMaxCount(Math.max(1, Math.round(v)))
              }}
            />
          </Field>
          <Button size="small" appearance="subtle" icon={<DeleteRegular />} onClick={onPrune}>
            Prune older files
          </Button>
          <div className={styles.spacer} />
          <Button size="small" appearance="subtle" icon={<ArrowUpRegular />} onClick={onUpgrade}>
            Upgrade below-target
          </Button>
        </div>
      )}
    </div>
  )
}
