/** * filekorolheader: 企业管理 - 企业信息管理与维护页面 * 功能:企业列表查询、详情查看、状态管理、分页筛选 * 路径:/central-config/tenant/enterprise-management * 规范:遵循crop-x/docs/开发项目规范.md,使用useReducer状态管理,API集成,shadcn语义化样式 */ 'use client'; import { useReducer, useEffect, useMemo } from 'react'; import { Card } from '@/components/ui/card'; import { Button } from '@/components/ui/button'; import { Badge } from '@/components/ui/badge'; import { Input } from '@/components/ui/input'; import { Label } from '@/components/ui/label'; import { Dialog, DialogContent, DialogHeader, DialogTitle, DialogDescription, DialogFooter } from '@/components/ui/dialog'; import { AlertDialog, AlertDialogAction, AlertDialogCancel, AlertDialogContent, AlertDialogDescription, AlertDialogFooter, AlertDialogHeader, AlertDialogTitle } from '@/components/ui/alert-dialog'; import { Table, TableBody, TableCell, TableHead, TableHeader, TableRow } from '@/components/ui/table'; import { Tabs, TabsContent, TabsList, TabsTrigger } from '@/components/ui/tabs'; import { ScrollArea } from '@/components/ui/scroll-area'; import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from '@/components/ui/select'; import { Building2, Eye, Power, PowerOff, Search, FileText, CreditCard, User, RefreshCw, AlertCircle, ChevronLeft, ChevronRight, Plus } from 'lucide-react'; import { toast } from 'sonner'; import { enterpriseReducer, initialState, EnterpriseState, EnterpriseAction } from './components/enterpriseReducer'; import { fetchTenants, transformTenantData, enableTenant, disableTenant, createEnterprise, TenantsQueryParams, Enterprise } from './components/enterpriseApi'; import { CreateEnterpriseDialog } from './components/CreateEnterpriseDialog'; // Utility functions const getStatusBadge = (status: 'active' | 'inactive') => { if (status === 'active') { return 启用; } return 禁用; }; const getAuditStatusBadge = (auditStatus: Enterprise['auditStatus']) => { switch (auditStatus) { case 'draft': return 草稿; case 'pending': return 待审核; case 'approved': return 审核通过; case 'rejected': return 已拒绝; default: return 草稿; } }; export default function EnterpriseManagement() { const [state, dispatch] = useReducer(enterpriseReducer, initialState); // 加载企业数据 const loadEnterprises = async (resetPage = false) => { try { dispatch({ type: 'SET_LOADING', payload: true }); const params: TenantsQueryParams = { search: state.filters.search || undefined, audit_status: state.filters.audit_status || undefined, page: resetPage ? 1 : state.pagination.page, size: state.pagination.size, order_by: state.sortBy, sort_order: state.sortOrder, }; const response = await fetchTenants(params); const transformedData = response.data.map(transformTenantData); console.log('API Response:', response); console.log('Transformed Data:', transformedData); dispatch({ type: 'SET_ENTERPRISES', payload: { data: transformedData, pagination: { page: response.page, size: response.size, total: response.total, totalPages: response.total_pages, hasNext: response.has_next, hasPrev: response.has_prev, } } }); } catch (error) { console.error('Failed to load enterprises:', error); const errorMessage = error instanceof Error ? error.message : '加载企业数据失败'; dispatch({ type: 'SET_ERROR', payload: errorMessage }); toast.error(errorMessage); } }; // 初始加载 useEffect(() => { loadEnterprises(true); }, [state.filters.search, state.filters.audit_status, state.sortBy, state.sortOrder]); // 分页加载 useEffect(() => { if (state.pagination.page > 1) { loadEnterprises(false); } }, [state.pagination.page]); // 计算统计数据 const stats = useMemo(() => ({ total: state.enterprises.length, active: state.enterprises.filter(e => e.status === 'active').length, inactive: state.enterprises.filter(e => e.status === 'inactive').length, }), [state.enterprises]); // 事件处理器 const handleSearch = (value: string) => { dispatch({ type: 'SET_FILTERS', payload: { search: value } }); }; const handleAuditStatusFilter = (value: string) => { dispatch({ type: 'SET_FILTERS', payload: { audit_status: value === 'all' ? '' : value } }); }; const handleSort = (sortBy?: string) => { const newSortOrder = state.sortBy === sortBy && state.sortOrder === 'desc' ? 'asc' : 'desc'; dispatch({ type: 'SET_SORT', payload: { sortBy, sortOrder: newSortOrder } }); }; const handlePageChange = (page: number) => { // 边界检查,确保页码在有效范围内 if (page < 1) { page = 1; } else if (page > state.pagination.totalPages && state.pagination.totalPages > 0) { page = state.pagination.totalPages; } dispatch({ type: 'SET_PAGINATION', payload: { page } }); }; const handleRefresh = () => { dispatch({ type: 'REFRESH_DATA' }); loadEnterprises(true); toast.success('数据已刷新'); }; const handleView = (enterprise: Enterprise) => { dispatch({ type: 'SET_SELECTED_ENTERPRISE', payload: enterprise }); dispatch({ type: 'TOGGLE_VIEW_DIALOG', payload: true }); }; const handleStatusChange = (enterprise: Enterprise, action: 'enable' | 'disable') => { dispatch({ type: 'SET_SELECTED_ENTERPRISE', payload: enterprise }); dispatch({ type: 'SET_STATUS_ACTION', payload: action }); dispatch({ type: 'TOGGLE_STATUS_DIALOG', payload: true }); }; const handleCreateNew = () => { dispatch({ type: 'RESET_FORM_DATA' }); dispatch({ type: 'TOGGLE_ADD_DIALOG', payload: true }); }; const handleCreateSuccess = () => { // 创建成功后刷新数据 loadEnterprises(true); }; const confirmStatusChange = async () => { if (!state.selectedEnterprise) return; try { dispatch({ type: 'SET_LOADING', payload: true }); const tenantId = state.selectedEnterprise.id; let updatedTenant; if (state.statusAction === 'enable') { updatedTenant = await enableTenant(tenantId); toast.success('企业已启用'); } else { updatedTenant = await disableTenant(tenantId); toast.success('企业已禁用'); } // 验证返回的数据是否正确更新了状态 console.log('API返回的更新数据:', updatedTenant); // 更新本地状态 const updatedEnterprise = transformTenantData(updatedTenant); dispatch({ type: 'SET_ENTERPRISES', payload: { data: state.enterprises.map(ent => ent.id === tenantId ? updatedEnterprise : ent ), pagination: state.pagination } }); dispatch({ type: 'TOGGLE_STATUS_DIALOG', payload: false }); // 不需要立即刷新,因为本地状态已经更新 // 如果用户需要看到最新数据,可以手动点击刷新按钮 } catch (error) { console.error('Status change failed:', error); const errorMessage = error instanceof Error ? error.message : '状态更新失败'; toast.error(errorMessage); } finally { dispatch({ type: 'SET_LOADING', payload: false }); } }; return (
{/* Page Header */}

企业管理

管理平台所有企业信息,支持查询、查看详情、启用/禁用企业

智能查询 状态管理 详情查看
{/* Statistics Cards */}
企业总数
{state.pagination.total}
全部企业数量
启用企业
{stats.active}
正常运营中
禁用企业
{stats.inactive}
已暂停使用
{/* Enterprise List */}

企业列表

handleSearch(e.target.value)} className="pl-10 w-64" />
{/* Error Display */} {state.error && (
{state.error}
)} {/* Loading State */} {state.loading && (

加载中...

)} {/* Data Table */} {!state.loading && !state.error && ( <>
handleSort('tenant_code')} > 企业编码 {state.sortBy === 'tenant_code' && ( {state.sortOrder === 'asc' ? '↑' : '↓'} )} handleSort('company_name')} > 企业名称 {state.sortBy === 'company_name' && ( {state.sortOrder === 'asc' ? '↑' : '↓'} )} 企业类型 登记人 联系电话 handleSort('created_at')} > 创建时间 {state.sortBy === 'created_at' && ( {state.sortOrder === 'asc' ? '↑' : '↓'} )} 审核状态 状态 操作 {state.enterprises.map((enterprise) => ( {enterprise.code}
{enterprise.name}
{enterprise.type} {enterprise.registrant || '-'} {enterprise.contactPhone || '-'} {enterprise.createdAt} {getAuditStatusBadge(enterprise.auditStatus)} {getStatusBadge(enterprise.status)}
{enterprise.status === 'active' ? ( ) : ( )}
))}
{state.enterprises.length === 0 && (

暂无企业数据

)} {/* Pagination */} {state.pagination.totalPages > 1 && (
显示第 {state.pagination.page} 页,共 {state.pagination.totalPages} 页 总计 {state.pagination.total} 条记录
{state.pagination.page} / {state.pagination.totalPages}
)} )}
{/* View Enterprise Details Dialog */} dispatch({ type: 'TOGGLE_VIEW_DIALOG', payload: open })}>
企业详情 {state.selectedEnterprise && (
{getAuditStatusBadge(state.selectedEnterprise.auditStatus)} {getStatusBadge(state.selectedEnterprise.status)}
)}
查看企业的详细信息
{state.selectedEnterprise && ( 基本信息 其他信息 开户信息 法人信息 {/* Basic Information */}
{state.selectedEnterprise.name}
{state.selectedEnterprise.code}
{state.selectedEnterprise.type}
{state.selectedEnterprise.province || '-'} {state.selectedEnterprise.city || ''} {state.selectedEnterprise.district || ''}
{state.selectedEnterprise.address || '-'}
{state.selectedEnterprise.registrant || '-'}
{state.selectedEnterprise.contactPhone || '-'}
{/* Other Information */}
{state.selectedEnterprise.companySize || '-'}
{state.selectedEnterprise.registeredCapital || '-'}
{state.selectedEnterprise.establishmentDate || '-'}
{state.selectedEnterprise.invoiceType || '-'}
{state.selectedEnterprise.socialCreditCode ? ( {state.selectedEnterprise.socialCreditCode} ) : '-'}
{state.selectedEnterprise.businessScope || '-'}
{state.selectedEnterprise.submitTime || '-'}
{state.selectedEnterprise.auditTime || '-'}
{/* Bank Information */}
{state.selectedEnterprise.bankAccount ? ( {state.selectedEnterprise.bankAccount} ) : '-'}
{state.selectedEnterprise.bankName || '-'}
{state.selectedEnterprise.bankFullName || '-'}
{state.selectedEnterprise.bankAddress || '-'}
{/* Legal Person Information */}
{state.selectedEnterprise.legalPerson || '-'}
{state.selectedEnterprise.registrant || '-'}
{state.selectedEnterprise.auditor || '-'}
{state.selectedEnterprise.auditComment || '-'}
)}
{/* Status Change Confirmation Dialog */} dispatch({ type: 'TOGGLE_STATUS_DIALOG', payload: open })}> 确认{state.statusAction === 'enable' ? '启用' : '禁用'}企业 {state.statusAction === 'enable' ? ( <> 启用企业 {state.selectedEnterprise?.name} 后,该企业用户将恢复正常登录和使用权限。 ) : ( <> 禁用企业 {state.selectedEnterprise?.name} 后,该企业所有用户将无法登录系统。此操作不会删除企业数据,可随时重新启用。 )} 取消 确认{state.statusAction === 'enable' ? '启用' : '禁用'} {/* Create Enterprise Dialog */} dispatch({ type: 'TOGGLE_ADD_DIALOG', payload: open })} onSuccess={handleCreateSuccess} />
); }