# 引航计划和用户管理功能需求文档 ## 文档概述 本文档详细描述了引航计划管理和用户管理两个功能模块的需求、功能设计、接口规范和实现细节。 --- # 第一部分:引航计划管理 ## 功能概述 引航计划管理功能用于管理船舶的引航计划,包括引航计划的查询、导入、导出等操作。该功能支持从外部系统导入引航计划数据,并提供灵活的查询和导出功能。 ## 功能模块 ### 1. 引航计划查询 #### 1.1 查询条件 引航计划页面提供以下查询条件: | 查询条件 | 说明 | 数据类型 | 是否必填 | |---------|------|---------|---------| | 作业时间 | 计划时间范围 | 日期范围 | 否 | | 港区作业类型 | 本港计划/外港计划 | 下拉选择 | 否 | | 港口 | 港口名称 | 下拉选择 | 否 | | 英文船名 | 船舶英文名称 | 文本输入 | 否 | | 状态 | 未调度/已调度 | 下拉选择 | 否 | | 船公司 | 船舶所属公司 | 下拉选择 | 否 | | 吃水 | 船舶吃水范围(最小值-最大值) | 数值范围 | 否 | | 交通船 | 交通船名称 | 文本输入 | 否 | #### 1.2 查询操作 - **查询按钮**:根据输入的查询条件筛选引航计划列表 - **重置按钮**:清空所有查询条件并重新加载引航计划列表 - **展开/收起按钮**:控制查询条件的显示和隐藏 #### 1.3 默认查询条件 - **作业时间**:默认设置为当月1日0点到当月最后一天23:59:59 - **其他条件**:默认为空 #### 1.4 引航计划列表显示 引航计划列表以表格形式展示,包含以下字段: | 字段名称 | 说明 | 数据来源 | 排序支持 | |---------|------|---------|---------| | 序号 | 记录的顺序号 | 前端计算 | 否 | | 计划时间 | 引航计划时间 | Disp_PilotPlan.PlanTime | 是 | | 中文船名 | 船舶中文名称 | Bus_Ship.CnShipName | 是 | | 英文船名 | 船舶英文名称 | Bus_Ship.EnShipName | 是 | | 船公司 | 船舶所属公司 | Bus_CustomerCompany.CustomerName | 是 | | 国籍 | 船舶国籍 | Bus_Ship.Nation | 是 | | 船长 | 船舶长度(米) | Bus_Ship.ShipLength | 是 | | 吃水 | 船舶吃水深度(米) | Disp_PilotPlan.Deep | 是 | | 动态 | 引航动态类型 | Bus_PilotTypeSetting.PilotTypeName | 是 | | 起点泊位 | 起始泊位名称 | Disp_Berthage.BerthageName | 是 | | 终点泊位 | 终止泊位名称 | Disp_Berthage.BerthageName | 是 | | 主引 | 主引航员姓名 | Disp_Pilot.Name | 是 | | 交通船 | 交通船名称 | Disp_PilotPlan.Trafficboat | 是 | | 代理 | 代理公司名称 | Bus_CustomerCompany.CustomerName | 是 | | 港区作业类型 | 本港计划/外港计划 | 计算字段 | 是 | | 航道 | 航道名称 | Disp_Waterway.WaterwayName | 是 | | 状态 | 调度状态 | Disp_Dispatcher.RecordStatus | 是 | #### 1.5 分页功能 - 支持分页显示引航计划列表 - 可选择每页显示10、20、50、100条记录 - 支持跳转到指定页码 - 显示总记录数 - 支持列头排序(数据库级排序) ### 2. 引航计划导入 #### 2.1 导入按钮 在操作按钮区提供"导入引航计划"按钮,点击后弹出导入对话框。 #### 2.2 导入对话框 导入对话框包含以下内容: | 元素 | 说明 | |------|------| | 文本区域 | 用于粘贴引航计划数据,支持制表符分隔的格式 | | 取消按钮 | 关闭导入对话框 | | 解析数据按钮 | 解析粘贴的数据并显示预览 | #### 2.3 数据格式要求 导入数据必须符合以下格式: - **分隔符**:使用制表符(Tab)分隔各字段 - **表头**:必须包含以下表头(顺序固定) ``` 序号|计划时间|中文船名|英文船名|国籍(地区)|船长|吃水|动态|起点泊位|终点泊位|合作标记|引航机构|主引|主引2|副引|其它引水|代理|代理电话|交通船|航道|侧推|备注 ``` - **时间格式**:`yyyy-MM-dd HH:mm`(支持24:00格式,自动转换为次日00:00) - **必填字段**:序号、计划时间、中文船名、英文船名 #### 2.4 导入操作流程 1. 点击"导入引航计划"按钮打开导入对话框 2. 从外部系统复制引航计划数据 3. 粘贴到文本区域 4. 点击"解析数据"按钮 5. 系统解析数据并显示预览对话框 6. 在预览对话框中可以搜索和查看数据 7. 点击"确认导入"按钮完成导入 8. 导入成功后刷新引航计划列表 #### 2.5 预览对话框 预览对话框包含以下内容: | 元素 | 说明 | |------|------| | 记录数量 | 显示待导入的记录数量 | | 搜索框 | 支持按多个字段搜索预览数据 | | 数据表格 | 显示解析后的引航计划数据 | | 取消按钮 | 取消导入操作 | | 确认导入按钮 | 确认导入数据,显示导入记录数量 | #### 2.6 导入逻辑 - **重复检查**:通过计划时间和中文船名判断是否重复 - **已调度保护**:已调度的计划(RecordStatus > 1)不允许再次导入 - **数据更新**:如果存在未调度的重复记录,则更新该记录 - **数据新增**:如果不存在重复记录,则新增该记录 - **调度同步**:导入成功后自动同步到调度表(Disp_Dispatcher) - **关联数据处理**: - 自动创建或关联船舶信息(Bus_Ship) - 自动创建或关联泊位信息(Disp_Berthage) - 自动创建或关联引航员信息(Disp_Pilot) - 自动创建或关联航道信息(Disp_Waterway) - 自动创建或关联代理信息(Bus_CustomerCompany) - 自动创建或关联引航类型(Bus_PilotTypeSetting) ### 3. 引航计划导出 #### 3.1 导出按钮 在操作按钮区提供"导出Excel"按钮,点击后导出当前查询条件的引航计划数据。 #### 3.2 导出逻辑 - 导出当前查询条件下的所有引航计划数据 - 不受分页限制,导出全部符合条件的数据 - 导出格式为Excel(.xlsx) - 文件名:`引航计划数据.xlsx` - 包含列表中显示的所有字段 ### 4. 港区作业类型计算 #### 4.1 本港计划 以下港口属于本港计划: - 深圳港 - 蛇口港 - 赤湾港 - 妈湾港 - 盐田港 - 大铲湾港 #### 4.2 外港计划 除本港计划外的所有港口都属于外港计划。 ## 数据库设计 ### 相关表结构 #### Disp_PilotPlan表(引航计划表) | 字段名 | 类型 | 说明 | |-------|------|------| | PilotPlanId | varchar(36) | 引航计划ID(主键) | | PlanTime | datetime | 计划时间 | | ShipId | varchar(36) | 船舶ID | | PilotType | int | 引航类型ID | | FromBerthageId | varchar(36) | 起始泊位ID | | ToBerthageId | varchar(36) | 终止泊位ID | | MainPilotId | varchar(36) | 主引航员ID | | AssitPilotId | varchar(36) | 副引航员ID | | WaterwayId | varchar(36) | 航道ID | | AgencyId | varchar(36) | 代理ID | | Trafficboat | varchar(100) | 交通船 | | Deep | decimal(18,2) | 吃水 | | SideThruster | varchar(500) | 侧推 | | Remark | varchar(500) | 备注 | | RecordStatus | int | 记录状态 | | CreateTime | datetime | 创建时间 | | CreateUserID | varchar(36) | 创建人ID | | ModifyTime | datetime | 修改时间 | | ModifyUserID | varchar(36) | 修改人ID | #### Bus_Ship表(船舶表) | 字段名 | 类型 | 说明 | |-------|------|------| | ShipId | varchar(36) | 船舶ID(主键) | | CnShipName | varchar(100) | 船舶中文名称 | | EnShipName | varchar(100) | 船舶英文名称 | | Nation | varchar(50) | 国籍 | | ShipLength | decimal(18,2) | 船长 | | RecordStatus | int | 记录状态 | #### Disp_Berthage表(泊位表) | 字段名 | 类型 | 说明 | |-------|------|------| | BerthageId | varchar(36) | 泊位ID(主键) | | BerthageName | varchar(100) | 泊位名称 | | PortId | varchar(36) | 港口ID | | RecordStatus | int | 记录状态 | #### Disp_Pilot表(引航员表) | 字段名 | 类型 | 说明 | |-------|------|------| | PilotId | varchar(36) | 引航员ID(主键) | | Name | varchar(100) | 引航员姓名 | | RecordStatus | int | 记录状态 | #### Disp_Waterway表(航道表) | 字段名 | 类型 | 说明 | |-------|------|------| | WaterwayId | varchar(36) | 航道ID(主键) | | WaterwayName | varchar(100) | 航道名称 | | RecordStatus | int | 记录状态 | #### Bus_CustomerCompany表(客户公司表) | 字段名 | 类型 | 说明 | |-------|------|------| | CustomerCompanyId | varchar(36) | 客户公司ID(主键) | | CustomerName | varchar(200) | 客户公司名称 | | CustomerType | int | 客户类型(2=船公司) | | RecordStatus | int | 记录状态 | #### Disp_Dispatcher表(调度表) | 字段名 | 类型 | 说明 | |-------|------|------| | DispatcherId | varchar(36) | 调度ID(主键) | | PilotPlanId | varchar(36) | 引航计划ID | | WorkTime | datetime | 作业时间 | | StartTime | datetime | 开始时间 | | EndTime | datetime | 结束时间 | | PortId | varchar(36) | 港口ID | | FromBerthageId | varchar(36) | 起始泊位ID | | ToBerthageId | varchar(36) | 终止泊位ID | | ShipId | varchar(36) | 船舶ID | | Deep | decimal(18,2) | 吃水 | | AgencyId | varchar(36) | 代理ID | | PilotTypeId | int | 引航类型ID | | RecordStatus | int | 记录状态 | | CreateTime | datetime | 创建时间 | | CreateUserID | varchar(36) | 创建人ID | | ModifyTime | datetime | 修改时间 | | ModifyUserID | varchar(36) | 修改人ID | #### Bus_PilotTypeSetting表(引航类型设置表) | 字段名 | 类型 | 说明 | |-------|------|------| | PilotTypeId | int | 引航类型ID(主键) | | PilotTypeName | varchar(100) | 引航类型名称 | | Hours | decimal(18,2) | 作业时长(小时) | | RecordStatus | int | 记录状态 | ## 接口设计 ### 1. 查询引航计划列表 **接口地址**:`GET /api/pilot-plan/list` **请求参数**: | 参数名 | 类型 | 必填 | 说明 | |-------|------|------|------| | planTimeStart | String | 否 | 计划时间开始(yyyy-MM-dd) | | planTimeEnd | String | 否 | 计划时间结束(yyyy-MM-dd) | | portAreaOperationType | String | 否 | 港区作业类型(本港计划/外港计划) | | portId | String | 否 | 港口ID | | englishShipName | String | 否 | 英文船名(模糊查询) | | status | String | 否 | 状态(未调度/已调度) | | shipownerId | String | 否 | 船公司ID | | deepStart | Double | 否 | 吃水最小值 | | deepEnd | Double | 否 | 吃水最大值 | | trafficboat | String | 否 | 交通船(模糊查询) | | page | Integer | 是 | 页码 | | pageSize | Integer | 是 | 每页行数 | | sortBy | String | 否 | 排序字段 | | sortOrder | String | 否 | 排序方向(ASC/DESC) | **响应示例**: ```json { "content": [ { "index": 1, "pilotPlanId": "pilot-plan-id-1", "planTime": "2026-03-03 10:30:00", "deep": 8.5, "trafficboat": "交通船A", "pilotType": 1, "pilotTypeName": "进港", "fromBerthageId": "berthage-id-1", "toBerthageId": "berthage-id-2", "mainPilotId": "pilot-id-1", "agencyId": "agency-id-1", "waterwayId": "waterway-id-1", "shipId": "ship-id-1", "chineseShipName": "测试船1", "englishShipName": "TEST SHIP1", "nation": "中国", "shipLength": 100.0, "shipCompanyName": "船公司A", "fromBerthName": "1号泊位", "toBerthName": "2号泊位", "mainPilotName": "张三", "agencyName": "代理A", "waterwayName": "主航道", "portAreaOperationType": "本港计划", "status": "未调度" } ], "totalElements": 100 } ``` ### 2. 导入引航计划 **接口地址**:`POST /api/pilot-plan/import` **请求参数**: ```json [ { "serialNumber": "1", "planTime": "2026-03-03 10:30", "chineseShipName": "测试船1", "englishShipName": "TEST SHIP1", "nationality": "中国", "shipLength": 100, "draft": 8.5, "dynamic": "进港", "startBerth": "1号泊位", "endBerth": "2号泊位", "cooperationMark": "是", "pilotAgency": "引航公司A", "mainPilot": "张三", "secondaryPilot": "李四", "deputyPilot": "王五", "otherPilots": "赵六", "agent": "代理A", "agentPhone": "13800138001", "transportVessel": "交通船A", "waterway": "主航道", "sideThruster": "有", "remark": "无备注" } ] ``` **响应示例**: ```json { "success": true, "message": "导入成功", "importedCount": 10 } ``` ### 3. 导出引航计划 **接口地址**:`GET /api/pilot-plan/export` **请求参数**:与查询引航计划列表相同 **响应**:Excel文件下载 ### 4. 获取港口列表 **接口地址**:`GET /api/port/list` **响应示例**: ```json [ { "portId": "port-id-1", "portName": "深圳港" }, { "portId": "port-id-2", "portName": "蛇口港" } ] ``` ### 5. 获取船公司列表 **接口地址**:`GET /api/ship-company/list` **响应示例**: ```json [ { "companyId": "company-id-1", "companyName": "船公司A" }, { "companyId": "company-id-2", "companyName": "船公司B" } ] ``` ## 权限控制 ### 功能权限代码 | 功能 | 权限代码 | |------|---------| | 查询引航计划列表 | 0104 | | 导入引航计划 | 010401 | | 导出引航计划 | 010403 | ### 权限验证 - 所有接口都需要进行权限验证 - 前端按钮根据用户权限代码显示或隐藏 - 后端接口使用@RequirePermission注解进行权限验证 ## 界面设计 ### 页面布局 1. **页面标题**:显示"引航计划管理" 2. **查询条件区**:包含多行查询条件和查询、重置、展开/收起按钮 3. **操作按钮区**:包含导入引航计划、导出Excel按钮 4. **表格区**:显示引航计划列表 5. **分页区**:显示分页控件 ### 响应式设计 - 表格高度自适应屏幕高度:`calc(100vh - 469px)` - 表格宽度自适应屏幕宽度:`calc(100vw - 330px)` - 支持横向滚动条(当表格内容超出屏幕宽度时) - 支持纵向滚动条(当表格内容超出可视区域时) - 查询条件支持展开/收起功能 --- # 第二部分:用户管理 ## 功能概述 用户管理功能用于管理系统中的用户信息,包括用户的查询、新增、编辑、删除和密码重置等操作。 ## 功能模块 ### 1. 用户查询 #### 1.1 查询条件 用户管理页面提供以下查询条件: | 查询条件 | 说明 | 数据类型 | 是否必填 | |---------|------|---------|---------| | 用户名 | 用户的名称 | 文本输入 | 否 | | 账号 | 用户的登录账号 | 文本输入 | 否 | | 状态 | 用户的状态 | 下拉选择 | 否 | #### 1.2 查询操作 - **查询按钮**:根据输入的查询条件筛选用户列表 - **重置按钮**:清空所有查询条件并重新加载用户列表 #### 1.3 用户列表显示 用户列表以表格形式展示,包含以下字段: | 字段名称 | 说明 | 数据来源 | 排序支持 | |---------|------|---------|---------| | 勾选列 | 复选框,用于批量选择用户 | - | 否 | | 序号 | 记录的顺序号,支持跨页顺序 | 前端计算 | 否 | | 用户名 | 用户的名称 | Sys_User.Name | 是 | | 账号 | 用户的登录账号 | Sys_User.LoginID | 是 | | 用户角色 | 用户关联的角色 | 通过Sys_UserRole关联Sys_Role | 是 | | 企业微信账号 | 用户的企业微信账号 | Sys_User.WeChatUserId | 是 | | 状态 | 用户的状态 | Sys_User.RecordStatus | 是 | | 操作 | 操作按钮列 | - | 否 | #### 1.4 分页功能 - 支持分页显示用户列表 - 可选择每页显示10、20、50、100条记录 - 支持跳转到指定页码 - 显示总记录数 - 支持列头排序(数据库级排序) ### 2. 用户新增 #### 2.1 新增按钮 在操作按钮区提供"新增"按钮,点击后弹出新增用户对话框。 #### 2.2 新增用户对话框 新增用户对话框包含以下字段: | 字段名称 | 是否必填 | 说明 | 验证规则 | |---------|---------|------|---------| | 关联用户 | 否 | 关联的员工 | 从员工列表中选择 | | 账号 | 是 | 用户的登录账号 | 不能为空 | | 用户名 | 是 | 用户的名称 | 不能为空 | | 状态 | 是 | 用户的状态 | 从字典表中选择 | #### 2.3 新增操作流程 1. 点击"新增"按钮打开对话框 2. 填写用户信息 3. 点击"提交"按钮 4. 前端进行表单验证 5. 验证通过后调用后端API创建用户 6. 创建成功后关闭对话框并刷新用户列表 7. 创建失败时显示错误信息 #### 2.4 默认密码 - 新增用户时,默认密码为"TIMS123456"的MD5加密值 ### 3. 用户编辑 #### 3.1 编辑按钮 在操作列提供"编辑"按钮,点击后弹出编辑用户对话框。 #### 3.2 编辑用户对话框 编辑用户对话框包含以下字段: | 字段名称 | 是否必填 | 说明 | 验证规则 | |---------|---------|------|---------| | 关联用户 | 否 | 关联的员工 | 从员工列表中选择 | | 账号 | 是 | 用户的登录账号 | 不能为空 | | 用户名 | 是 | 用户的名称 | 不能为空 | | 状态 | 是 | 用户的状态 | 从字典表中选择 | #### 3.3 编辑操作流程 1. 点击操作列的"编辑"按钮 2. 弹出对话框,显示用户信息 3. 修改用户信息 4. 点击"提交"按钮 5. 前端进行表单验证 6. 验证通过后调用后端API更新用户 7. 更新成功后关闭对话框并刷新用户列表 8. 更新失败时显示错误信息 ### 4. 用户删除 #### 4.1 批量删除 在操作按钮区提供"删除"按钮,用于批量删除选中的用户。 #### 4.2 单个删除 在操作列提供"删除"按钮,用于删除当前行的用户。 #### 4.3 删除操作流程 1. 选中要删除的用户(批量)或点击操作列的"删除"按钮(单个) 2. 弹出删除确认对话框 3. 确认后调用后端API删除用户 4. 删除成功后刷新用户列表 5. 删除失败时显示错误信息 #### 4.4 删除逻辑 - 删除用户时,同时删除该用户在Sys_UserRole表中的角色关联记录 - 从Sys_User表中删除用户记录 - 需要用户确认删除操作 ### 5. 密码重置 #### 5.1 重置密码按钮 在操作列提供"重置密码"按钮,点击后弹出重置密码对话框。 #### 5.2 重置密码对话框 重置密码对话框包含以下字段: | 字段名称 | 说明 | |---------|------| | 用户名 | 显示用户的名称(只读) | | 账号 | 显示用户的登录账号(只读) | | 新密码 | 输入新的密码 | | 确认密码 | 再次输入新密码 | #### 5.3 重置密码操作流程 1. 点击操作列的"重置密码"按钮 2. 弹出对话框,显示用户名和账号 3. 输入新密码和确认密码 4. 点击"提交"按钮 5. 前端验证两次输入的密码是否一致 6. 验证通过后调用后端API重置密码 7. 重置成功后关闭对话框并显示成功提示 8. 重置失败时显示错误信息 #### 5.4 密码加密 - 新密码使用MD5加密后存储到Sys_User.Password字段 ## 数据库设计 ### 相关表结构 #### Sys_User表(用户表) | 字段名 | 类型 | 说明 | |-------|------|------| | UserID | varchar(36) | 用户ID(主键) | | LoginID | varchar(50) | 登录账号 | | Name | varchar(100) | 用户名 | | Password | varchar(100) | 密码(MD5加密) | | WeChatUserId | varchar(100) | 企业微信账号 | | EmployeeId | varchar(36) | 关联员工ID | | RecordStatus | int | 状态 | | CreateTime | datetime | 创建时间 | | CreateUserID | varchar(36) | 创建人ID | | ModifyTime | datetime | 修改时间 | | ModifyUserID | varchar(36) | 修改人ID | #### Sys_Role表(角色表) | 字段名 | 类型 | 说明 | |-------|------|------| | RoleID | varchar(36) | 角色ID(主键) | | RoleName | varchar(100) | 角色名称 | | Description | varchar(500) | 角色描述 | | IsSystemRole | bit | 是否系统角色 | | RecordStatus | int | 状态 | #### Sys_UserRole表(用户角色关联表) | 字段名 | 类型 | 说明 | |-------|------|------| | UserID | varchar(36) | 用户ID(主键) | | RoleID | varchar(36) | 角色ID(主键) | #### Sys_DictionaryItem表(字典项表) | 字段名 | 类型 | 说明 | |-------|------|------| | DictionaryItemID | varchar(36) | 字典项ID(主键) | | DictionaryCode | varchar(50) | 字典代码 | | Value | int | 字典值 | | Name | varchar(100) | 字典名称 | #### Bus_Employee表(员工表) | 字段名 | 类型 | 说明 | |-------|------|------| | EmployeeId | varchar(36) | 员工ID(主键) | | Name | varchar(100) | 员工姓名 | | RecordStatus | int | 状态 | ## 接口设计 ### 1. 查询用户列表 **接口地址**:`GET /api/user/list` **请求参数**: | 参数名 | 类型 | 必填 | 说明 | |-------|------|------|------| | name | String | 否 | 用户名(模糊查询) | | loginId | String | 否 | 账号(模糊查询) | | recordStatus | Integer | 否 | 状态 | | page | Integer | 是 | 页码 | | pageSize | Integer | 是 | 每页行数 | | sortBy | String | 否 | 排序字段 | | sortOrder | String | 否 | 排序方向(ASC/DESC) | **响应示例**: ```json { "success": true, "data": { "content": [ { "id": "user-id-1", "loginId": "admin", "name": "管理员", "roleName": "系统管理员", "weChatUserId": "wx123456", "recordStatus": 1, "recordStatusName": "正常", "createTime": "2026-01-01 10:00:00", "modifyTime": "2026-01-01 10:00:00" } ], "totalElements": 100 } } ``` ### 2. 保存用户(新增或编辑) **接口地址**:`POST /api/user/save` **请求参数**: ```json { "id": "user-id-1", "employeeId": "employee-id-1", "loginId": "testuser", "name": "测试用户", "recordStatus": 1 } ``` **响应示例**: ```json { "success": true, "message": "用户创建成功", "data": { "id": "new-user-id", "loginId": "testuser", "name": "测试用户", "roleName": "系统管理员", "weChatUserId": "wx789012", "recordStatus": 1, "recordStatusName": "正常", "createTime": "2026-03-03 10:00:00", "modifyTime": "2026-03-03 10:00:00" } } ``` ### 3. 删除用户 **接口地址**:`DELETE /api/user/delete` **请求参数**: ```json ["user-id-1", "user-id-2"] ``` **响应示例**: ```json { "success": true, "message": "删除成功", "deletedCount": 2 } ``` ### 4. 重置密码 **接口地址**:`POST /api/user/reset-password` **请求参数**: ```json { "userId": "user-id-1", "newPassword": "newpassword123" } ``` **响应示例**: ```json { "success": true, "message": "密码重置成功" } ``` ### 5. 获取状态列表 **接口地址**:`GET /api/user/record-status` **响应示例**: ```json [ { "dictionaryItemId": "dict-id-1", "dictionaryCode": "RecordStatus", "value": 1, "name": "正常" }, { "dictionaryItemId": "dict-id-2", "dictionaryCode": "RecordStatus", "value": 0, "name": "禁用" } ] ``` ### 6. 获取员工列表 **接口地址**:`GET /api/employee/list` **请求参数**: | 参数名 | 类型 | 必填 | 说明 | |-------|------|------|------| | page | Integer | 否 | 页码 | | pageSize | Integer | 否 | 每页行数 | **响应示例**: ```json { "success": true, "data": { "content": [ { "employeeId": "employee-id-1", "name": "张三" } ], "totalElements": 50 } } ``` ## 权限控制 ### 功能权限代码 | 功能 | 权限代码 | |------|---------| | 查询用户列表 | 0101 | | 删除用户 | 0102 | | 重置密码 | 0103 | | 新增/编辑用户 | 0104 | ### 权限验证 - 所有接口都需要进行权限验证 - 前端按钮根据用户权限代码显示或隐藏 - 后端接口使用@RequirePermission注解进行权限验证 ## 界面设计 ### 页面布局 1. **页面标题**:显示"用户管理" 2. **查询条件区**:包含用户名、账号、状态查询条件和查询、重置按钮 3. **操作按钮区**:包含新增、删除按钮 4. **表格区**:显示用户列表 5. **分页区**:显示分页控件 ### 响应式设计 - 表格高度自适应屏幕高度:`calc(100vh - 395px)` - 表格宽度自适应屏幕宽度:`calc(100vw - 331px)` - 支持横向滚动条(当表格内容超出屏幕宽度时) - 支持纵向滚动条(当表格内容超出可视区域时) --- # 第三部分:通用技术规范 ## 后端技术栈 - Spring Boot 2.x - Spring Data JPA - Spring Security - SQL Server 2008 R2 - Apache POI(Excel导出) ## 前端技术栈 - Vue 3 - Element Plus 2.x - Axios - Vue Router ## 关键技术点 ### 1. 数据源路由 - 使用@DataSource注解指定数据源类型(COMMON/BRANCH) - 引航计划使用BRANCH数据源(liandatugboatmis数据库) - 用户管理使用COMMON数据源(tugboatcommon数据库) ### 2. 分页查询 - 使用Spring Data的Page和Pageable实现分页 - 支持数据库级排序 - 前端使用Element Plus的Pagination组件 ### 3. 密码加密 - 使用MD5算法加密密码 - 新增用户时设置默认密码"TIMS123456" ### 4. 表单验证 - 前端使用Element Plus的表单验证规则 - 后端使用@Valid注解进行验证 ### 5. 权限控制 - 使用自定义注解@RequirePermission进行权限验证 - 前端使用v-permission指令控制按钮显示 ### 6. 数据导入 - 支持制表符分隔的数据格式 - 自动解析并验证数据格式 - 支持数据预览和搜索 ### 7. 数据导出 - 使用Apache POI生成Excel文件 - 支持自定义导出字段 - 支持流式下载 ## 注意事项 ### 1. 数据源配置 - 引航计划功能使用BRANCH数据源(liandatugboatmis数据库) - 用户管理功能使用COMMON数据源(tugboatcommon数据库) - 不要随意修改数据源配置 ### 2. 密码安全 - 密码必须使用MD5加密存储 - 不要在前端传输明文密码 - 重置密码时需要用户确认 ### 3. 事务管理 - 删除用户时需要使用@Transactional注解保证事务一致性 - 导入引航计划时需要使用@Transactional注解保证数据一致性 ### 4. 级联删除 - 删除用户时需要同时删除用户角色关联记录 - 不要删除已调度的引航计划 ### 5. 输入验证 - 前端和后端都需要进行输入验证 - 所有用户输入都需要进行防SQL注入处理 ### 6. 错误处理 - 所有操作都需要进行异常处理 - 返回友好的错误信息给用户 - 记录详细的错误日志 ### 7. 权限验证 - 所有接口都需要进行权限验证 - 前端按钮根据权限显示或隐藏 - 后端接口必须验证权限 ## 开发规范 ### 代码规范 - 所有方法都需要添加函数级注释 - 遵循Java和Vue的代码规范 - 使用Lombok简化代码 - 使用DTO进行数据传输 ### 命名规范 - 实体类:使用驼峰命名法,如User、DispPilotPlan - 数据库表:使用下划线命名法,如Sys_User、Disp_PilotPlan - 接口路径:使用小写和连字符,如/user/list、/pilot-plan/list - Vue组件:使用PascalCase命名法,如UserManagement、PilotPlan ### 文件组织 - 后端代码按功能模块组织:controller、service、repository、dto、model - 前端组件按功能模块组织:components目录下按功能分类 ## 测试要点 ### 1. 引航计划功能测试 - 测试各种查询条件组合 - 测试导入功能(正常数据、重复数据、已调度数据) - 测试导出功能 - 测试分页和排序功能 - 测试港区作业类型计算 - 测试关联数据的自动创建 ### 2. 用户管理功能测试 - 测试各种查询条件组合 - 测试新增用户功能(必填字段验证、重复校验) - 测试编辑用户功能 - 测试删除用户功能(单个删除、批量删除) - 测试密码重置功能(密码一致性验证) - 测试分页和排序功能 - 测试权限控制 ### 3. 异常处理测试 - 测试各种异常情况的处理 - 测试网络异常的处理 - 测试数据库异常的处理 ## 后续优化建议 ### 1. 引航计划功能 - 支持批量编辑引航计划 - 支持引航计划的复制功能 - 支持引航计划的模板功能 - 支持引航计划的审批流程 - 支持引航计划的版本管理 ### 2. 用户管理功能 - 支持Excel批量导入用户 - 支持Excel批量导出用户 - 支持用户详情查看 - 支持用户操作日志 - 支持用户数据统计 - 支持密码复杂度策略配置 ### 3. 通用功能 - 支持数据导出格式自定义 - 支持查询条件保存 - 支持列表配置自定义 - 支持数据导入模板下载 - 支持操作日志记录 - 支持数据统计报表 --- ## 附录 ### A. 引航计划数据解析示例 **原始数据**: ``` 1 2026-03-03 10:30 测试船1 TEST SHIP1 中国 100 8.5 进港 1号泊位 2号泊位 是 引航公司A 张三 李四 王五 赵六 代理A 13800138001 交通船A 主航道 有 无备注 ``` **解析结果**: ```json { "serialNumber": "1", "planTime": "2026-03-03 10:30", "chineseShipName": "测试船1", "englishShipName": "TEST SHIP1", "nationality": "中国", "shipLength": 100, "draft": 8.5, "dynamic": "进港", "startBerth": "1号泊位", "endBerth": "2号泊位", "cooperationMark": "是", "pilotAgency": "引航公司A", "mainPilot": "张三", "secondaryPilot": "李四", "deputyPilot": "王五", "otherPilots": "赵六", "agent": "代理A", "agentPhone": "13800138001", "transportVessel": "交通船A", "waterway": "主航道", "sideThruster": "有", "remark": "无备注" } ``` ### B. 用户管理操作流程图 ``` 用户登录 → 进入用户管理页面 → 查询用户列表 ↓ [新增用户] → 填写用户信息 → 提交 → 刷新列表 ↓ [编辑用户] → 修改用户信息 → 提交 → 刷新列表 ↓ [删除用户] → 确认删除 → 删除 → 刷新列表 ↓ [重置密码] → 输入新密码 → 提交 → 刷新列表 ``` ### C. 引航计划导入流程图 ``` 点击导入按钮 → 打开导入对话框 → 粘贴数据 → 解析数据 ↓ 显示预览对话框 → 搜索/查看数据 → 确认导入 ↓ 数据验证 → 创建/更新关联数据 → 导入成功 ↓ 同步到调度表 → 刷新列表 ``` --- **文档版本**:v1.0 **创建日期**:2026-03-03 **最后更新**:2026-03-03 **文档作者**:AI助手