diff --git a/env/.env b/env/.env index d61e466..f1a5320 100644 --- a/env/.env +++ b/env/.env @@ -10,13 +10,22 @@ VITE_APP_PUBLIC_BASE=/ # 登录页面 VITE_LOGIN_URL = '/pages/login/login' # 第一个请求地址 -VITE_SERVER_BASEURL = 'https://mnp.zhuzhuda.cn' +VITE_SERVER_BASEURL = 'https://cz.stnav.com' -VITE_UPLOAD_BASEURL = 'https://mnp.zhuzhuda.cn/upload' +VITE_UPLOAD_BASEURL = 'https://cz.stnav.com/upload' # h5是否需要配置代理 VITE_APP_PROXY=false VITE_APP_PROXY_PREFIX = '/api' # 第二个请求地址 (目前alova中可以使用) -VITE_API_SECONDARY_URL = 'https://mnp.zhuzhuda.cn' \ No newline at end of file +VITE_SERVER_BASEURL = 'https://cz.stnav.com' + +# 默认地址 +VITE_DEFAULT_LONGITUDE = 113.665412 +VITE_DEFAULT_LATITUDE = 34.757975 +VITE_DEFAULT_ADDRESS = '上海市' +VITE_DEFAULT_LOCATION_EXPIRE_MS = 30 * 24 * 60 * 60 * 1000 # 30天 +VITE_DEFAULT_LOCATION_EXPIRE_KEY = 'location_expire_time' +VITE_DEFAULT_LOCATION_DENY_TIME_KEY = 'location_deny_time' +VITE_DEFAULT_LOCATION_DENY_INTERVAL = 60 * 60 * 1000 # 1小时 \ No newline at end of file diff --git a/manifest.config.ts b/manifest.config.ts index edf4b5c..a04cef1 100644 --- a/manifest.config.ts +++ b/manifest.config.ts @@ -124,12 +124,18 @@ export default defineManifestConfig({ es6: true, minified: true, }, + requiredPrivateInfos: ["getLocation" ], optimization: { subPackages: true, }, // styleIsolation: 'shared', usingComponents: true, // __usePrivacyCheck__: true, + permission: { + 'scope.userLocation' : { + desc : "我们需要获取您的位置,以方便推荐附近茶室给您" + } + }, }, 'mp-alipay': { usingComponents: true, diff --git a/src/api/foo-alova.ts b/src/api/foo-alova.ts index de35095..19a12cb 100644 --- a/src/api/foo-alova.ts +++ b/src/api/foo-alova.ts @@ -1,17 +1,17 @@ import { API_DOMAINS, http } from '@/http/alova' export interface IFoo { - id: number - name: string + id: number + name: string } export function foo() { - return http.Get('/foo', { - params: { - name: '菲鸽', - page: 1, - pageSize: 10, - }, - meta: { domain: API_DOMAINS.SECONDARY }, // 用于切换请求地址 - }) + return http.Get('/foo', { + params: { + name: '菲鸽', + page: 1, + pageSize: 10, + }, + meta: { domain: API_DOMAINS.SECONDARY }, // 用于切换请求地址 + }) } diff --git a/src/api/login.ts b/src/api/login.ts index de4266d..670e5f3 100644 --- a/src/api/login.ts +++ b/src/api/login.ts @@ -5,10 +5,10 @@ import { http } from '@/http/http' * 登录表单 */ export interface ILoginForm { - username: string - password: string - code: string - uuid: string + username: string + password: string + code: string + uuid: string } /** @@ -16,7 +16,7 @@ export interface ILoginForm { * @returns ICaptcha 验证码 */ export function getCode() { - return http.get('/user/getCode') + return http.get('/user/getCode') } /** @@ -24,35 +24,35 @@ export function getCode() { * @param loginForm 登录表单 */ export function login(loginForm: ILoginForm) { - return http.post('/user/login', loginForm) + return http.post('/user/login', loginForm) } /** * 获取用户信息 */ export function getUserInfo() { - return http.get('/user/info') + return http.get('/user/info') } /** * 退出登录 */ export function logout() { - return http.get('/user/logout') + return http.get('/user/logout') } /** * 修改用户信息 */ export function updateInfo(data: IUpdateInfo) { - return http.post('/user/updateInfo', data) + return http.post('/user/updateInfo', data) } /** * 修改用户密码 */ export function updateUserPassword(data: IUpdatePassword) { - return http.post('/user/updatePassword', data) + return http.post('/user/updatePassword', data) } /** @@ -60,13 +60,13 @@ export function updateUserPassword(data: IUpdatePassword) { * @returns Promise 包含微信登录凭证(code) */ export function getWxCode() { - return new Promise((resolve, reject) => { - uni.login({ - provider: 'weixin', - success: res => resolve(res), - fail: err => reject(new Error(err)), - }) - }) + return new Promise((resolve, reject) => { + uni.login({ + provider: 'weixin', + success: res => resolve(res), + fail: err => reject(new Error(err)), + }) + }) } /** @@ -79,5 +79,5 @@ export function getWxCode() { * @returns Promise 包含登录结果 */ export function wxLogin(data: { code: string }) { - return http.post('/user/wxLogin', data) + return http.post('/user/wxLogin', data) } diff --git a/src/api/types/login.ts b/src/api/types/login.ts index 560018f..fb911a9 100644 --- a/src/api/types/login.ts +++ b/src/api/types/login.ts @@ -3,9 +3,14 @@ */ export interface IUserInfoVo { id: number - username: string + nickname: string avatar: string token: string + sn: string + account: string + channel: number + is_new_user: number + mobile: string } /** diff --git a/src/components/Pay.vue b/src/components/Pay.vue new file mode 100644 index 0000000..6415727 --- /dev/null +++ b/src/components/Pay.vue @@ -0,0 +1,125 @@ + + + + + + + \ No newline at end of file diff --git a/src/components/TeaSpecialistLevel.vue b/src/components/TeaSpecialistLevel.vue new file mode 100644 index 0000000..9c2d2a6 --- /dev/null +++ b/src/components/TeaSpecialistLevel.vue @@ -0,0 +1,54 @@ + + + + + \ No newline at end of file diff --git a/src/hooks/useLocation.ts b/src/hooks/useLocation.ts new file mode 100644 index 0000000..7912cb2 --- /dev/null +++ b/src/hooks/useLocation.ts @@ -0,0 +1,82 @@ +import { router } from '@/utils/tools' + + +const LOCATION_EXPIRE_KEY = import.meta.env.VITE_DEFAULT_LOCATION_EXPIRE_KEY // 定位缓存KEY +const LOCATION_EXPIRE_MS = import.meta.env.VITE_DEFAULT_LOCATION_EXPIRE_MS // 30天 +const LOCATION_DEFAULT_CITY = import.meta.env.VITE_DEFAULT_ADDRESS // 默认城市 +const LOCATION_DEFAULT_LAT = import.meta.env.VITE_DEFAULT_LATITUDE // 上海经度 +const LOCATION_DEFAULT_LNG = import.meta.env.VITE_DEFAULT_LONGITUDE // 上海纬度 +const LOCATION_DENY_TIME_KEY = import.meta.env.VITE_DEFAULT_LOCATION_DENY_TIME_KEY +const LOCATION_DENY_INTERVAL = import.meta.env.VITE_DEFAULT_LOCATION_DENY_INTERVAL + +// 检查过期时间 +export function handleCheckLocationCacheHooks() { + const expire = uni.getStorageSync(LOCATION_EXPIRE_KEY) + if (expire && Date.now() > expire) { + uni.removeStorageSync('latitude') + uni.removeStorageSync('longitude') + uni.removeStorageSync(LOCATION_EXPIRE_KEY) + return false + } + return true +} + +// 设置经纬度缓存 +export function handleSetLocationCacheHooks(lat: number, lng: number) { + uni.setStorageSync('latitude', lat) + uni.setStorageSync('longitude', lng) + uni.setStorageSync(LOCATION_EXPIRE_KEY, Date.now() + LOCATION_EXPIRE_MS) +} + +// 初始化经纬度 +export async function handleEnsureLocationAuthHooks() { + // 1. 检查缓存 + if (handleCheckLocationCacheHooks()) { + const lat = uni.getStorageSync('latitude') + const lng = uni.getStorageSync('longitude') + if (lat && lng) return { lat, lng } + } + + // 2. 获取定位 + return new Promise<{ lat: number, lng: number }>((resolve) => { + uni.authorize({ + scope: 'scope.userLocation', + success() { + uni.getLocation({ + type: 'gcj02', + success(res) { + handleSetLocationCacheHooks(res.latitude, res.longitude) + resolve({ lat: res.latitude, lng: res.longitude }) + }, + fail() { + // 定位失败,返回默认上海 + resolve({ lat: LOCATION_DEFAULT_LAT, lng: LOCATION_DEFAULT_LNG }) + } + }) + }, + fail() { + // 用户拒绝授权 + if (shouldShowAuthModal()) { + uni.setStorageSync(LOCATION_DENY_TIME_KEY, Date.now()) + uni.showModal({ + title: '提示', + content: '需要获取您的地理位置,请授权定位服务', + showCancel: false, + success: () => { + // 可引导用户去设置页面 + uni.openSetting({}) + } + }) + } + // 返回默认上海 + resolve({ lat: LOCATION_DEFAULT_LAT, lng: LOCATION_DEFAULT_LNG }) + } + }) + }) +} + +// 检查是否需要弹授权框 +function shouldShowAuthModal() { + const lastDeny = uni.getStorageSync(LOCATION_DENY_TIME_KEY) + return !lastDeny || (Date.now() - lastDeny > LOCATION_DENY_INTERVAL) +} diff --git a/src/http/alova.ts b/src/http/alova.ts index d64402b..c7359d0 100644 --- a/src/http/alova.ts +++ b/src/http/alova.ts @@ -6,6 +6,8 @@ import { createServerTokenAuthentication } from 'alova/client' import VueHook from 'alova/vue' import { toast } from '@/utils/toast' import { ContentTypeEnum, ResultEnum, ShowMessage } from './tools/enum' +import { useUserStore } from '@/store' +import { router } from '@/utils/tools' // 配置动态Tag export const API_DOMAINS = { @@ -59,11 +61,22 @@ const alovaInstance = createAlova({ console.log('ignoreAuth===>', ignoreAuth) // 处理认证信息 自行处理认证问题 if (ignoreAuth) { - const token = 'getToken()' + // const token = 'getToken()' + // if (!token) { + // throw new Error('[请求错误]:未登录') + // } + // method.config.headers.token = token; + + const userStore = useUserStore() + const { token } = userStore.userInfo as unknown as IUserInfo + if (!token) { + toast.info('请先登录') + router.switchTab('/pages/my/my', 500) throw new Error('[请求错误]:未登录') } - // method.config.headers.token = token; + + method.config.headers.token = token; } // 处理动态域名 @@ -96,13 +109,29 @@ const alovaInstance = createAlova({ // } // 处理业务逻辑错误 - const { code, message, data } = rawData as IResponse - // if (code !== ResultEnum.Success) { - // if (config.meta?.toast !== false) { - // toast.warning(message) - // } - // throw new Error(`请求错误[${code}]:${message}`) - // } + const { code, msg, data } = rawData as IResponse + if (code === ResultEnum.Unauthorized) { + useUserStore().removeUserInfo() + + if (config.meta?.toast !== false) { + toast.info(msg) + router.switchTab('/pages/my/my', 1000) + } + throw new Error(`登录超时[${code}]:${msg}`) + } + + if (code === ResultEnum.Success) { + if (config.meta?.toast !== false && msg) { + if (msg !== '查询成功') toast.info(msg) + } + } + + if (code !== ResultEnum.Success) { + if (config.meta?.toast !== false) { + toast.warning(msg) + } + throw new Error(`请求错误[${code}]:${msg}`) + } // 处理成功响应,返回业务数据 return data }), diff --git a/src/http/types.ts b/src/http/types.ts index 25cf472..753f263 100644 --- a/src/http/types.ts +++ b/src/http/types.ts @@ -11,7 +11,7 @@ export type CustomRequestOptions = UniApp.RequestOptions & { export interface IResponse { code: number | string data: T - message: string + msg: string status: string | number } diff --git a/src/manifest.json b/src/manifest.json index 4741e66..ffa30e1 100644 --- a/src/manifest.json +++ b/src/manifest.json @@ -90,8 +90,16 @@ "minified": true }, "usingComponents": true, + "requiredPrivateInfos": [ + "getLocation" + ], "optimization": { "subPackages": true + }, + "permission": { + "scope.userLocation": { + "desc": "我们需要获取您的位置,以方便推荐附近工厂给您" + } } }, "mp-alipay": { diff --git a/src/pages/index/index.vue b/src/pages/index/index.vue index 2dfaaf5..5ad2964 100644 --- a/src/pages/index/index.vue +++ b/src/pages/index/index.vue @@ -13,13 +13,13 @@