// Collections management page (US-032) - Updated for RBAC field permissions

import { useState, useEffect, useCallback } from 'react'
import { useNavigate } from 'react-router-dom'
import apiClient from '@/api/client'
import { useWorkspace } from '@/contexts/WorkspaceContext'
import { useAuth } from '@/contexts/AuthContext'
import Button from '@/components/Button'
import Input from '@/components/Input'
import FieldPermissionEditor from '@/components/FieldPermissionEditor'
import type { Collection, Group, FieldPermission } from '@/types'

interface CollectionFormData {
  name: string
  schema: string
  field_permissions: FieldPermission[]
}

function CollectionModal({
  collection,
  workspaceId,
  availableGroups,
  onClose,
  onSave,
}: {
  collection: Collection | null
  workspaceId: string
  availableGroups: Group[]
  onClose: () => void
  onSave: () => void
}) {
  const [formData, setFormData] = useState<CollectionFormData>({
    name: collection?.name || '',
    schema: collection?.settings?.schema
      ? typeof collection.settings.schema === 'string'
        ? collection.settings.schema
        : JSON.stringify(collection.settings.schema, null, 2)
      : '{}',
    field_permissions: collection?.settings?.field_permissions || [],
  })
  const [isLoading, setIsLoading] = useState(false)
  const [error, setError] = useState<string | null>(null)
  const [schemaError, setSchemaError] = useState<string | null>(null)
  const [activeTab, setActiveTab] = useState<'schema' | 'permissions'>('schema')

  // Extract field names from schema for the field permission editor
  const schemaFields = (() => {
    try {
      const parsed = JSON.parse(formData.schema)
      if (parsed.properties && typeof parsed.properties === 'object') {
        return Object.keys(parsed.properties)
      }
      return []
    } catch {
      return []
    }
  })()

  const validateSchema = (schemaStr: string): boolean => {
    try {
      JSON.parse(schemaStr)
      setSchemaError(null)
      return true
    } catch {
      setSchemaError('Invalid JSON schema')
      return false
    }
  }

  const handleSchemaChange = (value: string) => {
    setFormData({ ...formData, schema: value })
    validateSchema(value)
  }

  const handleSubmit = async (e: React.FormEvent) => {
    e.preventDefault()

    if (!validateSchema(formData.schema)) {
      return
    }

    setIsLoading(true)
    setError(null)

    try {
      const payload = {
        name: formData.name,
        settings: {
          schema: JSON.parse(formData.schema),
          field_permissions: formData.field_permissions,
        },
      }

      if (collection) {
        await apiClient.request(`/workspaces/${workspaceId}/collections/${collection.name}`, {
          method: 'PUT',
          body: payload,
        })
      } else {
        await apiClient.post(`/workspaces/${workspaceId}/collections`, payload)
      }
      onSave()
    } catch (err) {
      setError(err instanceof Error ? err.message : 'Failed to save collection')
    } finally {
      setIsLoading(false)
    }
  }

  return (
    <div className="fixed inset-0 z-50 flex items-center justify-center bg-black/50">
      <div className="w-full max-w-3xl max-h-[90vh] overflow-y-auto rounded-lg bg-white p-6 shadow-xl">
        <h2 className="text-xl font-semibold text-gray-900">
          {collection ? 'Edit Collection' : 'Create Collection'}
        </h2>

        <form onSubmit={handleSubmit} className="mt-4 space-y-4">
          {error && (
            <div className="rounded-lg bg-red-50 px-4 py-3 text-sm text-red-700">{error}</div>
          )}

          <Input
            label="Collection Name"
            name="name"
            value={formData.name}
            onChange={(e) => setFormData({ ...formData, name: e.target.value })}
            placeholder="my_collection"
            required
            disabled={!!collection}
            autoFocus={!collection}
          />

          {/* Tabs */}
          <div className="border-b border-gray-200">
            <nav className="-mb-px flex space-x-8">
              <button
                type="button"
                onClick={() => setActiveTab('schema')}
                className={`py-2 px-1 border-b-2 font-medium text-sm ${
                  activeTab === 'schema'
                    ? 'border-indigo-500 text-indigo-600'
                    : 'border-transparent text-gray-500 hover:text-gray-700 hover:border-gray-300'
                }`}
              >
                Schema
              </button>
              <button
                type="button"
                onClick={() => setActiveTab('permissions')}
                className={`py-2 px-1 border-b-2 font-medium text-sm ${
                  activeTab === 'permissions'
                    ? 'border-indigo-500 text-indigo-600'
                    : 'border-transparent text-gray-500 hover:text-gray-700 hover:border-gray-300'
                }`}
              >
                Field Permissions
              </button>
            </nav>
          </div>

          {/* Tab Content */}
          {activeTab === 'schema' && (
            <div>
              <label className="mb-1.5 block text-sm font-medium text-gray-700">
                Schema (JSON)
              </label>
              <textarea
                value={formData.schema}
                onChange={(e) => handleSchemaChange(e.target.value)}
                placeholder='{ "type": "object", "properties": { ... } }'
                rows={12}
                className={`w-full rounded-lg border px-3 py-2 font-mono text-sm transition focus:outline-none focus:ring-2 ${
                  schemaError
                    ? 'border-red-500 focus:border-red-500 focus:ring-red-200'
                    : 'border-gray-300 focus:border-primary-500 focus:ring-primary-200'
                }`}
              />
              {schemaError && <p className="mt-1 text-sm text-red-600">{schemaError}</p>}
              <p className="mt-1 text-xs text-gray-500">
                Define the JSON Schema for document validation. Fields defined in the schema can be
                used for field-level permissions.
              </p>
            </div>
          )}

          {activeTab === 'permissions' && (
            <div className="space-y-4">
              <p className="text-sm text-gray-600">
                Configure which groups can read or write specific fields. Leave empty to allow all
                groups access.
              </p>
              <FieldPermissionEditor
                fieldPermissions={formData.field_permissions}
                onChange={(field_permissions) =>
                  setFormData({ ...formData, field_permissions })
                }
                availableGroups={availableGroups}
                fields={schemaFields}
              />
            </div>
          )}

          <div className="flex justify-end gap-3 pt-4 border-t">
            <Button type="button" variant="secondary" onClick={onClose} disabled={isLoading}>
              Cancel
            </Button>
            <Button type="submit" isLoading={isLoading} disabled={!!schemaError}>
              {collection ? 'Save Changes' : 'Create Collection'}
            </Button>
          </div>
        </form>
      </div>
    </div>
  )
}

function DeleteConfirmModal({
  collection,
  workspaceId,
  onClose,
  onConfirm,
}: {
  collection: Collection
  workspaceId: string
  onClose: () => void
  onConfirm: () => void
}) {
  const [isLoading, setIsLoading] = useState(false)
  const [error, setError] = useState<string | null>(null)
  const [confirmName, setConfirmName] = useState('')

  const handleDelete = async () => {
    if (confirmName !== collection.name) {
      setError('Collection name does not match')
      return
    }

    setIsLoading(true)
    setError(null)

    try {
      await apiClient.delete(`/workspaces/${workspaceId}/collections/${collection.name}`)
      onConfirm()
    } catch (err) {
      setError(err instanceof Error ? err.message : 'Failed to delete collection')
      setIsLoading(false)
    }
  }

  return (
    <div className="fixed inset-0 z-50 flex items-center justify-center bg-black/50">
      <div className="w-full max-w-md rounded-lg bg-white p-6 shadow-xl">
        <h2 className="text-xl font-semibold text-gray-900">Delete Collection</h2>
        <p className="mt-2 text-gray-600">
          This will permanently delete the collection <strong>{collection.name}</strong> and all its
          documents. This action cannot be undone.
        </p>

        <div className="mt-4">
          <label className="mb-1.5 block text-sm font-medium text-gray-700">
            Type <strong>{collection.name}</strong> to confirm
          </label>
          <Input
            value={confirmName}
            onChange={(e) => setConfirmName(e.target.value)}
            placeholder={collection.name}
          />
        </div>

        {error && (
          <div className="mt-4 rounded-lg bg-red-50 px-4 py-3 text-sm text-red-700">{error}</div>
        )}

        <div className="mt-6 flex justify-end gap-3">
          <Button type="button" variant="secondary" onClick={onClose} disabled={isLoading}>
            Cancel
          </Button>
          <Button
            type="button"
            variant="danger"
            onClick={handleDelete}
            isLoading={isLoading}
            disabled={confirmName !== collection.name}
          >
            Delete Collection
          </Button>
        </div>
      </div>
    </div>
  )
}

function Collections() {
  const navigate = useNavigate()
  const { currentWorkspace } = useWorkspace()
  const { user } = useAuth()
  const [collections, setCollections] = useState<Collection[]>([])
  const [groups, setGroups] = useState<Group[]>([])
  const [filteredCollections, setFilteredCollections] = useState<Collection[]>([])
  const [isLoading, setIsLoading] = useState(true)
  const [error, setError] = useState<string | null>(null)
  const [searchQuery, setSearchQuery] = useState('')
  const [showCreateModal, setShowCreateModal] = useState(false)
  const [editingCollection, setEditingCollection] = useState<Collection | null>(null)
  const [deletingCollection, setDeletingCollection] = useState<Collection | null>(null)

  const isSuperadmin = user?.is_superadmin === true

  const fetchCollections = useCallback(async () => {
    if (!currentWorkspace) {
      setCollections([])
      setIsLoading(false)
      return
    }

    setIsLoading(true)
    setError(null)
    try {
      let url = `/workspaces/${currentWorkspace.id}/collections`
      // Always include system collections for superadmins
      if (isSuperadmin) {
        url += '?include_system=true'
      }
      const response = await apiClient.get<{ collections: Collection[] }>(url)
      setCollections(response.collections || [])
    } catch (err) {
      setError(err instanceof Error ? err.message : 'Failed to fetch collections')
    } finally {
      setIsLoading(false)
    }
  }, [currentWorkspace, isSuperadmin])

  const fetchGroups = useCallback(async () => {
    if (!currentWorkspace) {
      setGroups([])
      return
    }

    try {
      const response = await apiClient.get<{ groups: Group[] }>(
        `/workspaces/${currentWorkspace.id}/groups`
      )
      setGroups(response.groups || [])
    } catch {
      // Silently fail - groups are optional for field permissions
    }
  }, [currentWorkspace])

  useEffect(() => {
    fetchCollections()
    fetchGroups()
  }, [fetchCollections, fetchGroups])

  useEffect(() => {
    const query = searchQuery.toLowerCase()
    setFilteredCollections(collections.filter((c) => c.name.toLowerCase().includes(query)))
  }, [collections, searchQuery])

  const handleSave = () => {
    setShowCreateModal(false)
    setEditingCollection(null)
    fetchCollections()
  }

  const handleDelete = () => {
    setDeletingCollection(null)
    fetchCollections()
  }

  const getFieldPermissionCount = (collection: Collection): number => {
    return collection.settings?.field_permissions?.length || 0
  }

  if (!currentWorkspace) {
    return (
      <div className="space-y-6">
        <div>
          <h1 className="text-2xl font-bold text-gray-900">Collections</h1>
          <p className="mt-1 text-gray-600">Manage your data collections</p>
        </div>
        <div className="rounded-lg bg-yellow-50 p-6 text-center">
          <p className="text-yellow-800">Please select a workspace to manage collections.</p>
        </div>
      </div>
    )
  }

  return (
    <div className="space-y-6">
      <div className="flex flex-col gap-4 sm:flex-row sm:items-center sm:justify-between">
        <div>
          <h1 className="text-2xl font-bold text-gray-900">Collections</h1>
          <p className="mt-1 text-gray-600">Manage collections in {currentWorkspace.name}</p>
        </div>
        <Button onClick={() => setShowCreateModal(true)}>
          <svg className="-ml-1 mr-2 h-5 w-5" fill="none" viewBox="0 0 24 24" stroke="currentColor">
            <path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M12 4v16m8-8H4" />
          </svg>
          Create Collection
        </Button>
      </div>

      {/* Search */}
      <div className="max-w-md">
        <Input
          type="search"
          placeholder="Search collections..."
          value={searchQuery}
          onChange={(e) => setSearchQuery(e.target.value)}
        />
      </div>

      {/* Error state */}
      {error && <div className="rounded-lg bg-red-50 px-4 py-3 text-sm text-red-700">{error}</div>}

      {/* Loading state */}
      {isLoading && (
        <div className="flex items-center justify-center py-12">
          <svg
            className="h-8 w-8 animate-spin text-primary-600"
            xmlns="http://www.w3.org/2000/svg"
            fill="none"
            viewBox="0 0 24 24"
          >
            <circle
              className="opacity-25"
              cx="12"
              cy="12"
              r="10"
              stroke="currentColor"
              strokeWidth="4"
            />
            <path
              className="opacity-75"
              fill="currentColor"
              d="M4 12a8 8 0 018-8V0C5.373 0 0 5.373 0 12h4zm2 5.291A7.962 7.962 0 014 12H0c0 3.042 1.135 5.824 3 7.938l3-2.647z"
            />
          </svg>
        </div>
      )}

      {/* Collection list */}
      {!isLoading && !error && (
        <div className="overflow-hidden rounded-lg bg-white shadow">
          {filteredCollections.length === 0 ? (
            <div className="px-6 py-12 text-center">
              <p className="text-gray-500">
                {searchQuery ? 'No collections match your search' : 'No collections found'}
              </p>
            </div>
          ) : (
            <table className="min-w-full divide-y divide-gray-200">
              <thead className="bg-gray-50">
                <tr>
                  <th className="px-6 py-3 text-left text-xs font-medium uppercase tracking-wider text-gray-500">
                    Name
                  </th>
                  <th className="px-6 py-3 text-left text-xs font-medium uppercase tracking-wider text-gray-500">
                    Type
                  </th>
                  <th className="px-6 py-3 text-left text-xs font-medium uppercase tracking-wider text-gray-500">
                    Documents
                  </th>
                  <th className="px-6 py-3 text-left text-xs font-medium uppercase tracking-wider text-gray-500">
                    Field Rules
                  </th>
                  <th className="px-6 py-3 text-left text-xs font-medium uppercase tracking-wider text-gray-500">
                    Created
                  </th>
                  <th className="px-6 py-3 text-right text-xs font-medium uppercase tracking-wider text-gray-500">
                    Actions
                  </th>
                </tr>
              </thead>
              <tbody className="divide-y divide-gray-200 bg-white">
                {filteredCollections.map((collection) => (
                  <tr key={collection.name} className="hover:bg-gray-50">
                    <td className="whitespace-nowrap px-6 py-4">
                      <div className="flex items-center gap-2">
                        <svg
                          className="h-5 w-5 text-gray-400"
                          fill="none"
                          viewBox="0 0 24 24"
                          stroke="currentColor"
                        >
                          <path
                            strokeLinecap="round"
                            strokeLinejoin="round"
                            strokeWidth={2}
                            d="M19 11H5m14 0a2 2 0 012 2v6a2 2 0 01-2 2H5a2 2 0 01-2-2v-6a2 2 0 012-2m14 0V9a2 2 0 00-2-2M5 11V9a2 2 0 012-2m0 0V5a2 2 0 012-2h6a2 2 0 012 2v2M7 7h10"
                          />
                        </svg>
                        <span className="font-medium text-gray-900">{collection.name}</span>
                      </div>
                    </td>
                    <td className="whitespace-nowrap px-6 py-4">
                      {collection.is_system ? (
                        <span className="inline-flex rounded-full bg-purple-100 px-2 py-0.5 text-xs font-medium text-purple-800">
                          System
                        </span>
                      ) : (
                        <span className="inline-flex rounded-full bg-gray-100 px-2 py-0.5 text-xs font-medium text-gray-600">
                          User
                        </span>
                      )}
                    </td>
                    <td className="whitespace-nowrap px-6 py-4 text-sm text-gray-500">
                      {collection.document_count ?? '-'}
                    </td>
                    <td className="whitespace-nowrap px-6 py-4 text-sm text-gray-500">
                      {getFieldPermissionCount(collection) > 0 ? (
                        <span className="inline-flex items-center rounded-full bg-yellow-100 px-2 py-0.5 text-xs font-medium text-yellow-800">
                          {getFieldPermissionCount(collection)} rules
                        </span>
                      ) : (
                        <span className="text-gray-400">-</span>
                      )}
                    </td>
                    <td className="whitespace-nowrap px-6 py-4 text-sm text-gray-500">
                      {new Date(collection.created_at).toLocaleDateString()}
                    </td>
                    <td className="whitespace-nowrap px-6 py-4 text-right">
                      <div className="flex justify-end gap-2">
                        <button
                          onClick={() => navigate(`/collections/${collection.name}`)}
                          className="rounded px-3 py-1 text-sm text-gray-600 hover:bg-gray-100"
                          title="View documents"
                        >
                          Documents
                        </button>
                        <button
                          onClick={() => setEditingCollection(collection)}
                          className="rounded px-3 py-1 text-sm text-primary-600 hover:bg-primary-50"
                          disabled={collection.is_system}
                          title={
                            collection.is_system
                              ? 'Cannot edit system collections'
                              : 'Edit'
                          }
                        >
                          Edit
                        </button>
                        <button
                          onClick={() => setDeletingCollection(collection)}
                          className="rounded px-3 py-1 text-sm text-red-600 hover:bg-red-50 disabled:cursor-not-allowed disabled:opacity-50"
                          disabled={collection.is_system}
                          title={
                            collection.is_system
                              ? 'Cannot delete system collections'
                              : 'Delete'
                          }
                        >
                          Delete
                        </button>
                      </div>
                    </td>
                  </tr>
                ))}
              </tbody>
            </table>
          )}
        </div>
      )}

      {/* Modals */}
      {showCreateModal && (
        <CollectionModal
          collection={null}
          workspaceId={currentWorkspace.id}
          availableGroups={groups}
          onClose={() => setShowCreateModal(false)}
          onSave={handleSave}
        />
      )}
      {editingCollection && !editingCollection.settings?.is_system && (
        <CollectionModal
          collection={editingCollection}
          workspaceId={currentWorkspace.id}
          availableGroups={groups}
          onClose={() => setEditingCollection(null)}
          onSave={handleSave}
        />
      )}
      {deletingCollection && !deletingCollection.settings?.is_system && (
        <DeleteConfirmModal
          collection={deletingCollection}
          workspaceId={currentWorkspace.id}
          onClose={() => setDeletingCollection(null)}
          onConfirm={handleDelete}
        />
      )}
    </div>
  )
}

export default Collections
