xiangqinxiaochengxu/miniprogram/utils/request.js
2026-04-17 10:49:14 +08:00

129 lines
3.9 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

const { getApiBaseUrl } = require('./constants')
function isPublicRequest(url) {
return url === '/auth/wx-login' || url === '/auth/public-config'
}
function normalizeError(message, detail) {
const error = new Error(message)
error.detail = detail
return error
}
function getFieldLabel(field) {
const labels = {
nickname: '昵称',
real_name: '真实姓名',
gender: '性别',
birth_year: '出生年份',
city: '所在城市',
height: '身高',
education: '学历',
job_industry: '行业',
job_company: '公司',
income_range: '收入范围',
personality_tags: '性格标签',
hobbies: '兴趣爱好',
wechat_id: '微信号',
phone: '手机号',
prefer_city: '期望城市',
self_intro: '个人介绍',
}
return labels[field] || field
}
function normalizeFieldErrorMessage(item) {
const fieldLabel = getFieldLabel(item.field)
const message = item.message || '参数不合法'
if (message.includes('at most') && message.includes('characters')) {
const matched = message.match(/at most\s+(\d+)\s+characters/i)
if (matched) {
return `${fieldLabel}不能超过${matched[1]}个字符`
}
}
if (message.includes('must be') && message.includes('list')) {
return `${fieldLabel}必须是数组`
}
if (message.includes('array') || message.includes('list')) {
return `${fieldLabel}必须是数组`
}
if (message.includes('string')) {
return `${fieldLabel}格式不正确`
}
return `${fieldLabel}${message}`
}
function executeRequest(options, resolve, reject) {
const app = getApp()
const token = wx.getStorageSync('token')
wx.request({
url: `${getApiBaseUrl()}${options.url}`,
method: options.method || 'GET',
data: options.data || {},
timeout: options.timeout || 10000,
header: {
'Content-Type': 'application/json',
Authorization: token ? `Bearer ${token}` : ''
},
success(res) {
if (res.statusCode === 401) {
wx.removeStorageSync('token')
wx.removeStorageSync('refresh_token')
if (app && typeof app.ensureLogin === 'function' && !options._retry && !isPublicRequest(options.url)) {
app.ensureLogin()
.then(() => request({ ...options, _retry: true }).then(resolve).catch(reject))
.catch((err) => {
wx.showToast({ title: '登录已过期', icon: 'none' })
reject(err || normalizeError('登录已过期'))
})
return
}
wx.showToast({ title: '登录已过期', icon: 'none' })
reject(normalizeError('登录已过期'))
return
}
if (!res.data || res.data.code !== 0) {
const detail = res.data || {}
const fieldErrors = detail?.data?.field_errors || []
const fieldErrorMessage = fieldErrors.length > 0
? fieldErrors.map((item) => normalizeFieldErrorMessage(item)).join('')
: ''
const message = fieldErrorMessage || detail.message || detail.detail || '请求失败'
wx.showToast({ title: message.slice(0, 60), icon: 'none' })
reject(normalizeError(message, detail))
return
}
resolve(res.data.data)
},
fail(err) {
const message = err && err.errMsg && err.errMsg.includes('url not in domain list')
? '域名未配置,请到后台系统设置修改'
: '网络异常,请重试'
wx.showToast({ title: message, icon: 'none' })
reject(normalizeError(message, err))
}
})
}
function request(options) {
return new Promise((resolve, reject) => {
const app = getApp()
if (!isPublicRequest(options.url) && app && typeof app.ensureLogin === 'function' && !wx.getStorageSync('token')) {
app.ensureLogin()
.then(() => executeRequest(options, resolve, reject))
.catch((err) => reject(err))
return
}
executeRequest(options, resolve, reject)
})
}
module.exports = request