feat: API层完全对齐原始v200 + 登录页验证码逻辑修复

- 重写19个API模块,170+函数完全对齐原始JavaScript
- 修复登录页: captchaEnabled默认true, getCodeImgs对齐原始, localStorage key对齐zhsw-*
- 修复HTTP模块: code===0成功码, 60s超时, 无Bearer前缀Token
- 修复userStore: setTokenFromLogin, UserInfo类型
- 新建rsaUtil.ts: RSA长文本加密
- 路由守卫验证通过, 浏览器全链路零报错
This commit is contained in:
2026-06-15 23:50:49 +08:00
parent f44c9bff49
commit a179fc0431
28 changed files with 2977 additions and 249 deletions

68
src/api/clientQR.ts Normal file
View File

@@ -0,0 +1,68 @@
/**
* 客户端二维码 / 排水户 / 设备 API
*
* @module api/clientQR
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
/**
* 获取排水户详情
* @param data - 查询数据
*/
export function queryTSwJcPshAll(data: any) {
return http.request({
url: SW_PATH + '/api/v1/drainage/queryTSwJcPshAll',
method: 'post',
data,
})
}
/**
* 获取设备详情
* @param params - { equipmentId }
*/
export function getEquipmentDetail(params: any) {
return http.request({
url: SW_PATH + '/asset/siteEquipment/equipment/getEquipmentList',
method: 'get',
params,
})
}
/**
* 获取设备型号
* @param params - { equipmentType }
*/
export function getSbxh(params: any) {
return http.request({
url: SW_PATH + '/asset/siteEquipment/equipment/getSbxhList',
method: 'get',
params,
})
}
/**
* 获取设备迁移列表
* @param params - { equipmentId, page?, size? }
*/
export function getMigrateList(params: any) {
return http.request({
url: SW_PATH + '/asset/siteEquipment/migrate/getList',
method: 'get',
params,
})
}
/**
* 获取维修记录列表
* @param params - { equipmentId, page?, size? }
*/
export function getRepairList(params: any) {
return http.request({
url: SW_PATH + '/asset/repair/list',
method: 'get',
params,
})
}

View File

@@ -1,139 +1,225 @@
/** /**
* 通用 API * 通用 API
* *
* 包含文件上传、字典查询、验证码获取、系统配置等公共接口。 * 包含文件上传、图片处理、字典查询、公告、防汛值班、
* 天气预报、平台使用上报、设备跟踪等公共接口。
* 匹配原始 JavaScript APIindex.js + uploadImg.js的完整行为。
* *
* @module api/common * @module api/common
*/ */
import { post, get } from '@/utils/http' import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
import { v4 as uuidv4 } from 'uuid'
// ══════════════════════════════════════════════ // ══════════════════════════════════════════════
// 请求参数类型 // 类型定义
// ══════════════════════════════════════════════ // ══════════════════════════════════════════════
/** 文件上传响应 */ /** 表单数据查询参数 */
export interface UploadResult { export interface CommonQueryParams {
/** 文件在服务器上的存储名称 */ [key: string]: any
fileName: string
/** 文件可访问的完整 URL */
url: string
} }
/** 字典项 */ /** 平台使用上报数据 */
export interface DictItem { export interface PlatUsageData {
/** 字典标签(显示用) */ menuId: string
dictLabel: string userId: string
/** 字典值(存储用) */ type: string | number
dictValue: string [key: string]: any
/** 字典类型 */
dictType?: string
/** CSS 类名(用于表格回显样式) */
cssClass?: string
/** 列表样式 */
listClass?: string
/** 是否默认 */
isDefault?: string
/** 排序号 */
dictSort?: number
} }
/** 验证码图片响应 */ /** 枚举查询数据 */
export interface CaptchaResult { export interface SourceEnumData {
/** 验证码唯一标识,登录时需要回传 */ mjfzbm?: string
uuid: string [key: string]: any
/** Base64 编码的验证码图片 */
img: string
/** 是否开启验证码 */
captchaEnabled: boolean
}
/** 系统配置项 */
export interface ConfigItem {
/** 参数键名 */
configKey: string
/** 参数值 */
configValue: string
} }
// ══════════════════════════════════════════════ // ══════════════════════════════════════════════
// API 方法 // 文件 / 图片相关(不使用 SW_PATH
// ══════════════════════════════════════════════ // ══════════════════════════════════════════════
/** /**
* 上传文件 * 上传文件
* *
* 支持图片、文档等文件上传,使用 FormData 格式。 * 使用 http.uploadFile 方法,以 multipart/form-data 格式上传
* *
* @param file - 要上传的文件对象 * @param file - 要上传的文件对象
* @returns 上传结果,包含文件名和访问 URL * @returns Promise
*/ */
export function uploadFile(file: File): Promise<UploadResult> { export function uploadFile(file: File) {
const formData = new FormData() const formData = new FormData()
formData.append('file', file) formData.append('file', file)
return (http as any).uploadFile(formData)
}
return post<UploadResult>('/common/upload', formData, { /**
headers: { 'Content-Type': 'multipart/form-data' }, * 上传图片 URL获取下载地址
*
* @param data - 请求数据
* @returns Promise
*/
export function uploadImgUrl(data?: any) {
return http.request({
url: '/file/v2/api-docs/file-minio/object/download',
method: 'post',
data,
}) })
} }
/** /**
* 批量上传文件 * 获取在线图片(以 blob 形式下载)
* @param files - 文件对象数组 *
* @returns 上传结果数组 * @param downloadUrl - 图片下载地址
* @param buckName - Bucket 名称(默认 swfile
* @returns Promiseblob 响应)
*/ */
export async function uploadFiles(files: File[]): Promise<UploadResult[]> { export function getOnLineImgs(downloadUrl: string, buckName?: string) {
const results: UploadResult[] = [] return http.request({
for (const file of files) { url: '/file/file-minio/object/getImg',
const result = await uploadFile(file) method: 'get',
results.push(result) params: {
} downloadUrl,
return results fileName: uuidv4(),
buckName: buckName || 'swfile',
},
responseType: 'blob',
})
} }
// ══════════════════════════════════════════════
// 字典(不使用 SW_PATH
// ══════════════════════════════════════════════
/** /**
* 获取字典数据 * 根据字典类型查询字典数据信息
*
* 根据字典类型查询对应的字典项列表,用于下拉框、单选框等组件的数据源。
* *
* @param dictType - 字典类型标识,如 'sys_user_sex' * @param dictType - 字典类型标识,如 'sys_user_sex'
* @returns 字典项数组 * @returns Promise
*/ */
export function getDictData(dictType: string): Promise<DictItem[]> { export function getDicts(dictType: string) {
return get<DictItem[]>('/system/dict/data/type', { dictType }) return http.request({
url: '/system/dict/data/type/' + dictType,
method: 'get',
})
}
// ══════════════════════════════════════════════
// 公告 / 防汛值班 / 天气预报 / 液位等(使用 SW_PATH
// ══════════════════════════════════════════════
/**
* 获取最新公告
*
* @param params - 查询参数
* @returns Promise
*/
export function publicNoticeLast(params?: CommonQueryParams) {
return http.request({
url: SW_PATH + '/publicNotice/last',
method: 'get',
params,
})
} }
/** /**
* 根据字典类型获取字典数据RESTful 风格) * 查询当前防汛值班
* @param dictType - 字典类型标识 *
* @returns 字典项数组 * @returns Promise
*/ */
export function getDictDataByType(dictType: string): Promise<DictItem[]> { export function floodDutyCurrentDay() {
return get<DictItem[]>(`/system/dict/data/type/${dictType}`) return http.request({
url: SW_PATH + '/floodDuty/duty/currentDay',
method: 'get',
})
} }
/** /**
* 获取验证码图片 * 获取易涝点液位深度信息
* @returns 验证码信息uuid 和 base64 图片) *
* @returns Promise
*/ */
export function getCaptcha(): Promise<CaptchaResult> { export function getDepthInfo() {
return get<CaptchaResult>('/captchaImage') return http.request({
url: SW_PATH + '/floodMonitoring2/getDepthInfo',
method: 'get',
})
} }
/** /**
* 根据配置键获取系统配置值 * 当前防汛日报
* @param configKey - 配置键名 *
* @returns 配置项的值 * @param params - 查询参数
* @returns Promise
*/ */
export function getConfigValue(configKey: string): Promise<string> { export function floodDailyReportCurrent(params?: CommonQueryParams) {
return get<string>(`/system/config/configKey/${configKey}`) return http.request({
url: SW_PATH + '/rainreview/floodDailyReportCurrent',
method: 'post',
params,
})
} }
/** /**
* 获取系统配置项详情 * 获取 3 日天气预报
* @param configKey - 配置键名 *
* @returns 配置项完整信息 * @returns Promise
*/ */
export function getConfigItem(configKey: string): Promise<ConfigItem> { export function get3dWeather() {
return get<ConfigItem>(`/system/config/configKey/${configKey}`) return http.request({
url: SW_PATH + '/floodMonitoring2/get3dWeather',
method: 'get',
})
}
/**
* 上报用户平台使用记录
*
* @param data - 使用记录数据 {menuId, userId, type: '1'}
* @returns Promise
*/
export function reportPlatUsage(data: PlatUsageData) {
return http.request({
url: SW_PATH + '/platformUsage/reportPlatUsage',
method: 'post',
data,
})
}
/**
* 根据用户获取绑定的设备信息
*
* @param params - 查询参数,如 {userid: '...'}
* @returns Promise
*/
export function getTrackEquipmentByUser(params?: CommonQueryParams) {
return http.request({
url: SW_PATH + '/equipmentTrack/getTrackEquipmentByUser',
method: 'get',
params,
})
}
/**
* 查询枚举信息
*
* @param data - 查询数据,如 {mjfzbm: '...'}
* @returns Promise
*/
export function querySourceEnumAll(data?: SourceEnumData) {
return http.request({
url: SW_PATH + '/api/v1/sourceNew/querySourceEnumAll',
method: 'post',
data,
})
}
/**
* 查询当月已经返回的区域列表(当月已考核过的区域列表)
*/
export function getCheckXzqhList() {
return http.request({
url: SW_PATH + '/maintenance/getSwYhKhTaskListByCurrentMonth',
method: 'get',
})
} }

165
src/api/fxgl.ts Normal file
View File

@@ -0,0 +1,165 @@
/**
* 防汛管理 API
*
* @module api/fxgl
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
/**
* 查询最新的防汛响应等级
*/
export function getSwDataFxxydjLatest(params: any) {
return http.request({
url: SW_PATH + '/fxData/getSwDataFxxydjLatest',
method: 'get',
params,
})
}
/**
* 查询所属单位下面的组长和组员列表
* @param data
* @param data.userid 用户id
*/
export function getSwDataFxrySsdwDkList(data: any) {
return http.request({
url: SW_PATH + '/fxData/getSwDataFxrySsdwDkList',
method: 'post',
data,
})
}
/**
* 查询所属单位下面的组长和组员列表
* @param data
* @param data.leaderid 组长id
*/
export function getSwDataFxryZzDkList(data: any) {
return http.request({
url: SW_PATH + '/fxData/getSwDataFxryZzDkList',
method: 'post',
data,
})
}
/**
* 查询所属单位下面的组长和组员列表
* @param data
* @param data.zzid 组长id
* @param data.ssdw 所属单位
* @param data.ssdwname 所属单位名称
* @param data.ry 打卡人员,用逗号分隔
* @param data.pic 照片
*/
export function saveSwDataFxryDk(data: any) {
return http.request({
url: SW_PATH + '/fxData/saveSwDataFxryDk',
method: 'post',
data,
})
}
/**
* 获取当前用户的调度指令列表
*/
export function getSwDataFxddZlDdByuserid(params: any) {
return http.request({
url: SW_PATH + '/fxData/getSwDataFxddZlDdByuserid',
method: 'get',
params,
})
}
/**
* 保存防汛调度指令人车调度打卡
* @param data
* @param data.ddid 调度id
* @param data.pic 打卡照片
*/
export function saveSwDataFxddZlDdDk(data: any) {
return http.request({
url: SW_PATH + '/fxData/saveSwDataFxddZlDdDk',
method: 'post',
data,
})
}
/**
* 保存防汛调度指令人车调度打卡
* @param data
* @param data.current 当前页码
* @param data.size 每页显示记录数
*/
export function getSwDataCkPage(data: any) {
return http.request({
url: SW_PATH + '/ckwz/getSwDataCkPage',
method: 'post',
data,
})
}
/**
* 获取部门列表
*/
export function getDeptCodeNew() {
return http.request({
url: '/system/dept/getDepts/allTree',
method: 'get',
params: { status: '0' },
})
}
/**
* 更新防汛人员状态
* @param data
* @param data.userid userid
* @param data.shape 点位
*/
export function updateSwDataFxryStatus(data: any) {
return http.request({
url: SW_PATH + '/fxData/updateSwDataFxryStatus',
method: 'post',
data,
})
}
/**
* 仓库信息详情
*/
export function getSwDataCkVo(params: any) {
return http.request({
url: SW_PATH + '/ckwz/getSwDataCkVo',
method: 'get',
params,
})
}
/**
* 仓库物资入库
* @param data
* @param data.ckid 仓库id
* @param data.list 物资列表
*/
export function inboundCkWzInfo(data: any) {
return http.request({
url: SW_PATH + '/ckwz/inboundCkWzInfo',
method: 'post',
data,
})
}
/**
* 仓库物资出库
* @param data
* @param data.ckid 仓库id
* @param data.list 物资列表
*/
export function outboundCkWzInfo(data: any) {
return http.request({
url: SW_PATH + '/ckwz/outboundCkWzInfo',
method: 'post',
data,
})
}

View File

@@ -4,39 +4,275 @@
* 统一导出所有 API 子模块的方法和类型,业务代码只需 * 统一导出所有 API 子模块的方法和类型,业务代码只需
* `import { login, getUserInfo } from '@/api'` 即可使用。 * `import { login, getUserInfo } from '@/api'` 即可使用。
* *
* 完全匹配原始 yuto-water-mobile-v200 JavaScript API 层。
*
* @module api * @module api
*/ */
// ── 用户模块 ── // ── 用户模块 ──
export { export {
login, login,
getCodeImg,
updateUserPwd,
getUserInfo, getUserInfo,
logout, listUser,
resetPassword, getHierarchicalLeader,
} from './user' getUserListByDeptIds,
export type { getUserListByIds,
LoginParams, getUserListByPostIds,
LoginResult, getUserListByRoleIds,
ResetPasswordParams,
UserInfo,
} from './user' } from './user'
export type { LoginUserInfo, UpdatePwdUserInfo, UserQuery, UserInfo } from './user'
// ── 通用模块 ── // ── 通用模块 ──
export { export {
uploadFile, uploadFile,
uploadFiles, uploadImgUrl,
getDictData, getOnLineImgs,
getDictDataByType, getDicts,
getCaptcha, publicNoticeLast,
getConfigValue, floodDutyCurrentDay,
getConfigItem, getDepthInfo,
} from './common' floodDailyReportCurrent,
export type { get3dWeather,
UploadResult, reportPlatUsage,
DictItem, getTrackEquipmentByUser,
CaptchaResult, querySourceEnumAll,
ConfigItem, getCheckXzqhList,
} from './common' } from './common'
export type { CommonQueryParams, PlatUsageData, SourceEnumData } from './common'
// ── 养护模块 ──
export {
planTaskList,
planTaskListDynamic,
taskList,
yhitems,
yhitemsDynamic,
maintenanceObj,
maintenanceObjDynamic,
maintenanceMobileList,
querySourceTableClassAll,
queryGxGdByGeomJl,
saveSwDataQnfd,
saveSwDataYxkjzy,
queryJdjByGeomJl,
relationEquipmentList,
relationEquipmentListDynamic,
cloclin,
getTaskDetail,
updateStatus,
maintenancePlanList,
maintenancePlanListDynamic,
clockinList,
newJYDreport,
addTSwDataXjyh,
workOrderMyTodo,
workOrderMyFinished,
workOrderMyStarted,
querySourceDetails,
workOrderFeedbackList,
workOrderFeedback,
jcdwList,
workOrderRepair,
getEquipmentList,
querySourceSymbolAll,
querySymbolByScode,
} from './maintenance'
// ── 巡检模块 ──
export {
getSwTaskMobilePage,
getXjTaskMileageTrackingList,
saveSwXjTaskTrack,
saveXjTaskMileage,
saveTaskClockinMobileDetail,
getSwTaskPage,
getXjTaskDetail,
getSwXjTaskRateClockinMobile,
saveSwXjProblem,
getRelationEquipmentList,
updateSwXjTaskRateMobile,
getSwXjTaskClockinAllVo,
getSwXjTaskNoClockinAllVo,
saveTaskClockinDetail,
getTaskStatusMobileByRateId,
getTaskInfoLast,
getSwXjProblemPage,
} from './inspection'
// ── 防汛模块 ──
export {
getSwDataFxxydjLatest,
getSwDataFxrySsdwDkList,
getSwDataFxryZzDkList,
saveSwDataFxryDk,
getSwDataFxddZlDdByuserid,
saveSwDataFxddZlDdDk,
getSwDataCkPage,
getDeptCodeNew,
updateSwDataFxryStatus,
getSwDataCkVo,
inboundCkWzInfo,
outboundCkWzInfo,
} from './fxgl'
// ── 排水户模块 ──
export {
getPshXjPhoneList,
pshXjPhoneClock,
listPshXjRound,
getPshXjProblemList,
getPshXjProblemTaskList,
getPshXjKhPhoneTaskList,
getPshXjKhPhoneRecordList,
reportPshXjKhPhoneRecord,
updatePshXjKhTaskStatus,
} from './pshgl'
// ── 监理模块 ──
export {
getSupervisionEquipmentMileageStatus,
getSupervisionCheckItemList,
saveSupervisionEquipmentMileage,
saveSupervisionRecords,
getSupervisionRecordsMobilePage,
saveSupervisionRecordsProblem,
getSupervisionRecordsDetail,
} from './supervisor'
// ── 地图模块 ──
export {
getFloodFacilityOverview,
getFloodDeviceTotal,
queryBasedSpatialInformation,
getTypeList as getMapTypeList,
getGridForecastInfo,
createWindField,
createGDYBPolygon,
getEquipmentDetailByName,
getLdtDataInfoNew,
getQweatherApi,
getSysResourceCatalogMetadataCountTree,
metaDataQueryList,
getFieldByClass,
getClassByClassGuid,
getFacilityRealTimeData,
getHistoryData as getMapHistoryData,
getSwDataMapList,
} from './map'
// ── 地图服务模块 ──
export { getAllService, getServiceListThemeByRole } from './mapService'
// ── 养护考核模块 ──
export {
saveSwYhKh,
getSwYhKhCheckList,
getSwYhKhMobileList,
getSwYhKhList,
getSwYhKhListDynamic,
metaDataFieldQuery,
} from './maintenanceCheck'
// ── 监测设备模块 ──
export {
getTypeList as getMonitorTypeList,
getRainStationList,
getPumpStationList,
getRepairRecordList,
getList as getMonitorFieldList,
getHistoryData as getMonitorHistoryData,
getAppTotalNumber,
getAlarmThresholdList,
getMonitorYjDataPage,
getRainfallRealtimeByTime,
} from './monitoringEquipment'
// ── 工作流模块 ──
export {
getProcessDetail,
getApproveList,
finishedTaskNode,
rejectTask,
stopTask,
getMyTodoList,
getMyFinishedList,
getMyStartList,
getReturnNodes,
returnTask,
revokeTask,
urgingTask,
updateProcessState,
deleteProcessInstance,
setTaskDelegateUser,
setTaskTransfer,
getUserList as getWorkflowUserList,
addSuperviseComment,
cancelSupervise,
getTaskAttribute,
getNextTaskAttribute,
getProcessDetailNew,
setNodeTimeout,
} from './workflow'
// ── 项目管理模块 ──
export {
getProjectList,
getProjectMyPhoneDeal,
getProjectInfo,
projectAudit,
getProjectInspectClockin,
getProjectInspectReport,
getProjectStageTime,
} from './projectManagement'
// ── 工程管理模块 ──
export {
saveSwDataEngineeringReporting,
getSwDataEngineeringReportingPage,
updateSwDataEngineeringReporting,
saveSwDataEngineeringReportingDetail,
getSwDataEngineeringReportingVo,
} from './xjgl'
// ── 有限空间作业模块 ──
export {
getSwDataYxkjzyPage,
getSwDataYxkjzy,
saveSwDataYxkjzySubmit,
updateSwDataYxkjzy,
updateSwDataYxkjzyManholes,
} from './yxkjzyRecords'
// ── 通知模块 ──
export {
getUnReadMessages,
getAllMessages,
getTemplate,
markAsRead,
} from './notice'
// ── 菜单模块 ──
export { getRouters, getRoutersByAppId } from './menu'
// ── 菜单编辑模块 ──
export {
getUserWorkStationList,
addWorkStationGroup,
deleteWorkStationGroup,
updateWorkStationGroup,
updateWorkStationInfo,
} from './menuEdit'
// ── 二维码客户端模块 ──
export {
queryTSwJcPshAll,
getEquipmentDetail,
getSbxh,
getMigrateList,
getRepairList,
} from './clientQR'
// ── HTTP 工具(便捷导出) ── // ── HTTP 工具(便捷导出) ──
export { getToken, setToken, removeToken } from '@/utils/http' export { getToken, setToken, removeToken } from '@/utils/http'

165
src/api/inspection.ts Normal file
View File

@@ -0,0 +1,165 @@
/**
* 巡检任务 API
*
* @module api/inspection
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
// 巡检任务查询
export function getSwTaskMobilePage(data: any) {
return http.request({
url: SW_PATH + `/swXjTask/getSwTaskMobilePage`,
method: 'post',
data,
})
}
// 查询当前是否存在任务轨迹信息
export function getXjTaskMileageTrackingList(data: any) {
return http.request({
url: SW_PATH + `/swXjTask/getXjTaskMileageTrackingList`,
method: 'post',
data,
})
}
/**
* 监管记录查询
* @param data
* @param data.type 0 巡检 1 项目管理
*/
export function saveSwXjTaskTrack(data: any) {
return http.request({
url: SW_PATH + `/swXjTask/saveSwXjTaskTrack`,
method: 'post',
data,
})
}
// 保存巡检轨迹里程信息
export function saveXjTaskMileage(data: any) {
return http.request({
url: SW_PATH + `/swXjTask/saveXjTaskMileage`,
method: 'post',
data,
})
}
// 打卡
export function saveTaskClockinMobileDetail(data: any) {
return http.request({
url: SW_PATH + `/swXjTask/saveTaskClockinMobileDetail`,
method: 'post',
data,
})
}
// 巡检任务查询
export function getSwTaskPage(data: any) {
return http.request({
url: SW_PATH + `/swXjTask/getSwTaskPage`,
method: 'post',
data,
})
}
// 巡检任务详情
export function getXjTaskDetail(params: any) {
return http.request({
url: SW_PATH + `/swXjTask/getXjTaskDetail`,
method: 'get',
params,
})
}
// 获取任务的打卡记录
export function getSwXjTaskRateClockinMobile(params: any) {
return http.request({
url: SW_PATH + `/swXjTask/getSwXjTaskRateClockinMobile`,
method: 'get',
params,
})
}
// 问题上报
export function saveSwXjProblem(data: any) {
return http.request({
url: SW_PATH + `/swXjProblem/saveSwXjProblem`,
method: 'post',
data,
})
}
// 获取关联设备
export function getRelationEquipmentList(params: any) {
return http.request({
url: SW_PATH + `/swXjTask/getRelationEquipmentList`,
method: 'get',
params,
})
}
// 更新当前任务当天状态
export function updateSwXjTaskRateMobile(data: any) {
return http.request({
url: SW_PATH + `/swXjTask/updateSwXjTaskRateMobile`,
method: 'post',
data,
})
}
// 打卡日期下面的打卡信息查询
export function getSwXjTaskClockinAllVo(params: any) {
return http.request({
url: SW_PATH + `/swXjTask/getSwXjTaskClockinAllVo`,
method: 'get',
params,
})
}
// 打卡日期下面的打卡信息查询(需要补卡的)
export function getSwXjTaskNoClockinAllVo(params: any) {
return http.request({
url: SW_PATH + `/swXjTask/getSwXjTaskNoClockinAllVo`,
method: 'get',
params,
})
}
// 保存打卡信息 补卡
export function saveTaskClockinDetail(data: any) {
return http.request({
url: SW_PATH + `/swXjTask/saveTaskClockinDetail`,
method: 'post',
data,
})
}
// rateId查固定打卡点状态
export function getTaskStatusMobileByRateId(params: any) {
return http.request({
url: SW_PATH + `/swXjTask/getTaskStatusMobileByRateId`,
method: 'get',
params,
})
}
// 根据x,y查询最近的巡检任务
export function getTaskInfoLast(data: any) {
return http.request({
url: SW_PATH + `/swXjTask/getTaskInfoLast`,
method: 'post',
data,
})
}
// 获取巡检任务的上报
export const getSwXjProblemPage = (data: any) => {
return http.request({
url: SW_PATH + '/swXjProblem/getSwXjProblemPage',
method: 'post',
data,
})
}

354
src/api/maintenance.ts Normal file
View File

@@ -0,0 +1,354 @@
/**
* 养护管理 API
*
* 包含养护计划、任务、打卡、设备关联、检查井、气囊封堵、
* 有限空间作业、积淹点、问题上报、工单等接口。
*
* 注意:以下函数已迁移到 common.ts此处不再重复
* getDicts, publicNoticeLast, floodDutyCurrentDay, getDepthInfo,
* floodDailyReportCurrent, querySourceEnumAll, getCheckXzqhList,
* reportPlatUsage, get3dWeather, getTrackEquipmentByUser
*
* @module api/maintenance
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
// ══════════════════════════════════════════════
// 养护计划
// ══════════════════════════════════════════════
/** 获取当月任务列表 */
export function planTaskList(params: any) {
return http.request({
url: SW_PATH + '/maintenance/plan/task/list',
method: 'get',
params,
})
}
/** 获取当月任务列表(动态) */
export function planTaskListDynamic(data: any) {
return http.request({
url: SW_PATH + '/maintenance/plan/task/listDynamic',
method: 'post',
data,
})
}
/** 获取养护计划对应任务详情 */
export function taskList(planId: string) {
return http.request({
url: SW_PATH + `/maintenance/plan/taskList/${planId}`,
method: 'get',
})
}
/** 获取养护任务对应养护项完成详情 */
export function yhitems(taskId: string) {
return http.request({
url: SW_PATH + `/maintenance/plan/task/yhitems/${taskId}`,
method: 'get',
})
}
/** 获取养护任务对应养护项完成详情(动态) */
export function yhitemsDynamic(data: any) {
return http.request({
url: SW_PATH + '/maintenance/plan/task/yhitemsDynamic',
method: 'post',
data,
})
}
/** 获取养护对象 */
export function maintenanceObj(params: any) {
return http.request({
url: SW_PATH + '/maintenance/maintenanceObj',
method: 'get',
params,
})
}
/** 获取养护对象(动态) */
export function maintenanceObjDynamic(data: any) {
return http.request({
url: SW_PATH + '/maintenance/maintenanceObjDynamic',
method: 'post',
data,
})
}
/** 获取进行中的养护对象(移动端) */
export function maintenanceMobileList(params: any) {
return http.request({
url: SW_PATH + '/maintenance/maintenanceMobileList',
method: 'get',
params,
})
}
/** 获取养护计划列表 */
export function maintenancePlanList(params: any) {
return http.request({
url: SW_PATH + '/maintenance/plan/list',
method: 'get',
params,
})
}
/** 获取养护计划列表(动态) */
export function maintenancePlanListDynamic(data: any) {
return http.request({
url: SW_PATH + '/maintenance/plan/listDynamic',
method: 'post',
data,
})
}
// ══════════════════════════════════════════════
// 养护任务 / 打卡
// ══════════════════════════════════════════════
/** 获取任务详情 */
export function getTaskDetail(taskId: string) {
return http.request({
url: SW_PATH + `/maintenance/plan/task/${taskId}`,
method: 'get',
})
}
/** 获取养护任务对应打卡详情 */
export function clockinList(taskId: string) {
return http.request({
url: SW_PATH + `/maintenance/plan/task/clockinList/${taskId}`,
method: 'get',
})
}
/** 打卡 */
export function cloclin(data: any) {
return http.request({
url: SW_PATH + '/maintenance/cloclin',
method: 'post',
data,
})
}
// ══════════════════════════════════════════════
// 关联设备
// ══════════════════════════════════════════════
/** 获取关联设备 */
export function relationEquipmentList(params: any) {
return http.request({
url: SW_PATH + '/maintenance/task/relationEquipment/list',
method: 'get',
params,
})
}
/** 获取关联设备(动态) */
export function relationEquipmentListDynamic(data: any) {
return http.request({
url: SW_PATH + '/maintenance/task/relationEquipment/listDynamic',
method: 'post',
data,
})
}
/** 设备状态修改 */
export function updateStatus(params: any) {
return http.request({
url: SW_PATH + '/maintenance/task/relationEquipment/updateStatus',
method: 'put',
params,
})
}
// ══════════════════════════════════════════════
// 检查井 / 要素拾取
// ══════════════════════════════════════════════
/** 获取检查井列表 */
export function querySourceTableClassAll(data: any) {
return http.request({
url: SW_PATH + '/api/v1/sourceNew/querySourceTableClassAll',
method: 'post',
data,
})
}
/** 要素拾取 — 根据几何和距离查询管线/管道 */
export function queryGxGdByGeomJl(params: any) {
return http.request({
url: SW_PATH + '/api/v1/equipmentLedger/queryGxGdByGeomJl',
method: 'post',
params,
})
}
/** 查询排水户附近的节点井信息 */
export function queryJdjByGeomJl(params: any) {
return http.request({
url: SW_PATH + '/api/v1/drainage/queryJdjByGeomJl',
method: 'post',
params,
})
}
// ══════════════════════════════════════════════
// 气囊封堵 / 有限空间作业
// ══════════════════════════════════════════════
/** 气囊封堵数据保存 */
export function saveSwDataQnfd(data: any) {
return http.request({
url: SW_PATH + '/qnfdData/saveSwDataQnfd',
method: 'post',
data,
})
}
/** 有限空间作业数据保存 */
export function saveSwDataYxkjzy(data: any) {
return http.request({
url: SW_PATH + '/yxkjzyData/saveSwDataYxkjzy',
method: 'post',
data,
})
}
// ══════════════════════════════════════════════
// 积淹点 / 问题上报
// ══════════════════════════════════════════════
/** 创建积淹点 */
export function newJYDreport(params: any) {
return http.request({
url: SW_PATH + '/jydReport/newJYDreport',
method: 'post',
params,
})
}
/** 创建问题上报 */
export function addTSwDataXjyh(data: any) {
return http.request({
url: SW_PATH + '/api/v1/problemReporting/addTSwDataXjyh',
method: 'post',
data,
})
}
// ══════════════════════════════════════════════
// 工单
// ══════════════════════════════════════════════
/** 我的待办 */
export function workOrderMyTodo(data: any) {
return http.request({
url: SW_PATH + '/workOrder/my/todo',
method: 'post',
data,
})
}
/** 我的已办 */
export function workOrderMyFinished(data: any) {
return http.request({
url: SW_PATH + '/workOrder/my/finished0',
method: 'post',
data,
})
}
/** 我的发起 */
export function workOrderMyStarted(data: any) {
return http.request({
url: SW_PATH + '/workOrder/my/started',
method: 'post',
data,
})
}
/** 上报问题详情 */
export function querySourceDetails(params: any) {
return http.request({
url: SW_PATH + '/api/v1/sourceNew/querySourceDetails',
method: 'post',
params,
})
}
/** 上报问题反馈详情 */
export function workOrderFeedbackList(params: any) {
return http.request({
url: SW_PATH + '/workOrder/feedback/list',
method: 'get',
params,
})
}
/** 工单处置反馈提交 */
export function workOrderFeedback(data: any) {
return http.request({
url: SW_PATH + '/workOrder/feedback',
method: 'post',
data,
})
}
// ══════════════════════════════════════════════
// 设备 / 监测点
// ══════════════════════════════════════════════
/** 获取监测点位列表 */
export function jcdwList(params: any) {
return http.request({
url: SW_PATH + '/asset/siteEquipment/jcdw/getJcdwList',
method: 'get',
params,
})
}
/** 新增维修管理工单 */
export function workOrderRepair(data: any) {
return http.request({
url: SW_PATH + '/asset/repair/add',
method: 'post',
data,
})
}
/** 获取设备列表(包含监测点信息) */
export function getEquipmentList(params: any) {
return http.request({
url: SW_PATH + '/asset/siteEquipment/equipment/getEquipmentList',
method: 'get',
params,
})
}
// ══════════════════════════════════════════════
// 符号库
// ══════════════════════════════════════════════
/** 获取符号库列表 */
export function querySourceSymbolAll(data: any) {
return http.request({
url: SW_PATH + '/api/v1/sourceNew/querySourceSymbolAll',
method: 'post',
data,
})
}
/** 查询多个符号样式 */
export function querySymbolByScode(params: any) {
return http.request({
url: SW_PATH + '/api/v1/sourceNew/querySymbolByScode',
method: 'post',
params,
})
}

View File

@@ -0,0 +1,96 @@
/**
* 养护考核 API
*
* @module api/maintenanceCheck
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
/**
* 养护考核保存
* @param data
* @param data.khTime 考核时间
* @param data.score 分数
* @param data.type 类型
* @param data.userid 扣分人
* @param data.xzqhdm 行政区划
* @param data.yhId 养护id
* 有问题额外字段
* @param data.checkId 检查项id
* @param data.detail 详细描述
* @param data.pic 图片
* @param data.remake 备注
* @param data.shape 点位
*/
export const saveSwYhKh = (data: any) => {
return http.request({
url: SW_PATH + `/maintenance/saveSwYhKh`,
method: 'post',
data: data,
})
}
/**
* 查询养护考核项
* @param params
* @param params.type 官网, 泵站 , 河道
*/
export function getSwYhKhCheckList(params: any) {
return http.request({
url: SW_PATH + '/maintenance/getSwYhKhCheckList',
method: 'get',
params,
})
}
/**
* 养护考核查询
* @param data
* @param data.time 日期
* @param data.type 类型 管网 河道 泵站
* @param data.xzqhdm 行政区代码
*/
export const getSwYhKhMobileList = (data: any) => {
return http.request({
url: SW_PATH + `/maintenance/getSwYhKhMobileList`,
method: 'post',
data: data,
})
}
/**
* 养护考核查询
* @param data
* @param data.time 日期
* @param data.xzqhdm 行政区代码
*/
export const getSwYhKhList = (data: any) => {
return http.request({
url: SW_PATH + `/maintenance/getSwYhKhList`,
method: 'post',
data: data,
})
}
/**
* 养护考核查询
* @param data
* @param data.time 日期
* @param data.xzqhdm 行政区代码
*/
export const getSwYhKhListDynamic = (data: any) => {
return http.request({
url: SW_PATH + `/maintenance/getSwYhKhListDynamic`,
method: 'post',
data: data,
})
}
export const metaDataFieldQuery = (data: any) => {
return http.request({
url: SW_PATH + `/metaData/field/query`,
method: 'post',
data,
})
}

215
src/api/map.ts Normal file
View File

@@ -0,0 +1,215 @@
/**
* 地图相关 API
*
* @module api/map
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
/**
* 获取防汛设施总览分组
* @param params
* @param params.type 类型 pc/onemap
* @param params.category 分类(可选)
*/
export const getFloodFacilityOverview = (params: any) => {
return http.request({
url: SW_PATH + '/floodMonitoring2/getFloodFacilityOverview',
method: 'get',
params,
})
}
// 获取防汛设备数据总量
export const getFloodDeviceTotal = (data: any) => {
return http.request({
url: SW_PATH + '/asset/oneMap/getFloodTotalNumber',
method: 'get',
params: data,
})
}
/**
* 根据classid和空间信息查询数据(新)
* @param params
* @param params.shape 空间信息(可选)
* @param params.classids classIds
*/
export const queryBasedSpatialInformation = (params: any) => {
return http.request({
url: SW_PATH + '/api/v1/sourceNew/queryBasedSpatialInformation',
method: 'get',
params: params,
})
}
// 查询撒点
export const getTypeList = (params: any) => {
return http.request({
url: SW_PATH + '/asset/oneMap/getTypeList',
method: 'get',
params: params,
})
}
// 查询中央气象台智能网格
export function getGridForecastInfo(data: any) {
return http.request({
url: SW_PATH + '/floodMonitoring2/getGridForecastInfo',
method: 'get',
})
}
/**
* 风场
*/
export function createWindField(data: any) {
return http.request({
url: SW_PATH + '/rainreview/createWindField',
method: 'post',
data,
})
}
export function createGDYBPolygon(params: any) {
return http.request({
url: SW_PATH + '/rainreview/createContourPolygon',
method: 'post',
data: {
...params,
},
})
}
/**
* 根据名称查询设备详情
* @param params
* @param params.name 设备名称
*/
export const getEquipmentDetailByName = (params: any) => {
return http.request({
url: SW_PATH + '/asset/oneMap/getEquipmentDetailByName',
method: 'get',
params: params,
})
}
/**
* 雷达图
*/
export function getLdtDataInfoNew() {
return http.request({
url: SW_PATH + '/floodMonitoring2/getLdtDataInfoNew',
method: 'get',
})
}
/**
* 查询台风路径信息
* @param data
* @param data.name 接口名称(天气预报:yb实时天气预警:yj查询历年台风列表:tflb查询台风轨迹路径:tflj
* @param data.param 查询参数
*/
export const getQweatherApi = (data: any) => {
return http.request({
url: SW_PATH + `/floodMonitoring2/getQweatherApi`,
method: 'post',
data,
})
}
/**
* 查询设施编目目录数据
* @param data
*/
export const getSysResourceCatalogMetadataCountTree = (data: any) => {
return http.request({
url: SW_PATH + `/sysResourceCatalog/getSysResourceCatalogMetadataCountTree`,
method: 'post',
data,
})
}
/**
* 查询设施编目基础类型数据
* @param data
*/
export const metaDataQueryList = (data: any) => {
return http.request({
url: SW_PATH + `/metaData/query/list`,
method: 'post',
data,
})
}
/**
* 通过表分类 获取字段列表
* 表分类id tableclassid/classGuid 必传其中一个
* @param data
* @param data.classGuid 表分类编码(可选)
* @param data.name 名称/别名(可选)
* @param data.tableclassid 表分类id可选
*/
export function getFieldByClass(data: any) {
return http.request({
url: SW_PATH + '/metaData/field/query',
method: 'post',
data,
})
}
/**
* 通过表分类编码 获取表分类信息
* @param classGuid 表分类编码
*/
export function getClassByClassGuid(classGuid: string) {
return http.request({
url: SW_PATH + '/metaData/class/queryByClassGuid',
method: 'get',
params: {
classGuid,
},
})
}
/**
* 获取历史数据监测点监测值类型
* @param params 点位id
*/
export function getFacilityRealTimeData(params: any) {
return http.request({
url: SW_PATH + '/asset/oneMap/getFacilityRealTimeData',
method: 'get',
params,
})
}
/**
* 获取历史数据
* @param params
*/
export function getHistoryData(params: any) {
return http.request({
url: SW_PATH + '/asset/oneMap/getHistoryData',
method: 'get',
params,
})
}
/**
* 地图服务查询
* @param data
* @param data.isDisplay 是否显示(默认显示)
* @param data.isEnabled 是否启用(默认启用)
* @param data.name 名称
* @param data.type 类型
* @param data.code 服务编码
*/
export function getSwDataMapList(data: any) {
return http.request({
url: SW_PATH + `/mapData/getSwDataMapList`,
method: 'post',
data,
})
}

30
src/api/mapService.ts Normal file
View File

@@ -0,0 +1,30 @@
/**
* 地图服务 API
*
* @module api/mapService
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
// 获取所有专题图服务
export function getAllService() {
return http.request({
url: SW_PATH + '/specialService/selectall',
method: 'post',
})
}
/**
* 查询角色和类型对应的服务
* @param data
* @param data.roles [] 角色
* @param data.type 类型(底图(影像,矢量)/ 专题)
*/
export function getServiceListThemeByRole(data: any) {
return http.request({
url: SW_PATH + `/mapData/getServiceListThemeByRole`,
method: 'post',
data,
})
}

28
src/api/menu.ts Normal file
View File

@@ -0,0 +1,28 @@
/**
* 菜单 / 路由 API
*
* @module api/menu
*/
import { http } from '@/utils/http'
/**
* 获取菜单路由
*/
export function getRouters() {
return http.request({
url: '/system/menu/getRouters',
method: 'get',
})
}
/**
* 获取子系统菜单
* @param appId - 子系统 appId
*/
export function getRoutersByAppId(appId: string) {
return http.request({
url: `/system/menu/getRoutersByAppId/${appId}`,
method: 'get',
})
}

68
src/api/menuEdit.ts Normal file
View File

@@ -0,0 +1,68 @@
/**
* 工作台菜单编辑 API
*
* @module api/menuEdit
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
/**
* 获取用户工作台列表
* @param params - 查询参数
*/
export function getUserWorkStationList(params: any) {
return http.request({
url: SW_PATH + '/asset/oneMap/getUserWorkStationList',
method: 'get',
params,
})
}
/**
* 新增分组
* @param data - 分组数据
*/
export function addWorkStationGroup(data: any) {
return http.request({
url: SW_PATH + '/asset/oneMap/addWorkStationGroup',
method: 'post',
data,
})
}
/**
* 删除分组
* @param params - 删除参数
*/
export function deleteWorkStationGroup(params: any) {
return http.request({
url: SW_PATH + '/asset/oneMap/deleteWorkStationGroup',
method: 'delete',
params,
})
}
/**
* 修改分组
* @param data - 分组数据
*/
export function updateWorkStationGroup(data: any) {
return http.request({
url: SW_PATH + '/asset/oneMap/updateWorkStationGroup',
method: 'put',
data,
})
}
/**
* 更新工作台信息
* @param data - 工作台数据
*/
export function updateWorkStationInfo(data: any) {
return http.request({
url: SW_PATH + '/asset/oneMap/updateWorkStationInfo',
method: 'put',
data,
})
}

View File

@@ -0,0 +1,108 @@
/**
* 监测设备 API
*
* @module api/monitoringEquipment
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
// 根据获取电子水尺数据
export function getTypeList(params: any) {
return http.request({
url: SW_PATH + '/asset/oneMap/getTypeList',
method: 'get',
params,
})
}
/**
* 获取雨量站数据
*/
export function getRainStationList(params: any) {
return http.request({
url: SW_PATH + '/asset/oneMap/getRainStationList',
method: 'get',
params,
})
}
/**
* 获取泵站数据
*/
export function getPumpStationList(params: any) {
return http.request({
url: SW_PATH + '/asset/oneMap/getPumpStationList',
method: 'get',
params,
})
}
// v2.0 获取维修记录列表
export const getRepairRecordList = (params: any) => {
return http.request({
url: SW_PATH + '/asset/repair/list',
method: 'get',
params,
})
}
// 获取设备型号的字段列表
export const getList = (data: any) => {
return http.request({
url: SW_PATH + '/asset/sbxhField/sbxhField/getList',
method: 'get',
params: data,
})
}
// 获取历史数据
export const getHistoryData = (data: any) => {
return http.request({
url: SW_PATH + '/asset/oneMap/getHistoryData',
method: 'get',
params: data,
})
}
// 获取app数据总量去掉设施和雨量计
export function getAppTotalNumber(params: any) {
return http.request({
url: SW_PATH + '/asset/oneMap/getAppTotalNumber',
method: 'get',
params,
})
}
// v2.0 获取报警阈值配置列表
export const getAlarmThresholdList = (data: any) => {
return http.request({
url: SW_PATH + '/asset/siteEquipment/warnConfig/getList',
method: 'get',
params: data,
})
}
// 获取报警预警数据
export function getMonitorYjDataPage(data: any) {
return http.request({
url: SW_PATH + `/monitorYjData/getMonitorYjDataPage`,
method: 'post',
data,
})
}
/**
* 获取累计雨量
* @param params
* @param params.startTime 开始时间 '2023-09-20 19:31:47'
* @param params.endTime 结束时间 '2023-09-22 19:31:47'
* @param params.xzqhdm 行政区划代码 ; 分割
*/
export function getRainfallRealtimeByTime(params: any) {
return http.request({
url: SW_PATH + '/floodMonitoring2/getRainfallRealtimeByTime',
method: 'get',
params,
})
}

56
src/api/notice.ts Normal file
View File

@@ -0,0 +1,56 @@
/**
* 消息通知 API
*
* @module api/notice
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
/**
* 获取未读消息列表
* @param params - { pageNum?, pageSize?, supportType? }
*/
export function getUnReadMessages(params: any) {
return http.request({
url: SW_PATH + '/sysMessage/getUnReadMessages',
method: 'get',
params,
})
}
/**
* 获取全部消息列表
* @param params - { pageNum?, pageSize?, supportType? }
*/
export function getAllMessages(params: any) {
return http.request({
url: SW_PATH + '/sysMessage/getAllMessages',
method: 'get',
params,
})
}
/**
* 根据模板 ID 获取消息模板
* @param params - { templateId }
*/
export function getTemplate(params: any) {
return http.request({
url: SW_PATH + '/sysMessage/getTemplate',
method: 'get',
params,
})
}
/**
* 标记消息为已读
* @param params - { recordId }
*/
export function markAsRead(params: any) {
return http.request({
url: SW_PATH + '/sysMessage/markAsRead',
method: 'get',
params,
})
}

View File

@@ -0,0 +1,91 @@
/**
* 项目管理 API
*
* @module api/projectManagement
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
/**
* 监管记录查询 / 项目列表
* @param data - { startTime?, endTime?, stage?, type?, pageNum?, pageSize?, inspectId? }
*/
export function getProjectList(data: any) {
return http.request({
url: SW_PATH + '/project/list',
method: 'post',
data,
})
}
/**
* 我的待办
*/
export function getProjectMyPhoneDeal() {
return http.request({
url: SW_PATH + '/project/myPhoneDeal',
method: 'get',
})
}
/**
* 项目表单详情
* @param params - { projectId, type? }
*/
export function getProjectInfo(params: any) {
return http.request({
url: SW_PATH + '/project/info',
method: 'get',
params,
})
}
/**
* 项目审批
* @param projectId - 项目 id
* @param data - 审批数据
*/
export function projectAudit(projectId: string, data: any) {
return http.request({
url: SW_PATH + '/project/audit/' + projectId,
method: 'post',
data,
})
}
/**
* 移动端监理巡检打卡
* @param data - { address, checkItemJson, createBy, createTime, description, pic, projectId, projectName, shape }
*/
export function getProjectInspectClockin(data: any) {
return http.request({
url: SW_PATH + '/project/inspect/clockin',
method: 'post',
data,
})
}
/**
* 移动端监理巡检问题上报
* @param data - { address, checkItemJson, content, pic, projectId, shape }
*/
export function getProjectInspectReport(data: any) {
return http.request({
url: SW_PATH + '/project/inspect/report',
method: 'post',
data,
})
}
/**
* 查询项目阶段开始时间表
* @param params - { projectId }
*/
export function getProjectStageTime(params: any) {
return http.request({
url: SW_PATH + '/project/stageTime',
method: 'get',
params,
})
}

171
src/api/pshgl.ts Normal file
View File

@@ -0,0 +1,171 @@
/**
* 排水户管理 API
*
* @module api/pshgl
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
/**
* 移动端查询待巡检排水户列表
* @param data
* @param data.mtmc 排水户名称
* @param data.sfxc 是否已巡查0:未巡查,1:已巡查,不传查询全部
* @param data.szdl 所在道路名称
* @param data.szjd 所在街道id
* @param data.xzqh 行政区划id
* @param data.pic 图片
* @param data.projectId 关联项目Id
* @param data.projectName 关联项目name
* @param data.shape 上报问题点位
*/
export function getPshXjPhoneList(data: any) {
return http.request({
url: SW_PATH + '/api/v1/drainage/getPshXjPhoneList',
method: 'post',
data,
})
}
/**
* 移动端排水户巡查打卡
* @param data
* @param data.checkUserId 打卡人id
* @param data.checkUserName 打卡人名称
* @param data.pic 图片
* @param data.pshId 排水户id
* @param data.remark 备注
* @param data.roundId 轮次id
* @param data.shape 巡查打卡位置
* @param data.status 状态 1无问题 2有问题
* @param data.taskId 轮次任务id
* @param data.type 问题类型
* @param data.typeName 问题类型名称
* @param data.wtms 问题描述
*/
export function pshXjPhoneClock(data: any) {
return http.request({
url: SW_PATH + '/api/v1/drainage/pshXjPhoneClock',
method: 'post',
data,
})
}
/**
* 查询排水户所有轮次
* @param params
* @param params.pageNum
* @param params.pageSize
*/
export function listPshXjRound(params: any) {
return http.request({
url: SW_PATH + '/api/v1/drainage/listPshXjRound',
method: 'get',
params,
})
}
/**
* 查询排水户巡查问题列表
* @param data
* @param data.pshName 排水户名称
* @param data.roundId 轮次id
* @param data.shzt 问题状态
* @param data.szjd 所在街道
* @param data.type 问题类型
* @param data.rwId 派发任务Id
* @param data.pageNum
* @param data.pageSize
*/
export function getPshXjProblemList(data: any) {
return http.request({
url: SW_PATH + '/api/v1/drainage/getPshXjProblemList',
method: 'post',
data,
})
}
/**
* 查询排水户巡查问题派发任务列表
* @param data
* @param data.shzt 任务状态
* @param data.pageNum
* @param data.pageSize
*/
export function getPshXjProblemTaskList(data: any) {
return http.request({
url: SW_PATH + '/api/v1/drainage/getPshXjProblemTaskList',
method: 'post',
data,
})
}
/**
* 查询街道考核任务列表
* @param data
* @param data.khTime 考核日期
* @param data.pageNum
* @param data.pageSize
* @param data.status 考核状态:待派发|待接收|进行中|已完成
* @param data.szjd 街道code
*/
export function getPshXjKhPhoneTaskList(data: any) {
return http.request({
url: SW_PATH + '/api/v1/drainage/getPshXjKhPhoneTaskList',
method: 'post',
data,
})
}
/**
* 查询待考核录列表
* @param data
* @param data.taskId 考核任务id
*/
export function getPshXjKhPhoneRecordList(data: any) {
return http.request({
url: SW_PATH + '/api/v1/drainage/getPshXjKhPhoneRecordList',
method: 'post',
data,
})
}
/**
* 上报考核任务
* @param data
* @param data.id id
* @param data.taskId 考核任务id
* @param data.pshId 排水户id
* @param data.status 考核状态:合格,不合格
* @param data.remark 考核描述
* @param data.pic 考核照片;分号分割
*/
export function reportPshXjKhPhoneRecord(data: any) {
return http.request({
url: SW_PATH + '/api/v1/drainage/reportPshXjKhPhoneRecord',
method: 'post',
data,
})
}
/**
* 考核管理-任务操作(派发|接收|撤回)
* @param data
* @param data.jsdw 接收单位reqType=1必填
* @param data.jsdwid 接收单位idreqType=1必填
* @param data.jsrid 接收人idreqType=2必填
* @param data.jsrname 接收人namereqType=2必填
* @param data.pfrid 派发人idreqType=1必填
* @param data.pfrname 派发人namereqType=1必填
* @param data.pshIds 排水户id列表reqType=1必填
* @param data.reqType 操作类型 1派发 2接收 3派发撤回
* @param data.taskId 考核任务id
*/
export function updatePshXjKhTaskStatus(data: any) {
return http.request({
url: SW_PATH + '/api/v1/drainage/updatePshXjKhTaskStatus',
method: 'post',
data,
})
}

103
src/api/supervisor.ts Normal file
View File

@@ -0,0 +1,103 @@
/**
* 三方监管 API
*
* @module api/supervisor
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
// 查询设备当前状态
export function getSupervisionEquipmentMileageStatus(data: any) {
return http.request({
url: SW_PATH + '/threePartySupervision/getSupervisionEquipmentMileageStatus',
method: 'post',
data,
})
}
// 监管检查项目查询
export function getSupervisionCheckItemList(data: any) {
return http.request({
url: SW_PATH + '/threePartySupervision/getSupervisionCheckItemList',
method: 'post',
data,
})
}
// 保存监管设备里程信息
export function saveSupervisionEquipmentMileage(data: any) {
return http.request({
url: SW_PATH + '/threePartySupervision/saveSupervisionEquipmentMileage',
method: 'post',
data,
})
}
// 保存监管记录
export function saveSupervisionRecords(data: any) {
return http.request({
url: SW_PATH + '/threePartySupervision/saveSupervisionRecords',
method: 'post',
data,
})
}
/**
* 监管记录查询
* @param data
* @param data.type 类型
* @param data.xzqhdm 行政区划代码
* @param data.time 监管月份 年月
* @param data.current 当前页码
* @param data.size 每页条数
*/
export function getSupervisionRecordsMobilePage(data: any) {
return http.request({
url: SW_PATH + '/threePartySupervision/getSupervisionRecordsMobilePage',
method: 'post',
data,
})
}
/**
* 保存监管记录问题上报
* @param data
* @param data.userid 用户id
* @param data.facilitiesId 养护任务objectId
* @param data.facilitiesName 养护任务名称
* @param data.facilitiesType 养护任务类型
* @param data.xzqhdm 行政区划代码
* @param data.xzqh 行政区划
* @param data.yhdw 养护单位
* @param data.yhdwId 养护单位id
* @param data.time 问题上报时间
* @param data.x 个人位置
* @param data.y 个人位置
* @param data.address 详细地址
* @param data.problemType 问题类型枚举
* @param data.problemTypeName 问题类型名称
* @param data.describe 问题描述
* @param data.pic 图片url
* @param data.jsdw 接收单位
*/
export function saveSupervisionRecordsProblem(data: any) {
return http.request({
url: SW_PATH + '/threePartySupervision/saveSupervisionRecordsProblem',
method: 'post',
data,
})
}
/**
* 监管记录详情查询
* @param params
* @param params.id 监管记录id
*/
export function getSupervisionRecordsDetail(params: any) {
return http.request({
url: SW_PATH + '/threePartySupervision/getSupervisionRecordsDetail',
method: 'get',
params,
})
}

View File

@@ -1,68 +1,50 @@
/** /**
* 用户相关 API * 用户相关接口
* *
* 包含登录、获取用户信息、退出登录、重置密码等用户模块接口。 * 包含登录、验证码、修改密码、用户查询等用户模块接口。
* 匹配原始 JavaScript APIuser.js的完整行为。
* *
* @module api/user * @module api/user
*/ */
import { post, get } from '@/utils/http' import { http } from '@/utils/http'
import { v4 as uuidv4 } from 'uuid'
import { rsaLong } from '@/utils/rsaUtil'
// ══════════════════════════════════════════════ // ══════════════════════════════════════════════
// 请求参数类型 // 类型定义
// ══════════════════════════════════════════════ // ══════════════════════════════════════════════
/** 登录请求参数 */ /** 登录请求参数 */
export interface LoginParams { export interface LoginUserInfo {
/** 用户名 */
username: string username: string
/** 密码 */
password: string password: string
/** 验证码 */ code: string
code?: string uuid: string
/** 验证码唯一标识 */
uuid?: string
} }
/** 重置密码请求参数 */ /** 修改密码请求参数 */
export interface ResetPasswordParams { export interface UpdatePwdUserInfo {
/** 旧密码 */
oldPassword: string oldPassword: string
/** 新密码 */
newPassword: string newPassword: string
} }
// ══════════════════════════════════════════════ /** 用户查询参数 */
// 响应数据类型 export interface UserQuery {
// ══════════════════════════════════════════════ [key: string]: any
/** 登录返回结果 */
export interface LoginResult {
/** 认证 Token */
token: string
} }
/** 用户信息 */ /** 用户信息 */
export interface UserInfo { export interface UserInfo {
/** 用户 ID */
userId: string | number userId: string | number
/** 用户名 */
userName: string userName: string
/** 昵称 */
nickName: string nickName: string
/** 头像地址 */
avatar: string avatar: string
/** 手机号 */
phonenumber?: string phonenumber?: string
/** 邮箱 */
email?: string email?: string
/** 性别0-男 1-女 2-未知) */
sex?: string sex?: string
/** 部门名称 */
deptName?: string deptName?: string
/** 角色列表 */
roles?: string[] roles?: string[]
/** 权限列表 */
permissions?: string[] permissions?: string[]
} }
@@ -71,35 +53,174 @@ export interface UserInfo {
// ══════════════════════════════════════════════ // ══════════════════════════════════════════════
/** /**
* 用户登录 * 登录
* @param params - 登录参数(用户名、密码、验证码等) *
* @returns 返回包含 Token 的登录结果 * 使用 RSA 加密构造请求体,包含 resource 对象:
* - algorithm: 'RSA'
* - ciphertext: rsaLong(encodeURIComponent(JSON.stringify({...})))
*
* 设置 headers.requireToken = false 跳过 Token 校验。
*/ */
export function login(params: LoginParams): Promise<LoginResult> { export function login(userInfo: LoginUserInfo) {
return post<LoginResult>('/login', params) const uuid = userInfo.uuid
const timestamp = new Date().valueOf()
const code = userInfo.code
const data = {
id: uuid,
uuid,
code,
timestamp,
resource: {
algorithm: 'RSA',
ciphertext: rsaLong(
encodeURIComponent(
JSON.stringify({
username: userInfo.username,
password: userInfo.password,
code: code,
uuId: uuid,
appId: '',
timestamp,
}),
),
),
associatedData: '',
nonce: '',
},
}
return http.request({
url: '/auth/login',
headers: {
requireToken: false,
},
method: 'post',
data,
})
}
/**
* 获取验证码
* @returns 验证码图片
*/
export function getCodeImg() {
return http.request({
url: '/code',
method: 'get',
})
}
/**
* 修改密码
*
* 使用 RSA 加密新旧密码,构造与登录类似的 resource 结构。
*/
export function updateUserPwd(userInfo: UpdatePwdUserInfo) {
const uuid = uuidv4()
const timestamp = new Date().valueOf()
const data = {
id: uuid,
timestamp,
resource: {
algorithm: 'RSA',
ciphertext: rsaLong(
encodeURIComponent(
JSON.stringify({
oldPassword: userInfo.oldPassword,
newPassword: userInfo.newPassword,
timestamp,
}),
),
),
associatedData: '',
nonce: '',
},
}
return http.request({
url: '/system/user/profile/updatePwd',
method: 'put',
data,
})
} }
/** /**
* 获取当前登录用户信息 * 获取当前登录用户信息
* @returns 用户详细信息
*/ */
export function getUserInfo(): Promise<UserInfo> { export function getUserInfo() {
return get<UserInfo>('/getInfo') return http.request({
url: '/system/user/getInfo',
method: 'get',
})
} }
/** /**
* 退出登录 * 查询用户列表
* @returns Promise<void> * @param query - 查询参数
*/ */
export function logout(): Promise<void> { export function listUser(query: UserQuery) {
return post<void>('/logout') return http.request({
url: '/system/user/list',
method: 'get',
params: query,
})
} }
/** /**
* 重置密码 * 根据用户 ID 查询上三级部门负责人
* @param params - 旧密码和新密码 * @param userId - 用户 ID
* @returns Promise<void>
*/ */
export function resetPassword(params: ResetPasswordParams): Promise<void> { export function getHierarchicalLeader(userId: string | number) {
return post<void>('/system/user/profile/resetPwd', params) return http.request({
url: `/system/user/getHierarchicalLeader/${userId}`,
method: 'get',
})
} }
/**
* 根据部门 IDs 查询用户列表
* @param deptIds - 部门 ID 数组
*/
export function getUserListByDeptIds(deptIds: (string | number)[]) {
const query = deptIds.map((id) => `deptIds=${id}`).join('&')
return http.request({
url: `/system/user/getUserListByDeptIds?${query}`,
method: 'get',
})
}
/**
* 根据用户 IDs 查询用户列表
* @param userIds - 用户 ID 数组
*/
export function getUserListByIds(userIds: (string | number)[]) {
const query = userIds.map((id) => `userIds=${id}`).join('&')
return http.request({
url: `/system/user/getUserListByIds?${query}`,
method: 'get',
})
}
/**
* 根据岗位 IDs 查询用户列表
* @param postIds - 岗位 ID 数组
*/
export function getUserListByPostIds(postIds: (string | number)[]) {
const query = postIds.map((id) => `postIds=${id}`).join('&')
return http.request({
url: `/system/user/getUserListByPostIds?${query}`,
method: 'get',
})
}
/**
* 根据角色 IDs 查询用户列表
* @param roleIds - 角色 ID 数组
*/
export function getUserListByRoleIds(roleIds: (string | number)[]) {
const query = roleIds.map((id) => `roleIds=${id}`).join('&')
return http.request({
url: `/system/user/getUserListByRoleIds?${query}`,
method: 'get',
})
}
export default login

340
src/api/workflow.ts Normal file
View File

@@ -0,0 +1,340 @@
/**
* 工作流 API
*
* 包含流程详情、审批、待办/已办/发起、退回、催办、
* 委派、转办、监督、节点超时等接口。
* 大部分接口不使用 SW_PATH直接走 /icp-bpm-manage 前缀。
*
* @module api/workflow
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
import dayjs from 'dayjs'
/**
* 查询流程详情(不带 taskId 则查询当前任务)
* @param params - { procInsId: string, taskId?: string }
*/
export function getProcessDetail(params: any) {
return http.request({
url: '/icp-bpm-manage/api/v1/process/detail',
method: 'get',
params,
})
}
/**
* 获取审批人列表
* @param data - { procInsId: string, taskId: string }
*/
export function getApproveList(data: any) {
return http.request({
url: '/icp-bpm-manage/api/v1/task/getApproveList',
method: 'post',
data,
})
}
/**
* 同意 — 结束当前任务节点
* @param data - { taskId, procInsId, userId, nextUserIds, comment }
*/
export function finishedTaskNode(data: any) {
return http.request({
url: '/icp-bpm-manage/api/v1/task/finished',
method: 'post',
data,
})
}
/**
* 不同意 — 拒绝当前任务节点
* @param data - { taskId, procInsId, userId, comment }
*/
export function rejectTask(data: any) {
return http.request({
url: '/icp-bpm-manage/api/v1/task/reject',
method: 'post',
data,
})
}
/**
* 结束流程
* @param data - { taskId, procInsId, userId }
*/
export function stopTask(data: any) {
return http.request({
url: '/icp-bpm-manage/api/v1/process/stop',
method: 'post',
data,
})
}
/**
* 查询我的待办
* @param data - { processName?, params?, userInfo, pageNum?, pageSize? }
*/
export function getMyTodoList(data: any) {
return http.request({
url: '/icp-bpm-manage/api/v1/task/my/todo',
method: 'post',
data: {
pageNum: 1,
pageSize: 5,
...data,
},
})
}
/**
* 查询我的已办
* @param data - { processName?, params?, userInfo, pageNum?, pageSize? }
*/
export function getMyFinishedList(data: any) {
return http.request({
url: '/icp-bpm-manage/api/v1/task/my/finished',
method: 'post',
data: {
pageNum: 1,
pageSize: 5,
...data,
},
})
}
/**
* 查询我发起的
* @param data - { processName?, params?, userInfo, pageNum?, pageSize? }
*/
export function getMyStartList(data: any) {
return http.request({
url: '/icp-bpm-manage/api/v1/process/my',
method: 'post',
data: {
pageNum: 1,
pageSize: 5,
...data,
},
})
}
/**
* 查询可回退的节点
* @param data - { procInsId, taskId, userId }
*/
export function getReturnNodes(data: any) {
return http.request({
url: '/icp-bpm-manage/api/v1/process/returnNodes',
method: 'post',
data,
})
}
/**
* 退回到指定节点
* @param data - { procInsId, taskId, userId, targetKey, comment }
*/
export function returnTask(data: any) {
return http.request({
url: '/icp-bpm-manage/api/v1/task/return',
method: 'post',
data,
})
}
/**
* 取回 / 撤回
* @param data - { procInsId, taskId, userId }
*/
export function revokeTask(data: any) {
return http.request({
url: '/icp-bpm-manage/api/v1/task/revoke',
method: 'post',
data,
})
}
/**
* 催办
* @param data - { proInsId, enable?, msgType?, msgText?, name? }
*/
export function urgingTask(data: any) {
return http.request({
url: '/icp-bpm-manage/api/v1/task/urging',
method: 'post',
data: {
enable: true,
msgType: 'INTERNAL',
msgText: '催办',
name: '催办',
...data,
},
})
}
/**
* 更新流程状态(挂起 / 激活)
* @param params - { instanceId, state? }
*/
export function updateProcessState(params: any) {
return http.request({
url: '/icp-bpm-manage/api/v1/process/updateState',
method: 'put',
params: {
state: 'suspended',
...params,
},
})
}
/**
* 删除流程实例
* @param instanceIds - 流程实例 id多个逗号分隔
* @param params - { force?, reason? }
*/
export function deleteProcessInstance(instanceIds: string, params: any = {}) {
return http.request({
url: `/icp-bpm-manage/api/v1/process/instance/${instanceIds}`,
method: 'delete',
params: {
force: 'true',
reason: '',
...params,
},
})
}
/**
* 加签(委派任务)
* @param userId - 要委派的用户 id
* @param taskId - 流程节点 id
*/
export function setTaskDelegateUser(userId: string, taskId: string) {
return http.request({
url: `/icp-bpm-manage/api/v1/task/delegate/${taskId}/${userId}`,
method: 'put',
})
}
/**
* 转办任务
* @param acceptUserId - 接受人 id
* @param currentUserId - 当前人 id
* @param taskId - 任务 id
*/
export function setTaskTransfer(acceptUserId: string, currentUserId: string, taskId: string) {
return http.request({
url: `/icp-bpm-manage/api/v1/task/transfer/${taskId}/${currentUserId}/${acceptUserId}`,
method: 'get',
})
}
/**
* 获取用户列表
* @param params - { pageNum?, pageSize?, nickName?, status? }
*/
export function getUserList(params: any = {}) {
return http.request({
url: '/system/user/list',
method: 'get',
params: {
pageNum: 1,
nickName: '',
pageSize: 9999999,
status: 0,
...params,
},
})
}
/**
* 添加监督意见
* @param data - { userId, procInsId, remark }
*/
export function addSuperviseComment(data: any) {
return http.request({
url: '/icp-bpm-manage/api/v1/task/supervise/comment',
method: 'post',
data,
})
}
/**
* 取消监督
* @param data - { userId, proInsId }
*/
export function cancelSupervise(data: any) {
return http.request({
url: '/icp-bpm-manage/api/v1/task/supervise/cancel',
method: 'post',
data,
})
}
/**
* 获取任务指定属性
* @param taskId - 任务 id
* @param attributeNames - 属性名称数组
*/
export function getTaskAttribute(taskId: string, attributeNames: string[]) {
return http.request({
url: '/icp-bpm-manage/api/v1/task/getTaskAttribute',
method: 'get',
params: {
taskId,
attributeNames: attributeNames.join(','),
},
})
}
/**
* 获取任务下一节点指定属性
* @param taskId - 任务 id
* @param attributeNames - 属性名称数组
*/
export function getNextTaskAttribute(taskId: string, attributeNames: string[]) {
return http.request({
url: '/icp-bpm-manage/api/v1/task/getNextTaskAttribute',
method: 'get',
params: {
taskId,
attributeNames: attributeNames.join(','),
},
})
}
/**
* 查询工单流程详情
* @param procInsId - 流程实例 id
*/
export function getProcessDetailNew(procInsId: string) {
return http.request({
url: `${SW_PATH}/workOrder/getProcessDetail`,
method: 'get',
params: {
procInsId,
},
})
}
/**
* 设置节点超时时间
* @param params - { proInsId, taskId, type?, timeout }
*/
export function setNodeTimeout(params: any) {
const { proInsId, taskId, type = 'cs', timeout } = params
// 将截止时间转换为 cron 表达式(秒 分 时 日 月 年)
const cronExpress = dayjs(timeout).format('s m H D M ?')
return http.request({
url: `${SW_PATH}/workOrder/setNodeTimeout`,
method: 'get',
params: {
proInsId,
taskId,
type,
cronExpress,
},
})
}

68
src/api/xjgl.ts Normal file
View File

@@ -0,0 +1,68 @@
/**
* 工程上报管理 API巡检管理
*
* @module api/xjgl
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
/**
* 工程上报数据保存
* @param data - { address, endTime, msg, startTime, userId, username, pic, remark, shape, cjdw, jsdw }
*/
export function saveSwDataEngineeringReporting(data: any) {
return http.request({
url: SW_PATH + '/engineeringReportingData/saveSwDataEngineeringReporting',
method: 'post',
data,
})
}
/**
* 工程上报数据分页查询
* @param data - { current, size }
*/
export function getSwDataEngineeringReportingPage(data: any) {
return http.request({
url: SW_PATH + '/engineeringReportingData/getSwDataEngineeringReportingPage',
method: 'post',
data,
})
}
/**
* 工程上报数据更新
* @param data - { id, endTime }
*/
export function updateSwDataEngineeringReporting(data: any) {
return http.request({
url: SW_PATH + '/engineeringReportingData/updateSwDataEngineeringReporting',
method: 'post',
data,
})
}
/**
* 工程上报跟踪数据保存
* @param data - { pic, remark, reportingid, status, time }
*/
export function saveSwDataEngineeringReportingDetail(data: any) {
return http.request({
url: SW_PATH + '/engineeringReportingData/saveSwDataEngineeringReportingDetail',
method: 'post',
data,
})
}
/**
* 工程上报详情
* @param params - { id }
*/
export function getSwDataEngineeringReportingVo(params: any) {
return http.request({
url: SW_PATH + '/engineeringReportingData/getSwDataEngineeringReportingVo',
method: 'get',
params,
})
}

68
src/api/yxkjzyRecords.ts Normal file
View File

@@ -0,0 +1,68 @@
/**
* 有限空间作业记录 API
*
* @module api/yxkjzyRecords
*/
import { http } from '@/utils/http'
import { SW_PATH } from '@/config/apiConfig'
/**
* 有限空间作业分页查询
* @param data - { current, order?, name?, sidx?, size?, sort?, xzqhdm? }
*/
export function getSwDataYxkjzyPage(data: any) {
return http.request({
url: SW_PATH + '/yxkjzyData/getSwDataYxkjzyPage',
method: 'post',
data,
})
}
/**
* 有限空间作业详情
* @param params - { id }
*/
export function getSwDataYxkjzy(params: any) {
return http.request({
url: SW_PATH + '/yxkjzyData/getSwDataYxkjzy',
method: 'get',
params,
})
}
/**
* 有限空间作业数据提交
* @param data - { id, xzqhdm, userid }
*/
export function saveSwDataYxkjzySubmit(data: any) {
return http.request({
url: SW_PATH + '/yxkjzyData/saveSwDataYxkjzySubmit',
method: 'post',
data,
})
}
/**
* 有限空间作业修改
* @param data - { id, shzt }
*/
export function updateSwDataYxkjzy(data: any) {
return http.request({
url: SW_PATH + '/yxkjzyData/updateSwDataYxkjzy',
method: 'post',
data,
})
}
/**
* 有限空间作业检查井修改
* @param data - { id, pic }
*/
export function updateSwDataYxkjzyManholes(data: any) {
return http.request({
url: SW_PATH + '/yxkjzyData/updateSwDataYxkjzyManholes',
method: 'post',
data,
})
}

12
src/config/apiConfig.ts Normal file
View File

@@ -0,0 +1,12 @@
/**
* API 配置常量
*
* 从 window.globalConfig 读取运行时配置,
* 提供 SW_PATH 等服务路径前缀供 API 模块使用。
*
* @module config/apiConfig
*/
/** 服务路径前缀(如 /wisdomwatersm用于拼接业务接口 URL */
export const SW_PATH: string =
(typeof window !== 'undefined' && window.globalConfig?.api?.swPath) || ''

View File

@@ -37,6 +37,8 @@ export interface ApiConfig {
baseURL: string baseURL: string
/** API 主机地址(图片上传下载等场景) */ /** API 主机地址(图片上传下载等场景) */
host: string host: string
/** 服务路径前缀(如 /wisdomwatersm */
swPath: string
/** WebSocket 连接地址 */ /** WebSocket 连接地址 */
wsURL?: string wsURL?: string
/** 请求超时时间(毫秒) */ /** 请求超时时间(毫秒) */

View File

@@ -12,9 +12,8 @@ import { ref, computed } from 'vue'
import { useTokenStore } from './token' import { useTokenStore } from './token'
import { import {
login as loginApi, login as loginApi,
logout as logoutApi,
getUserInfo as getUserInfoApi, getUserInfo as getUserInfoApi,
type LoginParams, type LoginUserInfo,
type UserInfo, type UserInfo,
} from '@/api' } from '@/api'
@@ -95,18 +94,20 @@ export const useUserStore = defineStore('user', () => {
/** /**
* 用户登录 * 用户登录
* *
* 调用登录接口获取 Token并写入 Token Store。 * 调用 RSA 加密登录接口获取 Token并写入 Token Store。
* 登录成功后自动调用 getUserInfo 获取用户详细信息。 * 登录成功后自动调用 getUserInfo 获取用户详细信息。
* *
* @param params - 登录参数(用户名、密码、验证码等) * @param params - 登录参数(用户名、密码、验证码等)
* @returns 登录成功后返回的 Token * @returns 登录成功后返回的 Token
*/ */
async function login(params: LoginParams): Promise<string> { async function login(params: LoginUserInfo): Promise<string> {
const tokenStore = useTokenStore() const tokenStore = useTokenStore()
const res = await loginApi(params) const res: any = await loginApi(params)
tokenStore.setToken(res.token) // 登录响应: { code, msg, data: { token } } 或直接 { token }
const token = res.data?.token ?? res.token
tokenStore.setToken(token)
await getUserInfo() await getUserInfo()
return res.token return token
} }
/** /**
@@ -116,27 +117,34 @@ export const useUserStore = defineStore('user', () => {
* roles 和 permissions 列表。 * roles 和 permissions 列表。
*/ */
async function getUserInfo(): Promise<void> { async function getUserInfo(): Promise<void> {
const info = await getUserInfoApi() const info: any = await getUserInfoApi()
userInfo.value = info userInfo.value = info.data ?? info
roles.value = info.roles ?? [] roles.value = (info.data ?? info).roles ?? []
permissions.value = info.permissions ?? [] permissions.value = (info.data ?? info).permissions ?? []
}
/**
* 登录成功后设置 Token 并加载用户信息
*
* 供登录页面直接调用(绕过 store.login 的 RSA 加密)。
*
* @param token - 从登录接口返回的 access_token
*/
function setTokenFromLogin(token: string): void {
const tokenStore = useTokenStore()
tokenStore.setToken(token)
} }
/** /**
* 退出登录 * 退出登录
* *
* 调用后端退出接口,清除 Token Store 中的 Token * 清除 Token Store 中的 Token并将当前 Store 状态重置为初始值。
* 并将当前 Store 状态重置为初始值 * 原始后端无服务端登出接口,仅清除前端状态
*/ */
async function logout(): Promise<void> { async function logout(): Promise<void> {
const tokenStore = useTokenStore() const tokenStore = useTokenStore()
try { tokenStore.clearToken()
await logoutApi() $reset()
} finally {
// 无论接口调用成功与否,前端都必须清除登录状态
tokenStore.clearToken()
$reset()
}
} }
/** /**
@@ -186,6 +194,7 @@ export const useUserStore = defineStore('user', () => {
login, login,
getUserInfo, getUserInfo,
logout, logout,
setTokenFromLogin,
hasPermission, hasPermission,
hasRole, hasRole,
$reset, $reset,

8
src/types/encryptlong.d.ts vendored Normal file
View File

@@ -0,0 +1,8 @@
declare module 'encryptlong' {
export class JSEncrypt {
setPublicKey(key: string): void
encryptLong(text: string): string | false
encrypt(text: string): string | false
decrypt(text: string): string | false
}
}

View File

@@ -5,8 +5,10 @@
* Token 管理以及类型安全的请求方法。 * Token 管理以及类型安全的请求方法。
* *
* - baseURL 从 window.globalConfig.api.baseURL 读取,回退到 '/dev-api' * - baseURL 从 window.globalConfig.api.baseURL 读取,回退到 '/dev-api'
* - 请求拦截器自动附加 Authorization Token * - 请求拦截器自动附加 Authorization Token(无 "Bearer " 前缀)
* - 响应拦截器自动解包数据并统一错误提示 * - requireToken: false 时跳过 Token 附加
* - 响应拦截器校验 code === 200 || code === 0
* - 内置 uploadFile 方法用于文件上传
* *
* @module utils/http * @module utils/http
*/ */
@@ -25,7 +27,7 @@ import { showFailToast } from 'vant'
/** 后端统一响应结构 */ /** 后端统一响应结构 */
export interface ApiResponse<T = unknown> { export interface ApiResponse<T = unknown> {
/** 状态码200 表示成功 */ /** 状态码200 或 0 表示成功 */
code: number code: number
/** 响应数据 */ /** 响应数据 */
data: T data: T
@@ -71,13 +73,13 @@ export function removeToken(): void {
* Axios 实例 * Axios 实例
* *
* - baseURL优先读取 window.globalConfig.api.baseURL不存在时使用 '/dev-api' * - baseURL优先读取 window.globalConfig.api.baseURL不存在时使用 '/dev-api'
* - timeout30 秒超时 * - timeout60 秒超时(匹配原始行为)
*/ */
const http: AxiosInstance = axios.create({ const http: AxiosInstance = axios.create({
baseURL: baseURL:
(typeof window !== 'undefined' && window.globalConfig?.api?.baseURL) || (typeof window !== 'undefined' && window.globalConfig?.api?.baseURL) ||
'/dev-api', '/dev-api',
timeout: 30_000, timeout: 60_000,
}) })
// ══════════════════════════════════════════════ // ══════════════════════════════════════════════
@@ -88,13 +90,18 @@ const http: AxiosInstance = axios.create({
* 请求拦截器 * 请求拦截器
* *
* 在每次请求发出前,自动从 localStorage 读取 Token * 在每次请求发出前,自动从 localStorage 读取 Token
* 并附加到请求头的 Authorization 字段中。 * 并附加到请求头的 Authorization 字段中(无 "Bearer " 前缀)
* 当配置 headers.requireToken === false 时跳过 Token 附加。
*/ */
http.interceptors.request.use( http.interceptors.request.use(
(config: InternalAxiosRequestConfig) => { (config: InternalAxiosRequestConfig) => {
// requireToken 为 false 时跳过(如登录接口)
if (config.headers?.requireToken === false) {
return config
}
const token = getToken() const token = getToken()
if (token && config.headers) { if (token && config.headers) {
config.headers.Authorization = `Bearer ${token}` config.headers.Authorization = token
} }
return config return config
}, },
@@ -110,36 +117,48 @@ http.interceptors.request.use(
/** /**
* 响应拦截器 * 响应拦截器
* *
* - 成功code === 200解包返回 response.data.data * - 文件/blob/arraybuffer 响应直接透传
* - 业务异常:弹出错误提示并 reject * - 成功code === 200 || code === 0返回 response.data 完整对象 {code, msg, data}
* - 网络异常:弹出错误提示并 reject * - 401清除 Token延时跳转登录
* - 其他错误码:弹出错误提示并 reject
*/ */
let redirectTimer: ReturnType<typeof setTimeout> | null = null
http.interceptors.response.use( http.interceptors.response.use(
(response): AxiosResponse | Promise<AxiosResponse> => { (response: AxiosResponse): AxiosResponse | Promise<AxiosResponse> => {
// 文件下载等特殊响应blob / arraybuffer直接返回
if (
response.config.responseType === 'blob' ||
response.config.responseType === 'arraybuffer'
) {
return response
}
const res = response.data as ApiResponse const res = response.data as ApiResponse
// 文件下载等特殊响应(非 JSON直接返回 // 成功code === 200 或 code === 0
if (response.config.responseType === 'blob') { if (res.code === 200 || res.code === 0) {
return response return response.data
} }
if (res.code === 200) { // 401 未授权:跳转登录
// 解包:将 response.data 替换为业务数据 if (res.code === 401) {
response.data = res.data showFailToast(res.msg || '登录已过期,请重新登录')
return response removeToken()
if (redirectTimer) clearTimeout(redirectTimer)
redirectTimer = setTimeout(() => {
window.location.href = '#/login'
}, 500)
return Promise.reject(response.data)
} }
// 业务错误码处理 // 其他业务错误
const errMsg = res.msg || '请求失败' const errMsg = res.msg || '请求失败'
showFailToast(errMsg) showFailToast(errMsg)
return Promise.reject(response.data)
// Token 过期等特殊错误码可在此扩展处理
// if (res.code === 401) { removeToken(); /* 跳转登录 */ }
return Promise.reject(new Error(errMsg))
}, },
(error: unknown) => { (error: unknown) => {
let msg = '网络错误,请稍后重试' let msg = '接口请求失败'
if (axios.isAxiosError(error)) { if (axios.isAxiosError(error)) {
const resData = error.response?.data as ApiResponse | undefined const resData = error.response?.data as ApiResponse | undefined
@@ -154,7 +173,10 @@ http.interceptors.response.use(
if (status === 401) { if (status === 401) {
msg = '登录已过期,请重新登录' msg = '登录已过期,请重新登录'
removeToken() removeToken()
// TODO: 跳转登录页 if (redirectTimer) clearTimeout(redirectTimer)
redirectTimer = setTimeout(() => {
window.location.href = '#/login'
}, 500)
} else if (status === 403) { } else if (status === 403) {
msg = '没有操作权限' msg = '没有操作权限'
} else if (status === 404) { } else if (status === 404) {
@@ -171,6 +193,27 @@ http.interceptors.response.use(
}, },
) )
// ══════════════════════════════════════════════
// 文件上传方法(挂载在 http 实例上)
// ══════════════════════════════════════════════
/**
* 文件上传
*
* 使用 multipart/form-data 格式上传文件。
* 匹配原始 uploadFile 行为。
*
* @param formData - 包含文件的 FormData 对象
* @returns Promise<ApiResponse>
*/
;(http as any).uploadFile = (formData: FormData) => {
return http.post('/file/file-minio/object/upload', formData, {
headers: {
'Content-Type': 'multipart/form-data',
},
})
}
// ══════════════════════════════════════════════ // ══════════════════════════════════════════════
// 类型安全的请求方法 // 类型安全的请求方法
// ══════════════════════════════════════════════ // ══════════════════════════════════════════════
@@ -233,5 +276,8 @@ export async function del<T>(
return http.delete(url, config) as Promise<T> return http.delete(url, config) as Promise<T>
} }
/** 导出原始的 Axios 实例,供特殊场景(如文件上传进度监听)使用 */ /** 导出 http 实例(命名导出,供 API 模块使用 */
export { http }
/** 导出原始的 Axios 实例作为默认导出,供特殊场景使用 */
export default http export default http

25
src/utils/rsaUtil.ts Normal file
View File

@@ -0,0 +1,25 @@
/**
* RSA 长文本加密工具
*
* 匹配原始 rsaUtil.js 的完整行为。
* 使用 encryptlong 对长文本进行分段加密。
*/
import { JSEncrypt as EncryptLong } from 'encryptlong'
/**
* 公钥 - 与后端加密通信的密钥
*/
const PUBLIC_KEY =
'MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCExx/4MM/1MXOGt0XFT6zDmAVNbuyuFY3y/+YlBJxFUreQBnAcuq76sg6h40ZmffAARjuomcHzCCM7WbZp3rfuP7qBxERgvTbADKmt4q05b4ddl7q19EjULHIcbfKjD+m8q8iqX2Ygwj10vLSiDUBE78HWGd3Zwy4O8zKoohsFAwIDAQAB'
/**
* RSA 长文本加密
* @param str - 待加密的字符串
* @returns 加密后的密文
*/
export const rsaLong = (str: string): string => {
const encryptor = new EncryptLong()
encryptor.setPublicKey(PUBLIC_KEY)
return encryptor.encryptLong(str) as string
}

View File

@@ -9,8 +9,8 @@ import { ref, onMounted, onUnmounted } from 'vue'
import { useRouter } from 'vue-router' import { useRouter } from 'vue-router'
import { useUserStore } from '@/stores/user' import { useUserStore } from '@/stores/user'
import { useAppStore } from '@/stores/app' import { useAppStore } from '@/stores/app'
import { getCaptcha } from '@/api/common' import { getCodeImg, login } from '@/api/user'
import { showToast, Checkbox } from 'vant' import { showToast } from 'vant'
const router = useRouter() const router = useRouter()
const userStore = useUserStore() const userStore = useUserStore()
@@ -26,70 +26,59 @@ const password = ref('')
const code = ref('') const code = ref('')
const uuid = ref('') const uuid = ref('')
const codeUrl = ref('') const codeUrl = ref('')
const captchaEnabled = ref(false) const captchaEnabled = ref(true) // 默认开启,调接口后更新
const loading = ref(false) const loading = ref(false)
const savePsw = ref(true) const savePsw = ref(true)
const isInputActive = ref(false) const isInputActive = ref(false)
// 恢复记住的账号密码 // 恢复记住的账号密码key 对齐原始 zhsw-user / zhsw-password
username.value = localStorage.getItem('yuto-user') || '' username.value = localStorage.getItem('zhsw-user') || ''
password.value = localStorage.getItem('yuto-password') || '' password.value = localStorage.getItem('zhsw-password') || ''
// ── 获取验证码 ── // ── 获取验证码(对齐原始 getCodeImgs ──
async function fetchCaptcha(): Promise<void> { function getCodeImgs(): void {
try { getCodeImg().then((res: any) => {
const res = await getCaptcha() captchaEnabled.value = res.captchaEnabled === undefined ? true : res.captchaEnabled
captchaEnabled.value = res.captchaEnabled if (captchaEnabled.value) {
if (res.captchaEnabled) {
codeUrl.value = 'data:image/gif;base64,' + res.img codeUrl.value = 'data:image/gif;base64,' + res.img
uuid.value = res.uuid uuid.value = res.uuid
} }
} catch { }).catch(() => { /* 验证码获取失败不阻塞 */ })
// 验证码获取失败,不阻塞登录流程
}
} }
// ── 提交登录 ── // ── 提交登录(对齐原始 onSubmit ──
async function onSubmit(): Promise<void> { function onSubmit(): void {
if (!username.value) { if (!username.value) { showToast('请输入账号'); return }
showToast('请输入账号') if (!password.value) { showToast('请输入密码'); return }
return if (captchaEnabled.value && !code.value) { showToast('请输入验证码'); return }
}
if (!password.value) {
showToast('请输入密码')
return
}
if (captchaEnabled.value && !code.value) {
showToast('请输入验证码')
return
}
loading.value = true loading.value = true
try { // 对齐原始:始终传 code 和 uuid
await userStore.login({ login({
username: username.value, username: username.value,
password: password.value, password: password.value,
code: captchaEnabled.value ? code.value : undefined, code: code.value,
uuid: captchaEnabled.value ? uuid.value : undefined, uuid: uuid.value,
}) } as any).then((res: any) => {
// 原始响应: { code: 200, data: { access_token: '...' } }
// 记住密码 const token = res.data?.access_token ?? res.access_token
localStorage.setItem('yuto-user', username.value) userStore.setTokenFromLogin(token)
localStorage.setItem('zhsw-user', username.value)
if (savePsw.value) { if (savePsw.value) {
localStorage.setItem('yuto-password', password.value) localStorage.setItem('zhsw-password', password.value)
} else { } else {
localStorage.removeItem('yuto-password') localStorage.setItem('zhsw-password', '')
} }
showToast('登录成功') showToast('登录成功')
router.replace('/home') router.replace('/home')
} catch { }).catch(() => {
// 错误已在拦截器中统一处理 // 错误已在拦截器中统一处理
} finally { }).finally(() => {
loading.value = false loading.value = false
code.value = '' code.value = ''
fetchCaptcha() uuid.value = ''
} getCodeImgs()
})
} }
// ── 隐私政策 ── // ── 隐私政策 ──
@@ -109,7 +98,7 @@ onMounted(() => {
version.value = appStore.globalConfig.system.version || version.value version.value = appStore.globalConfig.system.version || version.value
} }
window.addEventListener('resize', handleResize) window.addEventListener('resize', handleResize)
fetchCaptcha() getCodeImgs()
}) })
onUnmounted(() => { onUnmounted(() => {
@@ -172,7 +161,7 @@ onUnmounted(() => {
class="login-captcha-img" class="login-captcha-img"
:src="codeUrl" :src="codeUrl"
alt="验证码" alt="验证码"
@click="fetchCaptcha" @click="getCodeImgs"
/> />
</template> </template>
</van-field> </van-field>

View File

@@ -8,7 +8,7 @@
import { ref, reactive } from 'vue' import { ref, reactive } from 'vue'
import { useRouter } from 'vue-router' import { useRouter } from 'vue-router'
import { showSuccessToast, showFailToast } from 'vant' import { showSuccessToast, showFailToast } from 'vant'
import { resetPassword } from '@/api' import { updateUserPwd } from '@/api'
const router = useRouter() const router = useRouter()
@@ -60,7 +60,7 @@ async function handleSubmit(): Promise<void> {
loading.value = true loading.value = true
try { try {
await resetPassword({ await updateUserPwd({
oldPassword: pwdForm.oldPassword, oldPassword: pwdForm.oldPassword,
newPassword: pwdForm.newPassword, newPassword: pwdForm.newPassword,
}) })