diff --git a/bank-backend/controllers/employeeController.js b/bank-backend/controllers/employeeController.js index 80a1eff..dfd4730 100644 --- a/bank-backend/controllers/employeeController.js +++ b/bank-backend/controllers/employeeController.js @@ -46,7 +46,7 @@ const getEmployees = async (req, res) => { where, limit, offset, - order: [['createdAt', 'DESC']], + order: [['created_at', 'DESC']], attributes: { exclude: ['password'] // 不返回密码 } diff --git a/bank-backend/controllers/loanApplicationController.js b/bank-backend/controllers/loanApplicationController.js index faf22ba..0862680 100644 --- a/bank-backend/controllers/loanApplicationController.js +++ b/bank-backend/controllers/loanApplicationController.js @@ -35,6 +35,9 @@ const getApplications = async (req, res) => { where.customer_phone = { [Op.like]: `%${searchValue}%` }; } else if (searchField === 'customerIdCard') { where.customer_id_card = { [Op.like]: `%${searchValue}%` }; + } else if (searchField === 'applicationNumber') { + // 数据库中实际没有applicationNumber字段,使用id作为替代 + where.id = { [Op.like]: `%${searchValue}%` }; } } @@ -47,8 +50,17 @@ const getApplications = async (req, res) => { const offset = (parseInt(page) - 1) * parseInt(pageSize); const limit = parseInt(pageSize); - // 排序参数 - const order = [[sortField, sortOrder.toUpperCase()]]; + // 排序参数 - 映射字段名 + const fieldMapping = { + 'createdAt': 'created_at', + 'updatedAt': 'updated_at', + 'applicationDate': 'application_date', + 'loanAmount': 'loan_amount', + 'loanTerm': 'loan_term', + 'interestRate': 'interest_rate' + }; + const dbSortField = fieldMapping[sortField] || sortField; + const order = [[dbSortField, sortOrder.toUpperCase()]]; // 查询数据 const { count, rows } = await LoanApplication.findAndCountAll({ diff --git a/bank-backend/controllers/loanContractController.js b/bank-backend/controllers/loanContractController.js index b8dc98e..812817e 100644 --- a/bank-backend/controllers/loanContractController.js +++ b/bank-backend/controllers/loanContractController.js @@ -37,6 +37,9 @@ const getContracts = async (req, res) => { where.customer_phone = { [Op.like]: `%${searchValue}%` }; } else if (searchField === 'customerIdCard') { where.customer_id_card = { [Op.like]: `%${searchValue}%` }; + } else if (searchField === 'applicationNumber') { + // 数据库中实际没有applicationNumber字段,使用id作为替代 + where.id = { [Op.like]: `%${searchValue}%` }; } } @@ -49,8 +52,17 @@ const getContracts = async (req, res) => { const offset = (parseInt(page) - 1) * parseInt(pageSize); const limit = parseInt(pageSize); - // 排序参数 - const order = [[sortField, sortOrder.toUpperCase()]]; + // 排序参数 - 映射字段名 + const fieldMapping = { + 'createdAt': 'created_at', + 'updatedAt': 'updated_at', + 'contractDate': 'contract_date', + 'loanAmount': 'loan_amount', + 'loanTerm': 'loan_term', + 'interestRate': 'interest_rate' + }; + const dbSortField = fieldMapping[sortField] || sortField; + const order = [[dbSortField, sortOrder.toUpperCase()]]; // 查询数据 const { count, rows } = await LoanContract.findAndCountAll({ diff --git a/bank-backend/controllers/loanProductController.js b/bank-backend/controllers/loanProductController.js index 2174a18..fcb46bf 100644 --- a/bank-backend/controllers/loanProductController.js +++ b/bank-backend/controllers/loanProductController.js @@ -200,6 +200,14 @@ const createLoanProduct = async (req, res) => { }); } + // 检查用户信息 + if (!req.user || !req.user.id) { + return res.status(401).json({ + success: false, + message: '用户信息无效' + }); + } + const product = await LoanProduct.create({ productName, loanAmount, diff --git a/bank-backend/models/Employee.js b/bank-backend/models/Employee.js index 6f07ab4..f0d2f46 100644 --- a/bank-backend/models/Employee.js +++ b/bank-backend/models/Employee.js @@ -68,21 +68,14 @@ module.exports = (sequelize) => { type: DataTypes.DATE, allowNull: true, comment: '锁定到期时间' - }, - createdBy: { - type: DataTypes.INTEGER, - allowNull: true, - comment: '创建人ID' - }, - updatedBy: { - type: DataTypes.INTEGER, - allowNull: true, - comment: '更新人ID' } }, { tableName: 'bank_employees', timestamps: true, + createdAt: 'created_at', + updatedAt: 'updated_at', paranoid: true, + deletedAt: 'deleted_at', comment: '银行员工表', hooks: { beforeSave: async (employee) => { diff --git a/bank-backend/models/Role.js b/bank-backend/models/Role.js index 86cb213..cc0fbf3 100644 --- a/bank-backend/models/Role.js +++ b/bank-backend/models/Role.js @@ -107,7 +107,11 @@ Role.init({ }, { sequelize, tableName: 'bank_roles', - modelName: 'Role' + modelName: 'Role', + timestamps: true, + underscored: true, + createdAt: 'created_at', + updatedAt: 'updated_at' }); module.exports = Role; \ No newline at end of file diff --git a/bank-backend/test-create-loan-product.js b/bank-backend/test-create-loan-product.js new file mode 100644 index 0000000..3e69eb0 --- /dev/null +++ b/bank-backend/test-create-loan-product.js @@ -0,0 +1,42 @@ +/** + * 测试创建贷款商品 + */ +const { LoanProduct } = require('./models'); + +async function testCreateLoanProduct() { + try { + console.log('🧪 测试创建贷款商品...'); + + const productData = { + productName: '测试贷款产品', + loanAmount: '50000~5000000', + loanTerm: 12, + interestRate: 5.5, + serviceArea: '北京市', + servicePhone: '13800138000', + productDescription: '这是一个测试贷款产品', + applicationRequirements: '需要提供身份证和收入证明', + requiredDocuments: '身份证、收入证明、银行流水', + approvalProcess: '提交申请->审核->放款', + riskLevel: 'LOW', + minLoanAmount: 50000, + maxLoanAmount: 5000000, + createdBy: 2, + updatedBy: 2 + }; + + console.log('创建数据:', productData); + + const product = await LoanProduct.create(productData); + + console.log('✅ 创建成功:', product.toJSON()); + + } catch (error) { + console.error('❌ 创建失败:', error.message); + console.error('详细错误:', error); + } + + process.exit(0); +} + +testCreateLoanProduct(); diff --git a/bank-backend/test-login.js b/bank-backend/test-login.js deleted file mode 100644 index bc7d2cf..0000000 --- a/bank-backend/test-login.js +++ /dev/null @@ -1,16 +0,0 @@ -const axios = require('axios'); - -async function testLogin() { - try { - console.log('测试登录API...'); - const response = await axios.post('http://localhost:3001/api/auth/login', { - username: 'admin', - password: 'Admin123456' - }); - console.log('登录成功:', response.data); - } catch (error) { - console.log('登录失败:', error.response ? error.response.data : error.message); - } -} - -testLogin(); diff --git a/bank-frontend/src/views/loan/LoanProducts.vue b/bank-frontend/src/views/loan/LoanProducts.vue index 332d8dd..14dd81a 100644 --- a/bank-frontend/src/views/loan/LoanProducts.vue +++ b/bank-frontend/src/views/loan/LoanProducts.vue @@ -79,6 +79,154 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + 低风险 + 中风险 + 高风险 + + + + + + + {{ addForm.onSaleStatus ? '在售' : '停售' }} + + + + + + + + + + + + + + + + + + + + + + { + if (!value) return Promise.reject('请输入贷款额度') + // 支持数字或范围字符串(如:50000~5000000) + if (typeof value === 'number') { + if (value <= 0) return Promise.reject('贷款额度必须大于0') + } else if (typeof value === 'string') { + // 处理范围字符串 + if (value.includes('~')) { + const [min, max] = value.split('~').map(v => parseFloat(v.trim())) + if (isNaN(min) || isNaN(max) || min <= 0 || max <= 0) { + return Promise.reject('贷款额度范围格式不正确') + } + } else { + const numValue = parseFloat(value) + if (isNaN(numValue) || numValue <= 0) { + return Promise.reject('贷款额度必须大于0') + } + } + } + return Promise.resolve() + }, + trigger: 'blur' + } + ], + loanTerm: [ + { required: true, message: '请输入贷款周期', trigger: 'blur' }, + { type: 'number', min: 1, message: '贷款周期必须大于0', trigger: 'blur' } + ], + interestRate: [ + { required: true, message: '请输入贷款利率', trigger: 'blur' }, + { + validator: (rule, value) => { + if (!value) return Promise.reject('请输入贷款利率') + const numValue = parseFloat(value) + if (isNaN(numValue)) return Promise.reject('请输入有效的数字') + if (numValue < 0 || numValue > 100) { + return Promise.reject('贷款利率必须在0-100之间') + } + return Promise.resolve() + }, + trigger: 'blur' + } + ], + serviceArea: [ + { required: true, message: '请输入服务区域', trigger: 'blur' } + ], + servicePhone: [ + { required: true, message: '请输入服务电话', trigger: 'blur' }, + { pattern: /^1[3-9]\d{9}$/, message: '请输入正确的手机号码', trigger: 'blur' } + ], + minLoanAmount: [ + { required: true, message: '请输入最小贷款金额', trigger: 'blur' }, + { type: 'number', min: 0, message: '最小贷款金额不能小于0', trigger: 'blur' } + ], + maxLoanAmount: [ + { required: true, message: '请输入最大贷款金额', trigger: 'blur' }, + { type: 'number', min: 0, message: '最大贷款金额不能小于0', trigger: 'blur' } + ], + riskLevel: [ + { required: true, message: '请选择风险等级', trigger: 'change' } + ] +} + // 行选择配置 const rowSelection = { selectedRowKeys: selectedRowKeys, @@ -472,7 +713,24 @@ const handleReset = () => { } const handleAddProduct = () => { - message.info('新增贷款功能开发中...') + // 重置表单 + Object.assign(addForm, { + productName: '', + loanAmount: '', + loanTerm: null, + interestRate: '', + serviceArea: '', + servicePhone: '', + minLoanAmount: null, + maxLoanAmount: null, + riskLevel: 'LOW', + onSaleStatus: true, + productDescription: '', + applicationRequirements: '', + requiredDocuments: '', + approvalProcess: '' + }) + addModalVisible.value = true } const handleEdit = async (record) => { @@ -554,6 +812,36 @@ const handleEditCancel = () => { editFormRef.value?.resetFields() } +// 新增提交 +const handleAddSubmit = async () => { + try { + await addFormRef.value.validate() + addLoading.value = true + + const response = await api.loanProducts.create(addForm) + + if (response.success) { + message.success('新增贷款商品成功') + addModalVisible.value = false + addFormRef.value?.resetFields() + fetchProducts() // 刷新列表 + } else { + message.error(response.message || '新增失败') + } + } catch (error) { + console.error('新增失败:', error) + message.error('新增失败') + } finally { + addLoading.value = false + } +} + +// 新增取消 +const handleAddCancel = () => { + addModalVisible.value = false + addFormRef.value?.resetFields() +} + // 删除产品 const handleDelete = async (record) => { try { diff --git a/government-admin/package-lock.json b/government-admin/package-lock.json index b892091..452a9fc 100644 --- a/government-admin/package-lock.json +++ b/government-admin/package-lock.json @@ -10,7 +10,6 @@ "dependencies": { "@ant-design/icons-vue": "^6.1.0", "ant-design-vue": "^4.0.0", - "axios": "^1.4.0", "dayjs": "^1.11.18", "echarts": "^5.4.2", "pinia": "^2.1.6", @@ -20,6 +19,7 @@ }, "devDependencies": { "@vitejs/plugin-vue": "^4.2.3", + "axios": "^1.12.2", "eslint": "^8.45.0", "eslint-plugin-vue": "^9.15.1", "sass": "^1.93.0", @@ -1238,12 +1238,14 @@ "version": "0.4.0", "resolved": "https://registry.npmmirror.com/asynckit/-/asynckit-0.4.0.tgz", "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==", + "dev": true, "license": "MIT" }, "node_modules/axios": { "version": "1.12.2", "resolved": "https://registry.npmmirror.com/axios/-/axios-1.12.2.tgz", "integrity": "sha512-vMJzPewAlRyOgxV2dU0Cuz2O8zzzx9VYtbJOaBgXFeLc4IV/Eg50n4LowmehOOR61S8ZMpc2K5Sa7g6A4jfkUw==", + "dev": true, "license": "MIT", "dependencies": { "follow-redirects": "^1.15.6", @@ -1294,6 +1296,7 @@ "version": "1.0.2", "resolved": "https://registry.npmmirror.com/call-bind-apply-helpers/-/call-bind-apply-helpers-1.0.2.tgz", "integrity": "sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==", + "dev": true, "license": "MIT", "dependencies": { "es-errors": "^1.3.0", @@ -1370,6 +1373,7 @@ "version": "1.0.8", "resolved": "https://registry.npmmirror.com/combined-stream/-/combined-stream-1.0.8.tgz", "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "dev": true, "license": "MIT", "dependencies": { "delayed-stream": "~1.0.0" @@ -1471,6 +1475,7 @@ "version": "1.0.0", "resolved": "https://registry.npmmirror.com/delayed-stream/-/delayed-stream-1.0.0.tgz", "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", + "dev": true, "license": "MIT", "engines": { "node": ">=0.4.0" @@ -1519,6 +1524,7 @@ "version": "1.0.1", "resolved": "https://registry.npmmirror.com/dunder-proto/-/dunder-proto-1.0.1.tgz", "integrity": "sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==", + "dev": true, "license": "MIT", "dependencies": { "call-bind-apply-helpers": "^1.0.1", @@ -1555,6 +1561,7 @@ "version": "1.0.1", "resolved": "https://registry.npmmirror.com/es-define-property/-/es-define-property-1.0.1.tgz", "integrity": "sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==", + "dev": true, "license": "MIT", "engines": { "node": ">= 0.4" @@ -1564,6 +1571,7 @@ "version": "1.3.0", "resolved": "https://registry.npmmirror.com/es-errors/-/es-errors-1.3.0.tgz", "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==", + "dev": true, "license": "MIT", "engines": { "node": ">= 0.4" @@ -1573,6 +1581,7 @@ "version": "1.1.1", "resolved": "https://registry.npmmirror.com/es-object-atoms/-/es-object-atoms-1.1.1.tgz", "integrity": "sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==", + "dev": true, "license": "MIT", "dependencies": { "es-errors": "^1.3.0" @@ -1585,6 +1594,7 @@ "version": "2.1.0", "resolved": "https://registry.npmmirror.com/es-set-tostringtag/-/es-set-tostringtag-2.1.0.tgz", "integrity": "sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==", + "dev": true, "license": "MIT", "dependencies": { "es-errors": "^1.3.0", @@ -1928,6 +1938,7 @@ "version": "1.15.11", "resolved": "https://registry.npmmirror.com/follow-redirects/-/follow-redirects-1.15.11.tgz", "integrity": "sha512-deG2P0JfjrTxl50XGCDyfI97ZGVCxIpfKYmfyrQ54n5FO/0gfIES8C/Psl6kWVDolizcaaxZJnTS0QSMxvnsBQ==", + "dev": true, "funding": [ { "type": "individual", @@ -1948,6 +1959,7 @@ "version": "4.0.4", "resolved": "https://registry.npmmirror.com/form-data/-/form-data-4.0.4.tgz", "integrity": "sha512-KrGhL9Q4zjj0kiUt5OO4Mr/A/jlI2jDYs5eHBpYHPcBEVSiipAvn2Ko2HnPe20rmcuuvMHNdZFp+4IlGTMF0Ow==", + "dev": true, "license": "MIT", "dependencies": { "asynckit": "^0.4.0", @@ -1986,6 +1998,7 @@ "version": "1.1.2", "resolved": "https://registry.npmmirror.com/function-bind/-/function-bind-1.1.2.tgz", "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==", + "dev": true, "license": "MIT", "funding": { "url": "https://github.com/sponsors/ljharb" @@ -1995,6 +2008,7 @@ "version": "1.3.0", "resolved": "https://registry.npmmirror.com/get-intrinsic/-/get-intrinsic-1.3.0.tgz", "integrity": "sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==", + "dev": true, "license": "MIT", "dependencies": { "call-bind-apply-helpers": "^1.0.2", @@ -2019,6 +2033,7 @@ "version": "1.0.1", "resolved": "https://registry.npmmirror.com/get-proto/-/get-proto-1.0.1.tgz", "integrity": "sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==", + "dev": true, "license": "MIT", "dependencies": { "dunder-proto": "^1.0.1", @@ -2083,6 +2098,7 @@ "version": "1.2.0", "resolved": "https://registry.npmmirror.com/gopd/-/gopd-1.2.0.tgz", "integrity": "sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==", + "dev": true, "license": "MIT", "engines": { "node": ">= 0.4" @@ -2112,6 +2128,7 @@ "version": "1.1.0", "resolved": "https://registry.npmmirror.com/has-symbols/-/has-symbols-1.1.0.tgz", "integrity": "sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==", + "dev": true, "license": "MIT", "engines": { "node": ">= 0.4" @@ -2124,6 +2141,7 @@ "version": "1.0.2", "resolved": "https://registry.npmmirror.com/has-tostringtag/-/has-tostringtag-1.0.2.tgz", "integrity": "sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==", + "dev": true, "license": "MIT", "dependencies": { "has-symbols": "^1.0.3" @@ -2139,6 +2157,7 @@ "version": "2.0.2", "resolved": "https://registry.npmmirror.com/hasown/-/hasown-2.0.2.tgz", "integrity": "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==", + "dev": true, "license": "MIT", "dependencies": { "function-bind": "^1.1.2" @@ -2394,6 +2413,7 @@ "version": "1.1.0", "resolved": "https://registry.npmmirror.com/math-intrinsics/-/math-intrinsics-1.1.0.tgz", "integrity": "sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==", + "dev": true, "license": "MIT", "engines": { "node": ">= 0.4" @@ -2418,6 +2438,7 @@ "version": "1.52.0", "resolved": "https://registry.npmmirror.com/mime-db/-/mime-db-1.52.0.tgz", "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "dev": true, "license": "MIT", "engines": { "node": ">= 0.6" @@ -2427,6 +2448,7 @@ "version": "2.1.35", "resolved": "https://registry.npmmirror.com/mime-types/-/mime-types-2.1.35.tgz", "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "dev": true, "license": "MIT", "dependencies": { "mime-db": "1.52.0" @@ -2708,6 +2730,7 @@ "version": "1.1.0", "resolved": "https://registry.npmmirror.com/proxy-from-env/-/proxy-from-env-1.1.0.tgz", "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==", + "dev": true, "license": "MIT" }, "node_modules/punycode": { diff --git a/government-admin/package.json b/government-admin/package.json index d465368..42dcb35 100644 --- a/government-admin/package.json +++ b/government-admin/package.json @@ -12,7 +12,6 @@ "dependencies": { "@ant-design/icons-vue": "^6.1.0", "ant-design-vue": "^4.0.0", - "axios": "^1.4.0", "dayjs": "^1.11.18", "echarts": "^5.4.2", "pinia": "^2.1.6", @@ -22,6 +21,7 @@ }, "devDependencies": { "@vitejs/plugin-vue": "^4.2.3", + "axios": "^1.12.2", "eslint": "^8.45.0", "eslint-plugin-vue": "^9.15.1", "sass": "^1.93.0", diff --git a/government-admin/src/utils/api.js b/government-admin/src/utils/api.js index ae3909b..283e6a3 100644 --- a/government-admin/src/utils/api.js +++ b/government-admin/src/utils/api.js @@ -1,6 +1,5 @@ -import { message } from 'antd' -import { useUserStore } from '@/stores/user' import axios from 'axios' +import { message } from 'ant-design-vue' // 创建axios实例 const instance = axios.create({ @@ -11,14 +10,14 @@ const instance = axios.create({ } }) -// 请求拦截器 +// 请求拦截器 - 从localStorage中获取token instance.interceptors.request.use( config => { - // 获取用户store - const userStore = useUserStore() + // 从localStorage中获取token + const token = localStorage.getItem('token') // 如果有token,添加到请求头 - if (userStore.token) { - config.headers['Authorization'] = `Bearer ${userStore.token}` + if (token) { + config.headers['Authorization'] = `Bearer ${token}` } return config }, @@ -40,227 +39,257 @@ instance.interceptors.response.use( switch (error.response.status) { case 401: // 未授权,跳转到登录页面 - const userStore = useUserStore() - userStore.logout() + localStorage.removeItem('token') window.location.href = '/login' - import('ant-design-vue').then(({ message }) => { - message.error('登录已过期,请重新登录') - }) + message.error('登录已过期,请重新登录') break case 403: - import('ant-design-vue').then(({ message }) => { - message.error('没有权限执行此操作') - }) + message.error('没有权限执行此操作') break case 404: - import('ant-design-vue').then(({ message }) => { - message.error('请求的资源不存在') - }) + message.error('请求的资源不存在') break case 500: - import('ant-design-vue').then(({ message }) => { - message.error('服务器内部错误') - }) + message.error('服务器内部错误') break default: - import('ant-design-vue').then(({ message }) => { - message.error(error.response.data.message || '请求失败') - }) + message.error('请求失败') } } else if (error.request) { // 请求发出但没有收到响应 - import('ant-design-vue').then(({ message }) => { - message.error('网络错误,请检查网络连接') - }) + message.error('网络连接失败') } else { // 请求配置出错 - import('ant-design-vue').then(({ message }) => { - message.error('请求配置错误') - }) + message.error('请求配置出错') } return Promise.reject(error) } ) -// API接口定义 -const api = { - // 认证相关API - auth: { - // 登录 - login: (data) => instance.post('/auth/login', data), - // 获取用户信息 - getUserInfo: () => instance.get('/auth/userinfo'), - // 退出登录 - logout: () => instance.post('/auth/logout'), +// 认证相关的API +const auth = { + // 登录 + login: data => instance.post('/auth/login', data), + // 获取用户信息 + getUserInfo: () => instance.get('/auth/userInfo'), + // 退出登录 + logout: () => instance.post('/auth/logout'), + // 重置密码 + resetPassword: data => instance.post('/auth/resetPassword', data) +} + +// 用户管理相关的API +const user = { + // 获取用户列表 + getList: params => instance.get('/user/list', { params }), + // 新增用户 + create: data => instance.post('/user/create', data), + // 编辑用户 + update: data => instance.post('/user/update', data), + // 删除用户 + delete: id => instance.post(`/user/delete/${id}`), + // 禁用/启用用户 + toggleStatus: data => instance.post('/user/toggleStatus', data), + // 重置密码 + resetPassword: id => instance.post(`/user/resetPassword/${id}`) +} + +// 监管相关的API +const supervision = { + // 获取监管列表 + getList: params => instance.get('/supervision/list', { params }), + // 获取监管详情 + getDetail: id => instance.get(`/supervision/detail/${id}`), + // 新增监管 + create: data => instance.post('/supervision/create', data), + // 更新监管 + update: data => instance.post('/supervision/update', data), + // 删除监管 + delete: id => instance.post(`/supervision/delete/${id}`) +} + +// 审批相关的API +const approval = { + // 获取审批列表 + getList: params => instance.get('/approval/list', { params }), + // 获取审批详情 + getDetail: id => instance.get(`/approval/detail/${id}`), + // 提交审批 + submit: data => instance.post('/approval/submit', data), + // 审批操作 + approve: data => instance.post('/approval/approve', data), + // 驳回操作 + reject: data => instance.post('/approval/reject', data), + // 撤回操作 + withdraw: id => instance.post(`/approval/withdraw/${id}`) +} + +// 疫情监控相关的API +const epidemic = { + // 获取疫情监控列表 + getList: params => instance.get('/epidemic/list', { params }), + // 获取疫情监控详情 + getDetail: id => instance.get(`/epidemic/detail/${id}`), + // 新增疫情监控 + create: data => instance.post('/epidemic/create', data), + // 更新疫情监控 + update: data => instance.post('/epidemic/update', data), + // 删除疫情监控 + delete: id => instance.post(`/epidemic/delete/${id}`), + // 处理疫情 + handle: data => instance.post('/epidemic/handle', data) +} + +// 数据可视化相关的API +const visualization = { + // 获取养殖情况统计 + getBreedingStats: params => instance.get('/visualization/breedingStats', { params }), + // 获取疫情趋势 + getEpidemicTrend: params => instance.get('/visualization/epidemicTrend', { params }), + // 获取监管效果 + getSupervisionEffect: params => instance.get('/visualization/supervisionEffect', { params }) +} + +// 文件管理相关的API +const file = { + // 上传文件 + upload: data => instance.post('/file/upload', data), + // 下载文件 + download: id => instance.get(`/file/download/${id}`), + // 获取文件列表 + getList: params => instance.get('/file/list', { params }), + // 删除文件 + delete: id => instance.post(`/file/delete/${id}`) +} + +// 人员管理相关的API +const staff = { + // 获取人员列表 + getList: params => instance.get('/staff/list', { params }), + // 新增人员 + create: data => instance.post('/staff/create', data), + // 更新人员 + update: data => instance.post('/staff/update', data), + // 删除人员 + delete: id => instance.post(`/staff/delete/${id}`), + // 获取人员详情 + getDetail: id => instance.get(`/staff/detail/${id}`) +} + +// 服务管理相关的API +const service = { + // 获取服务列表 + getList: params => instance.get('/service/list', { params }), + // 新增服务 + create: data => instance.post('/service/create', data), + // 更新服务 + update: data => instance.post('/service/update', data), + // 删除服务 + delete: id => instance.post(`/service/delete/${id}`), + // 获取服务详情 + getDetail: id => instance.get(`/service/detail/${id}`) +} + +// 仓库管理相关的API +const warehouse = { + // 获取仓库列表 + getList: params => instance.get('/warehouse/list', { params }), + // 新增仓库 + create: data => instance.post('/warehouse/create', data), + // 更新仓库 + update: data => instance.post('/warehouse/update', data), + // 删除仓库 + delete: id => instance.post(`/warehouse/delete/${id}`), + // 获取仓库详情 + getDetail: id => instance.get(`/warehouse/detail/${id}`) +} + +// 系统设置相关的API +const system = { + // 获取系统设置 + getSettings: () => instance.get('/system/settings'), + // 更新系统设置 + updateSettings: data => instance.post('/system/updateSettings', data), + // 获取操作日志 + getOperationLogs: params => instance.get('/system/operationLogs', { params }) +} + +// 政府管理相关的API +const government = { + // 行政人员管理 + adminStaff: { + // 获取行政人员列表 + getList: params => instance.get('/government/admin-staff/list', { params }), + // 新增行政人员 + create: data => instance.post('/government/admin-staff/create', data), + // 编辑行政人员 + update: data => instance.post('/government/admin-staff/update', data), + // 删除行政人员 + delete: id => instance.post(`/government/admin-staff/delete/${id}`), // 重置密码 - resetPassword: (data) => instance.post('/auth/reset-password', data) + resetPassword: id => instance.post(`/government/admin-staff/reset-password/${id}`) }, - - // 用户管理相关API - user: { - // 获取用户列表 - getList: (params) => instance.get('/users', { params }), - // 获取单个用户信息 - getDetail: (id) => instance.get(`/users/${id}`), - // 创建用户 - create: (data) => instance.post('/users', data), - // 更新用户 - update: (id, data) => instance.put(`/users/${id}`, data), - // 删除用户 - delete: (id) => instance.delete(`/users/${id}`), - // 批量删除用户 - batchDelete: (ids) => instance.post('/users/batch-delete', { ids }), - // 更新用户状态 - updateStatus: (id, status) => instance.put(`/users/${id}/status`, { status }) + // 部门管理 + departments: { + // 获取部门列表 + getList: () => instance.get('/government/departments/list'), + // 新增部门 + create: data => instance.post('/government/departments/create', data), + // 编辑部门 + update: data => instance.post('/government/departments/update', data), + // 删除部门 + delete: id => instance.post(`/government/departments/delete/${id}`) }, - - // 监管相关API - supervision: { - // 获取监管统计数据 - getStats: () => instance.get('/supervision/stats'), - // 获取监管任务列表 - getTasks: (params) => instance.get('/supervision/tasks', { params }), - // 获取监管任务详情 - getTaskDetail: (id) => instance.get(`/supervision/tasks/${id}`), - // 创建监管任务 - createTask: (data) => instance.post('/supervision/tasks', data), - // 更新监管任务 - updateTask: (id, data) => instance.put(`/supervision/tasks/${id}`, data), - // 删除监管任务 - deleteTask: (id) => instance.delete(`/supervision/tasks/${id}`) + // 岗位管理 + positions: { + // 获取岗位列表 + getList: () => instance.get('/government/positions/list'), + // 新增岗位 + create: data => instance.post('/government/positions/create', data), + // 编辑岗位 + update: data => instance.post('/government/positions/update', data), + // 删除岗位 + delete: id => instance.post(`/government/positions/delete/${id}`) }, - - // 审批相关API - approval: { - // 获取审批流程列表 - getList: (params) => instance.get('/approval', { params }), - // 创建审批流程 - create: (data) => instance.post('/approval', data), - // 获取审批详情 - getDetail: (id) => instance.get(`/approval/${id}`), - // 更新审批状态 - updateStatus: (id, status) => instance.put(`/approval/${id}/status`, { status }) - }, - - // 疫情监控相关API - epidemic: { - // 获取疫情统计数据 - getStats: () => instance.get('/epidemic/stats'), - // 获取疫苗接种数据 - getVaccinationData: (params) => instance.get('/epidemic/vaccination', { params }), - // 获取检测数据 - getTestData: (params) => instance.get('/epidemic/test', { params }) - }, - - // 数据可视化相关API - visualization: { - // 获取可视化数据 - getData: (params) => instance.get('/visualization/data', { params }) - }, - - // 文件管理相关API - file: { - // 获取文件列表 - getList: (params) => instance.get('/files', { params }), - // 上传文件 - upload: (file, onUploadProgress) => { - const formData = new FormData() - formData.append('file', file) - return instance.post('/files/upload', formData, { - headers: { - 'Content-Type': 'multipart/form-data' - }, - onUploadProgress - }) + // 养殖户管理 + farmers: { + // 获取养殖户列表 + getList: params => instance.get('/government/farmers', { params }), + // 新增养殖户 + create: data => instance.post('/government/farmers', data), + // 编辑养殖户 + update: (id, data) => instance.put(`/government/farmers/${id}`, data), + // 删除养殖户 + delete: id => instance.delete(`/government/farmers/${id}`), + // 重置密码 + resetPassword: id => instance.post(`/government/farmers/${id}/reset-password`) }, - // 下载文件 - download: (id) => instance.get(`/files/${id}/download`, { responseType: 'blob' }), - // 删除文件 - delete: (id) => instance.delete(`/files/${id}`) + // 养殖类型相关 + farmTypes: { + // 获取养殖类型列表 + getList: () => instance.get('/government/farm-types') }, - - // 人员管理相关API - personnel: { - // 获取人员列表 - getList: (params) => instance.get('/personnel', { params }), - // 创建人员 - create: (data) => instance.post('/personnel', data), - // 更新人员 - update: (id, data) => instance.put(`/personnel/${id}`, data), - // 删除人员 - delete: (id) => instance.delete(`/personnel/${id}`) - }, - - // 服务管理相关API - service: { - // 获取服务列表 - getList: (params) => instance.get('/service', { params }), - // 创建服务 - create: (data) => instance.post('/service', data), - // 更新服务 - update: (id, data) => instance.put(`/service/${id}`, data), - // 删除服务 - delete: (id) => instance.delete(`/service/${id}`) - }, - - // 仓库管理相关API - warehouse: { - // 获取物资列表 - getList: (params) => instance.get('/warehouse', { params }), - // 获取单个物资详情 - getDetail: (id) => instance.get(`/warehouse/${id}`), - // 创建物资 - create: (data) => instance.post('/warehouse', data), - // 更新物资 - update: (id, data) => instance.put(`/warehouse/${id}`, data), - // 删除物资 - delete: (id) => instance.delete(`/warehouse/${id}`), - // 物资入库 - stockIn: (data) => instance.post('/warehouse/in', data), - // 物资出库 - stockOut: (data) => instance.post('/warehouse/out', data), - // 获取库存统计信息 - getStats: () => instance.get('/warehouse/stats') - }, - - // 系统设置相关API - system: { - // 获取系统设置 - getSettings: () => instance.get('/system/settings'), - // 更新系统设置 - updateSettings: (data) => instance.put('/system/settings', data), - // 获取日志列表 - getLogs: (params) => instance.get('/system/logs', { params }) - }, - - // 政府管理相关API - government: { - // 行政人员管理 - adminStaff: { - // 获取行政人员列表 - getList: (params) => instance.get('/government/admin-staff', { params }), - // 创建行政人员 - create: (data) => instance.post('/government/admin-staff', data), - // 更新行政人员 - update: (id, data) => instance.put(`/government/admin-staff/${id}`, data), - // 删除行政人员 - delete: (id) => instance.delete(`/government/admin-staff/${id}`), - // 重置行政人员密码 - resetPassword: (id) => instance.post(`/government/admin-staff/${id}/reset-password`) - }, - - // 部门管理 - departments: { - // 获取部门列表 - getList: (params) => instance.get('/government/departments', { params }) - }, - - // 岗位管理 - positions: { - // 获取岗位列表 - getList: (params) => instance.get('/government/positions', { params }) - } + // 养殖种类相关 + animalTypes: { + // 获取养殖种类列表 + getList: () => instance.get('/government/animal-types') } } +// 导出所有API +const api = { + auth, + user, + supervision, + approval, + epidemic, + visualization, + file, + staff, + service, + warehouse, + system, + government +} + export default api \ No newline at end of file diff --git a/government-admin/src/views/AdminStaff.vue b/government-admin/src/views/AdminStaff.vue index 713ae53..35479a7 100644 --- a/government-admin/src/views/AdminStaff.vue +++ b/government-admin/src/views/AdminStaff.vue @@ -166,16 +166,32 @@ const fetchAdminStaffList = async () => { search: searchValue.value } const response = await api.government.adminStaff.getList(params) - staffData.value = response.data.map(item => ({ - ...item, - department: departments.value.find(dept => dept.id === item.department_id)?.name || '', - position: positions.value.find(pos => pos.id === item.position_id)?.name || '', - key: item.id - })) - pagination.total = response.total + + // 确保response.data是一个数组 + if (response && Array.isArray(response.data)) { + staffData.value = response.data.map(item => ({ + ...item, + department: departments.value.find(dept => dept.id === item.department_id)?.name || '', + position: positions.value.find(pos => pos.id === item.position_id)?.name || '', + key: item.id + })) + pagination.total = response.total || response.data.length + } else { + // 处理异常情况 + staffData.value = [] + pagination.total = 0 + console.error('行政人员列表数据格式错误:', response) + } + + console.log('行政人员列表数据:', staffData.value) } catch (error) { message.error('获取行政人员列表失败') console.error('获取行政人员列表失败:', error) + // 添加错误详细信息展示 + if (error.response) { + console.error('错误状态码:', error.response.status) + console.error('错误数据:', error.response.data) + } } } @@ -183,7 +199,16 @@ const fetchAdminStaffList = async () => { const fetchDepartments = async () => { try { const response = await api.government.departments.getList() - departments.value = response.data + // 处理数据格式 - 确保departments是一个数组 + if (response && response.data && Array.isArray(response.data)) { + departments.value = response.data + } else if (response) { + // 处理API返回的非标准格式数据 + departments.value = Object.values(response).map(item => + typeof item === 'object' ? item : { id: item, name: item } + ) + } + console.log('部门列表数据:', departments.value) } catch (error) { message.error('获取部门列表失败') console.error('获取部门列表失败:', error) @@ -194,7 +219,16 @@ const fetchDepartments = async () => { const fetchPositions = async () => { try { const response = await api.government.positions.getList() - positions.value = response.data + // 处理数据格式 - 确保positions是一个数组 + if (response && response.data && Array.isArray(response.data)) { + positions.value = response.data + } else if (response) { + // 处理API返回的非标准格式数据 + positions.value = Object.values(response).map(item => + typeof item === 'object' ? item : { id: item, name: item } + ) + } + console.log('岗位列表数据:', positions.value) } catch (error) { message.error('获取岗位列表失败') console.error('获取岗位列表失败:', error) diff --git a/government-admin/src/views/FarmerManagement.vue b/government-admin/src/views/FarmerManagement.vue index 38e7832..68d7b1b 100644 --- a/government-admin/src/views/FarmerManagement.vue +++ b/government-admin/src/views/FarmerManagement.vue @@ -7,20 +7,28 @@
全部 - 账号筛选1 - 账号筛选2 + {{ type.label }} + + + 全部 + {{ type.label }}
@@ -32,11 +40,13 @@ :pagination="pagination" row-key="id" :scroll="{ x: 'max-content' }" + @change="handleTableChange" + :loading="loading" >