import { PlusOutlined, SearchOutlined } from '@ant-design/icons';
import { ProCard } from '@ant-design/pro-components';
import {
  App,
  Button,
  Checkbox,
  Drawer,
  Form,
  Input,
  Modal,
  Popconfirm,
  Select,
  Space,
  Switch,
  Table,
  Tree,
  Typography,
} from 'antd';
import type { ColumnsType } from 'antd/es/table';
import { useMemo, useState } from 'react';

import { buttonPermissionOptions, initialRoles, menuPermissionTree, type RoleItem } from './mock';

interface RoleFormValues {
  name: string;
  code: string;
  description: string;
  enabled: boolean;
}

export default function RoleManagement() {
  const { message } = App.useApp();
  const [form] = Form.useForm<RoleFormValues>();
  const [roles, setRoles] = useState(initialRoles);
  const [keyword, setKeyword] = useState('');
  const [enabled, setEnabled] = useState<boolean>();
  const [formOpen, setFormOpen] = useState(false);
  const [editing, setEditing] = useState<RoleItem>();
  const [permissionRole, setPermissionRole] = useState<RoleItem>();
  const [menuKeys, setMenuKeys] = useState<string[]>([]);
  const [buttonKeys, setButtonKeys] = useState<string[]>([]);

  const filteredRoles = useMemo(() => {
    const normalized = keyword.trim().toLowerCase();
    return roles.filter(role => {
      const matchesKeyword =
        !normalized || role.name.toLowerCase().includes(normalized) || role.code.toLowerCase().includes(normalized);
      return matchesKeyword && (enabled === undefined || role.enabled === enabled);
    });
  }, [enabled, keyword, roles]);

  const openCreate = () => {
    setEditing(undefined);
    form.setFieldsValue({ name: '', code: '', description: '', enabled: true });
    setFormOpen(true);
  };

  const openEdit = (role: RoleItem) => {
    setEditing(role);
    form.setFieldsValue({
      name: role.name,
      code: role.code,
      description: role.description,
      enabled: role.enabled,
    });
    setFormOpen(true);
  };

  const closeForm = () => {
    setFormOpen(false);
    setEditing(undefined);
    form.resetFields();
  };

  const saveRole = async () => {
    const values = await form.validateFields();
    if (editing) {
      setRoles(current =>
        current.map(role =>
          role.id === editing.id
            ? {
                ...role,
                ...values,
                updatedAt: '2026-07-26 02:30',
              }
            : role,
        ),
      );
      message.success('角色已更新');
    } else {
      setRoles(current => [
        ...current,
        {
          id: `role-${Date.now()}`,
          name: values.name,
          code: values.code,
          description: values.description,
          enabled: values.enabled,
          userCount: 0,
          updatedAt: '2026-07-26 02:30',
          menuKeys: ['dashboard'],
          buttonKeys: [],
        },
      ]);
      message.success('角色已添加');
    }
    closeForm();
  };

  const deleteRole = (role: RoleItem) => {
    setRoles(current => current.filter(item => item.id !== role.id));
    message.success('角色已删除');
  };

  const openPermission = (role: RoleItem) => {
    setPermissionRole(role);
    setMenuKeys(role.menuKeys);
    setButtonKeys(role.buttonKeys);
  };

  const savePermission = () => {
    if (!permissionRole) return;
    setRoles(current =>
      current.map(role =>
        role.id === permissionRole.id ? { ...role, menuKeys, buttonKeys, updatedAt: '2026-07-26 02:30' } : role,
      ),
    );
    message.success('权限已保存');
    setPermissionRole(undefined);
  };

  const columns: ColumnsType<RoleItem> = [
    { title: '角色名称', dataIndex: 'name', width: 140 },
    {
      title: '角色编码',
      dataIndex: 'code',
      width: 160,
      render: (value: string) => <Typography.Text code>{value}</Typography.Text>,
    },
    {
      title: '用户数',
      dataIndex: 'userCount',
      width: 90,
      align: 'right',
      render: (value: number) => `${value} 人`,
    },
    {
      title: '状态',
      dataIndex: 'enabled',
      width: 100,
      render: (value: boolean, record) => (
        <Switch
          size="small"
          checked={value}
          checkedChildren="启用"
          unCheckedChildren="禁用"
          aria-label={`${record.name}状态`}
          onChange={checked => {
            setRoles(current => current.map(item => (item.id === record.id ? { ...item, enabled: checked } : item)));
            message.success(checked ? '角色已启用' : '角色已禁用');
          }}
        />
      ),
    },
    { title: '描述', dataIndex: 'description', ellipsis: true },
    { title: '更新时间', dataIndex: 'updatedAt', width: 160 },
    {
      title: '操作',
      key: 'actions',
      width: 220,
      fixed: 'right',
      render: (_, record) => (
        <Space size={2}>
          <Button type="link" size="small" onClick={() => openPermission(record)}>
            权限配置
          </Button>
          <Button type="link" size="small" onClick={() => openEdit(record)}>
            编辑
          </Button>
          <Popconfirm title={`确定删除角色 ${record.name}？`} onConfirm={() => deleteRole(record)}>
            <Button type="link" danger size="small">
              删除
            </Button>
          </Popconfirm>
        </Space>
      ),
    },
  ];

  return (
    <>
      <ProCard variant="outlined">
        <Space vertical size={16} style={{ width: '100%' }}>
          <Space style={{ width: '100%', justifyContent: 'space-between' }} align="start">
            <div>
              <Typography.Title level={5} style={{ margin: 0 }}>
                角色管理
              </Typography.Title>
              <Typography.Text type="secondary">定义角色并配置可访问的菜单与操作权限。</Typography.Text>
            </div>
            <Button type="primary" icon={<PlusOutlined />} onClick={openCreate}>
              新增角色
            </Button>
          </Space>

          <Space wrap>
            <Input
              allowClear
              prefix={<SearchOutlined />}
              placeholder="搜索角色名称"
              style={{ width: 240 }}
              value={keyword}
              onChange={event => setKeyword(event.target.value)}
            />
            <Select
              allowClear
              placeholder="全部状态"
              style={{ width: 130 }}
              options={[
                { label: '已启用', value: true },
                { label: '已禁用', value: false },
              ]}
              value={enabled}
              onChange={setEnabled}
            />
          </Space>

          <Table<RoleItem>
            rowKey="id"
            columns={columns}
            dataSource={filteredRoles}
            scroll={{ x: 1000 }}
            pagination={{ pageSize: 10, showSizeChanger: true, showTotal: total => `共 ${total} 条` }}
          />
        </Space>
      </ProCard>

      <Modal
        open={formOpen}
        title={editing ? '编辑角色' : '新增角色'}
        okText="保存"
        cancelText="取消"
        onOk={saveRole}
        onCancel={closeForm}
      >
        <Form<RoleFormValues> form={form} layout="vertical" requiredMark="optional">
          <Form.Item label="角色名称" name="name" rules={[{ required: true, message: '请输入角色名称' }]}>
            <Input placeholder="例如 运营" />
          </Form.Item>
          <Form.Item
            label="角色编码"
            name="code"
            rules={[
              { required: true, message: '请输入角色编码' },
              { pattern: /^ROLE_[A-Z0-9_]+$/, message: '格式如 ROLE_OPERATOR' },
            ]}
          >
            <Input disabled={Boolean(editing)} placeholder="例如 ROLE_OPERATOR" />
          </Form.Item>
          <Form.Item label="描述" name="description">
            <Input.TextArea rows={2} placeholder="请输入角色描述" />
          </Form.Item>
          <Form.Item label="状态" name="enabled" valuePropName="checked">
            <Switch checkedChildren="启用" unCheckedChildren="禁用" />
          </Form.Item>
        </Form>
      </Modal>

      <Drawer
        open={Boolean(permissionRole)}
        title={`配置权限 - ${permissionRole?.name ?? ''}`}
        size={420}
        onClose={() => setPermissionRole(undefined)}
        footer={
          <Space style={{ width: '100%', justifyContent: 'flex-end' }}>
            <Button onClick={() => setPermissionRole(undefined)}>取消</Button>
            <Button type="primary" onClick={savePermission}>
              保存
            </Button>
          </Space>
        }
      >
        <Space vertical size={20} style={{ width: '100%' }}>
          <div>
            <Typography.Title level={5} style={{ marginTop: 0 }}>
              菜单权限
            </Typography.Title>
            <Tree
              checkable
              checkStrictly
              defaultExpandAll
              checkedKeys={menuKeys}
              treeData={menuPermissionTree}
              fieldNames={{ title: 'title', key: 'key', children: 'children' }}
              onCheck={checked => {
                const keys = Array.isArray(checked) ? checked : checked.checked;
                setMenuKeys(keys.map(String));
              }}
            />
          </div>
          <div>
            <Typography.Title level={5}>按钮权限</Typography.Title>
            <Checkbox.Group
              options={buttonPermissionOptions}
              value={buttonKeys}
              onChange={values => setButtonKeys(values.map(String))}
              style={{ display: 'flex', flexDirection: 'column', gap: 8 }}
            />
          </div>
        </Space>
      </Drawer>
    </>
  );
}
