import { useEffect, useMemo, useState } from 'react'
import { toast } from 'react-hot-toast'
import {
  createTransaction,
  deleteTransaction,
  getAllTransactions,
  updateTransaction,

} from '../services/transactionsService'
import { getAllProducts } from '../services/productsService'
import { getAllWarehouses } from '../services/warehousesService'
import Modal from '../components/common/Modal'
import TableShell from '../components/common/TableShell'
import { validateTransactionForm } from '../utils/validators'

export default function TransactionsPage() {
  const [loading, setLoading] = useState(true)
  const [transactions, setTransactions] = useState([])

  const [products, setProducts] = useState([])
  const [warehouses, setWarehouses] = useState([])

  const [form, setForm] = useState({
    product: '',
    warehouse: '',
    transactionDate: '',
    quantityMoved: 1,
    transactionType: 'Stock In',
  })
  const [formErrors, setFormErrors] = useState({})
  const [submitting, setSubmitting] = useState(false)

  const [editOpen, setEditOpen] = useState(false)
  const [editId, setEditId] = useState(null)
  const [editForm, setEditForm] = useState({ quantityMoved: 1, transactionType: 'Stock In' })
  const [editErrors, setEditErrors] = useState({})
  const [editLoading, setEditLoading] = useState(false)

  const columns = useMemo(
    () => [
      { header: 'Product', accessor: (t) => t.product?.productCode || t.product?.productName },
      { header: 'Warehouse', accessor: (t) => t.warehouse?.warehouseCode || t.warehouse?.warehouseName },
      { header: 'Date', accessor: (t) => (t.transactionDate ? new Date(t.transactionDate).toISOString().split('T')[0] : '') },
      { header: 'Type', accessor: (t) => t.transactionType },
      { header: 'Qty', accessor: (t) => t.quantityMoved },
    ],
    [],
  )

  const reload = async () => {
    const data = await getAllTransactions()
    setTransactions(Array.isArray(data) ? data : [])
  }

  useEffect(() => {
    const run = async () => {
      try {
        setLoading(true)
        const [p, w] = await Promise.all([getAllProducts(), getAllWarehouses()])
        setProducts(Array.isArray(p) ? p : [])
        setWarehouses(Array.isArray(w) ? w : [])
        await reload()
      } catch (err) {
        toast.error(err?.message || 'Failed to load transactions')
      } finally {
        setLoading(false)
      }
    }
    run()
  }, [])

  return (
    <div>
      <div className="flex items-start justify-between gap-4 mb-4">
        <div>
          <h2 className="text-2xl font-semibold">Transactions</h2>
          <p className="text-sm text-slate-400 mt-1">Stock in/out operations with validation and CRUD.</p>
        </div>
      </div>

      <div className="grid grid-cols-1 xl:grid-cols-5 gap-4">
        <div className="xl:col-span-2">
          <div className="rounded-2xl border border-white/10 bg-white/5 p-4 sticky top-4">
            <div className="text-sm font-semibold">Create Transaction</div>
            <div className="text-xs text-slate-400 mt-1 mb-4">Stock levels update automatically.</div>

            <form
              onSubmit={async (e) => {
                e.preventDefault()
                const nextErrors = validateTransactionForm({
                  ...form,
                  quantityMoved: form.quantityMoved,
                })
                setFormErrors(nextErrors)
                if (Object.keys(nextErrors).length > 0) return

                setSubmitting(true)
                try {
                  await createTransaction({
                    product: form.product,
                    warehouse: form.warehouse,
                    transactionDate: form.transactionDate || undefined,
                    quantityMoved: Number(form.quantityMoved),
                    transactionType: form.transactionType,
                  })
                  toast.success('Transaction created')
                  setForm({
                    product: '',
                    warehouse: '',
                    transactionDate: '',
                    quantityMoved: 1,
                    transactionType: 'Stock In',
                  })
                  setFormErrors({})
                  await reload()
                } catch (err) {
                  toast.error(err?.response?.data?.message || err?.message || 'Failed to create transaction')
                } finally {
                  setSubmitting(false)
                }
              }}
              className="space-y-3"
            >
              <SelectField
                label="Product"
                error={formErrors.product}
                value={form.product}
                onChange={(v) => setForm((s) => ({ ...s, product: v }))}
              >
                <option value="">Select product</option>
                {products.map((p) => (
                  <option key={p._id} value={p._id}>
                    {p.productCode} • {p.productName}
                  </option>
                ))}
              </SelectField>

              <SelectField
                label="Warehouse"
                error={formErrors.warehouse}
                value={form.warehouse}
                onChange={(v) => setForm((s) => ({ ...s, warehouse: v }))}
              >
                <option value="">Select warehouse</option>
                {warehouses.map((w) => (
                  <option key={w._id} value={w._id}>
                    {w.warehouseCode} • {w.warehouseName}
                  </option>
                ))}
              </SelectField>

              <div className="grid grid-cols-2 gap-3">
                <div>
                  <label className="block text-xs text-slate-300 font-medium mb-1">Transaction Date</label>
                  <input
                    type="date"
                    className="w-full rounded-xl border border-white/10 bg-black/20 px-3 py-2 text-sm outline-none focus:border-fuchsia-400/60"
                    value={form.transactionDate}
                    onChange={(e) => setForm((s) => ({ ...s, transactionDate: e.target.value }))}
                  />
                  {formErrors.transactionDate ? <p className="text-xs text-red-300 mt-1">{formErrors.transactionDate}</p> : null}
                </div>

                <div>
                  <label className="block text-xs text-slate-300 font-medium mb-1">Quantity Moved</label>
                  <input
                    type="number"
                    min={1}
                    className="w-full rounded-xl border border-white/10 bg-black/20 px-3 py-2 text-sm outline-none focus:border-fuchsia-400/60"
                    value={form.quantityMoved}
                    onChange={(e) => setForm((s) => ({ ...s, quantityMoved: e.target.value }))}
                  />
                  {formErrors.quantityMoved ? <p className="text-xs text-red-300 mt-1">{formErrors.quantityMoved}</p> : null}
                </div>
              </div>

              <SelectField
                label="Transaction Type"
                error={formErrors.transactionType}
                value={form.transactionType}
                onChange={(v) => setForm((s) => ({ ...s, transactionType: v }))}
              >
                <option value="Stock In">Stock In</option>
                <option value="Stock Out">Stock Out</option>
              </SelectField>

              <button
                type="submit"
                disabled={submitting}
                className="w-full rounded-xl bg-gradient-to-r from-purple-500 to-fuchsia-500 text-white py-2.5 text-sm font-semibold shadow-lg hover:opacity-95 disabled:opacity-60 disabled:cursor-not-allowed transition"
              >
                {submitting ? 'Creating...' : 'Create Transaction'}
              </button>
            </form>
          </div>
        </div>

        <div className="xl:col-span-3">
          <div className="rounded-2xl border border-white/10 bg-white/5 p-4">
            <div className="flex items-center justify-between gap-3 mb-4">
              <div>
                <div className="text-sm font-semibold">Transactions</div>
                <div className="text-xs text-slate-400 mt-1">Search, paginate, edit and delete.</div>
              </div>
            </div>

            <TableShell
              items={transactions}
              loading={loading}
              columns={columns}
              searchKeys={['transactionType', 'product', 'warehouse']}
              rowAction={(row) => (
                <div className="flex gap-2 justify-end">
                  <button
                    onClick={() => {
                      setEditId(row._id)
                      setEditForm({
                        quantityMoved: row.quantityMoved,
                        transactionType: row.transactionType,
                      })
                      setEditErrors({})
                      setEditOpen(true)
                    }}
                    className="text-xs font-semibold px-3 py-1.5 rounded-full border border-white/10 bg-black/20 hover:bg-white/10 transition"
                  >
                    Edit
                  </button>
                  <button
                    onClick={async () => {
                      try {
                        await deleteTransaction(row._id)
                        toast.success('Transaction deleted')
                        await reload()
                      } catch (err) {
                        toast.error(err?.message || 'Failed to delete transaction')
                      }
                    }}
                    className="text-xs font-semibold px-3 py-1.5 rounded-full border border-red-500/30 bg-red-500/10 text-red-200 hover:bg-red-500/15 transition"
                  >
                    Delete
                  </button>
                </div>
              )}
            />
          </div>
        </div>
      </div>

      <Modal
        open={editOpen}
        onClose={() => setEditOpen(false)}
        title="Edit Transaction"
      >
        <form
          className="space-y-3"
          onSubmit={async (e) => {
            e.preventDefault()
            const nextErrors = validateTransactionForm({
              product: form.product || undefined,
              warehouse: form.warehouse || undefined,
              transactionDate: undefined,
              quantityMoved: editForm.quantityMoved,
              transactionType: editForm.transactionType,
            })
            // only validate relevant fields
            const filteredErrors = {
              quantityMoved: nextErrors.quantityMoved,
              transactionType: nextErrors.transactionType,
            }
            setEditErrors(filteredErrors)
            if (Object.values(filteredErrors).filter(Boolean).length > 0) return

            setEditLoading(true)
            try {
              await updateTransaction(editId, {
                quantityMoved: Number(editForm.quantityMoved),
                transactionType: editForm.transactionType,
              })
              toast.success('Transaction updated')
              setEditOpen(false)
              await reload()
            } catch (err) {
              toast.error(err?.response?.data?.message || err?.message || 'Failed to update transaction')
            } finally {
              setEditLoading(false)
            }
          }}
        >
          <div>
            <label className="block text-xs text-slate-300 font-medium mb-1">Quantity Moved</label>
            <input
              type="number"
              min={1}
              className="w-full rounded-xl border border-white/10 bg-black/20 px-3 py-2 text-sm outline-none focus:border-fuchsia-400/60"
              value={editForm.quantityMoved}
              onChange={(e) => setEditForm((s) => ({ ...s, quantityMoved: e.target.value }))}
            />
            {editErrors.quantityMoved ? <p className="text-xs text-red-300 mt-1">{editErrors.quantityMoved}</p> : null}
          </div>

          <div>
            <label className="block text-xs text-slate-300 font-medium mb-1">Transaction Type</label>
            <select
              className="w-full rounded-xl border border-white/10 bg-black/20 px-3 py-2 text-sm outline-none focus:border-fuchsia-400/60"
              value={editForm.transactionType}
              onChange={(e) => setEditForm((s) => ({ ...s, transactionType: e.target.value }))}
            >
              <option value="Stock In">Stock In</option>
              <option value="Stock Out">Stock Out</option>
            </select>
            {editErrors.transactionType ? <p className="text-xs text-red-300 mt-1">{editErrors.transactionType}</p> : null}
          </div>

          <div className="flex gap-2 justify-end pt-2">
            <button
              type="button"
              onClick={() => setEditOpen(false)}
              className="rounded-xl border border-white/10 bg-white/5 px-4 py-2 text-sm hover:bg-white/10 transition"
            >
              Cancel
            </button>
            <button
              type="submit"
              disabled={editLoading}
              className="rounded-xl bg-gradient-to-r from-purple-500 to-fuchsia-500 text-white px-4 py-2 text-sm font-semibold hover:opacity-95 disabled:opacity-60 transition"
            >
              {editLoading ? 'Saving...' : 'Save Changes'}
            </button>
          </div>
        </form>
      </Modal>
    </div>
  )
}

function SelectField({ label, error, value, onChange, children }) {
  return (
    <div>
      <label className="block text-xs text-slate-300 font-medium mb-1">{label}</label>
      <select
        value={value}
        onChange={(e) => onChange(e.target.value)}
        className="w-full rounded-xl border border-white/10 bg-black/20 px-3 py-2 text-sm outline-none focus:border-fuchsia-400/60"
      >
        {children}
      </select>
      {error ? <p className="text-xs text-red-300 mt-1">{error}</p> : null}
    </div>
  )
}

