资讯详情

资讯详情

Django+Vue适老化健康预警系统:旧笔记本部署实战

简介本资源是一套面向Python全栈开发者与高校计算机专业学生的适老化健康预警系统完整实现方案聚焦老年人健康实时监控与异常预警场景融合Django后端与Vue前端技术助力学习者掌握前后端分离架构在医疗健康类项目中的落地实践。压缩包共635个文件涵盖118个Vue组件文件实现响应式老年友好界面、54个Python核心逻辑文件含Django视图、模型与API接口、95张JPG/42张PNG素材图含UI图标与演示截图、159个SVG矢量图标适配大字体高对比度设计以及bat脚本含安装、运行、数据库初始化等6类自动化操作整体55.3MB结构清晰便于模块化学习。已有124人下载学习资源附带完整演示视频MP4及可直接运行的源码工程开箱即用特别提供适老化交互设计细节如简化导航、放大控件、预警弹窗逻辑与MySQL5.7数据表结构脚本是理解健康数据采集、阈值预警算法集成与跨端协同开发的优质实战案例。1. 这不是又一个“健康管理系统”Demo它真能跑在社区养老站的旧笔记本上用Django做后端兜底、Vue做前端适配把血压/心率异常自动转成语音提醒家属微信通知你见过多少个标着“健康预警”的毕业设计点开全是登录页模拟数据静态图表——连MySQL表都没建全。但这个「Django-vue适老化健康预警系统」源码包我拆开第一眼就停住了requirements.txt里明确锁死django3.2.23LTS长期支持版vue.config.js里强制target: es2015docker-compose.yml里MySQL挂载了/data/mysql卷——这不是学生交差稿是冲着真实部署去的。它解决的是三类人的真实痛点社区养老站管理员没IT背景要能一键启停、老年用户视力弱、操作慢界面必须大字高对比语音反馈、家属不装App用微信接收预警。核心逻辑很实在设备上报的收缩压160mmHg且持续3分钟触发双重动作——前端弹出红色大字告警框后端调用微信模板消息API推送到绑定手机号。整个流程不依赖任何云服务MySQL本地存档Django Celery异步发通知Vue用audio标签直接播放预录的MP3语音。如果你正卡在“怎么让老人真正用起来”而不是“怎么让答辩老师点头”这份源码值得你花40分钟跑通。2. 从零启动环境搭建、数据库初始化与Django后端服务验证2.1 环境隔离与Python依赖安装为什么必须用venv而非conda很多新手一上来就pip install django vue结果发现Vue CLI和Django开发服务器端口冲突或者numpy版本和PyMySQL打架。这个项目强制要求venv原因很实际Django 3.2.x对Python版本敏感仅支持3.6-3.9而社区养老站的旧电脑大概率装着Python 3.8.10——conda默认会升级到3.10反而破坏兼容性。正确做法是# 进入项目根目录解压后看到manage.py和package.json的那层 cd /path/to/django-vue-elderly-health # 创建独立虚拟环境显式指定Python解释器路径避免系统默认版本干扰 python3.8 -m venv venv # 激活环境Linux/macOS source venv/bin/activate # Windows用户用venv\Scripts\activate.bat # 安装Django后端依赖注意requirements.txt里已剔除前端构建工具 pip install -r requirements.txt提示requirements.txt中django3.2.23、djangorestframework3.12.4、pymysql1.0.2三者版本组合经过实测若强行升级Django到4.xdjango.contrib.auth.models.User的username字段长度限制会与本项目UserProfile模型冲突导致迁移失败。2.2 MySQL数据库初始化建库、授权、导入初始数据项目不提供SQL文件而是用Djangomigrate自动生成表结构但必须手动创建数据库并授权——这是新手最容易卡住的环节。别用phpMyAdmin点点点直接命令行执行# 登录MySQL假设root密码为123456 mysql -u root -p123456 # 创建专用数据库字符集必须为utf8mb4否则微信模板消息里的emoji会乱码 CREATE DATABASE elderly_health DEFAULT CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci; # 创建专用用户并授权禁止用root账号跑生产服务 CREATE USER elderly_applocalhost IDENTIFIED BY ElderlyPass2024!; GRANT ALL PRIVILEGES ON elderly_health.* TO elderly_applocalhost; FLUSH PRIVILEGES; EXIT;接着修改Django配置文件health_backend/settings.py中的数据库配置段DATABASES { default: { ENGINE: django.db.backends.mysql, NAME: elderly_health, # 必须与上面CREATE DATABASE名称一致 USER: elderly_app, # 必须与上面CREATE USER用户名一致 PASSWORD: ElderlyPass2024!, # 注意引号内不能有空格 HOST: 127.0.0.1, # 不要用localhostMySQL socket连接会失败 PORT: 3306, OPTIONS: { charset: utf8mb4, # 关键确保支持4字节UTF8 } } }然后执行迁移# 生成迁移文件检查是否生成0001_initial.py python manage.py makemigrations # 应用迁移此时会创建auth_user、health_record、family_member等12张表 python manage.py migrate # 创建超级管理员用于后台管理http://127.0.0.1:8000/admin/ python manage.py createsuperuser # 按提示输入用户名、邮箱、密码密码至少8位含大小写字母数字2.3 启动Django开发服务器并验证API端点别急着跑Vue先确认后端API是否真正可用。启动命令带--noreload参数避免热重载在旧笔记本上卡死# 在health_backend目录下执行注意不是项目根目录 cd health_backend python manage.py runserver 0.0.0.0:8000 --noreload打开浏览器访问http://127.0.0.1:8000/health/api/v1/status/返回应为JSON{status: ok, timestamp: 2024-06-15T14:22:33.123Z, database: connected}再测试数据上报接口用curl模拟设备发送curl -X POST http://127.0.0.1:8000/health/api/v1/record/ \ -H Content-Type: application/json \ -d { device_id: elderly_001, systolic: 168, diastolic: 92, heart_rate: 112, timestamp: 2024-06-15T14:25:00Z }成功响应应为HTTP 201并在MySQL的health_healthrecord表中看到新记录。如果返回500错误立刻看Django终端日志——90%的问题出在settings.py的DATABASES配置或MySQL用户权限。2.4 常见问题排查环境、数据库、API三类高频翻车点现象1pip install -r requirements.txt报错ModuleNotFoundError: No module named django原因虚拟环境未激活或激活后执行了deactivate命令退出。解决执行which python确认输出路径包含venv/bin/python若显示/usr/bin/python说明环境未激活重新执行source venv/bin/activate。现象2python manage.py migrate报错django.db.utils.OperationalError: (1045, Access denied for user...)原因MySQL用户密码含特殊字符如!、$未被shell正确转义或settings.py中PASSWORD字段多写了空格。解决在MySQL命令行中执行SELECT User,Host FROM mysql.user;确认用户存在用单引号包裹密码ElderlyPass2024!且引号内无空格。现象3访问/health/api/v1/status/返回{detail:Authentication credentials were not provided.}原因Django REST Framework默认启用Token认证但此接口未配置豁免。解决打开health_backend/health/urls.py找到path(status/, StatusView.as_view(), namestatus)在其上方添加装饰器from rest_framework.decorators import api_view, permission_classes from rest_framework.permissions import AllowAny from rest_framework.response import Response api_view([GET]) permission_classes([AllowAny]) def status_view(request): return Response({status: ok, ...})然后在urls.py中改为path(status/, status_view, namestatus)。现象4curl上报数据后MySQL无记录Django日志显示IntegrityError: (1048, Column device_id cannot be null)原因HealthRecord模型中device_id字段设为nullFalse但请求体JSON的device_id值为空字符串或缺失。解决检查curl命令中-d参数是否完整在health_backend/health/views.py的RecordCreateView.post()方法开头加日志logger.info(fReceived data: {request.data}) # 确认前端传参结构3. Vue前端构建与适老化交互实现大字、语音、微信通知的落地细节3.1 Vue环境配置为什么放弃Vue CLI而用Vite但本项目偏偏不用搜索热词里大量出现“vue安装及环境配置”但本项目package.json里scripts字段明确写着scripts: { dev: vue-cli-service serve, build: vue-cli-service build, lint: vue-cli-service lint }这说明它基于Vue 2.x Vue CLI 3.x非Vite。原因很务实Vite的ESM模块在IE11兼容性上仍有坑而社区养老站的旧电脑大概率还在用Edge Legacy或IE11。Vue CLI 3.x打包的UMD格式能完美降级。安装步骤必须严格# 在项目根目录有package.json的位置执行 npm install -g vue/cli3.12.1 # 锁死CLI版本避免4.x生成不兼容配置 # 安装项目依赖注意不要用npm install --legacy-peer-deps会跳过关键校验 npm install # 启动开发服务器端口8080与Django的8000分离 npm run dev注意vue.config.js中devServer.proxy配置了/api: { target: http://127.0.0.1:8000 }这意味着所有/api/**请求会代理到Django后端。务必确认Django服务已启动否则Vue页面加载时API请求会504超时。3.2 适老化UI核心改造字体、间距、色彩的硬编码参数别信“响应式设计能自动适配老人”真实场景中必须硬编码。打开src/assets/styles/elderly.css关键参数如下CSS属性原值适老化值作用font-size14px24px全局基础字号覆盖所有文本节点line-height1.52.2行高拉大防止视力模糊导致误读color正文#333#000黑色纯度提升增强与背景对比度background-color主容器#fff#f5f5f5浅灰背景减少强光反射保护老年用户眼睛border-radius4px0去掉圆角降低视觉复杂度更关键的是src/components/AlertBox.vue中的语音播报逻辑template div v-ifshowAlert classalert-box h2{{ alertTitle }}/h2 p{{ alertContent }}/p !-- 预加载MP3避免点击时卡顿 -- audio refalertAudio preloadauto source :srcgetAlertSound() typeaudio/mpeg /audio /div /template script export default { methods: { getAlertSound() { // 根据预警级别返回不同语音文件 const sounds { high: /static/sounds/blood_pressure_high.mp3, low: /static/sounds/blood_pressure_low.mp3, hr: /static/sounds/heart_rate_abnormal.mp3 } return sounds[this.level] || /static/sounds/default.mp3 }, playAlert() { // 强制重置音频避免连续触发时静音 this.$refs.alertAudio.currentTime 0 this.$refs.alertAudio.play().catch(e { console.warn(Audio play failed:, e) // 静音模式下忽略错误 }) } } } /script血泪经验MP3文件必须放在public/static/sounds/目录下非src/assets因为Webpack不会处理public目录下的静态资源确保路径绝对可靠。我曾因把MP3放错位置导致语音功能在生产环境失效——老人听不到提醒责任重大。3.3 微信模板消息推送Django后端如何安全调用微信API前端只负责展示真正的预警动作在Django后端完成。health_backend/health/tasks.py中定义了Celery异步任务from celery import shared_task import requests import json shared_task def send_wechat_alert(record_id): # 1. 查询记录详情 from .models import HealthRecord record HealthRecord.objects.get(idrecord_id) # 2. 获取绑定的家属微信open_id关联FamilyMember模型 family record.elderly_user.family_member_set.first() if not family or not family.wechat_openid: return # 3. 调用微信模板消息API需提前在公众号后台配置模板 access_token get_access_token() # 封装的token获取函数含缓存 url fhttps://api.weixin.qq.com/cgi-bin/message/template/send?access_token{access_token} payload { touser: family.wechat_openid, template_id: TEMPLATE_ID_HERE, # 替换为你的公众号模板ID data: { first: {value: 【健康预警】您的家人血压异常, color: #173177}, keyword1: {value: record.elderly_user.name, color: #173177}, keyword2: {value: f{record.systolic}/{record.diastolic} mmHg, color: #FF0000}, keyword3: {value: record.timestamp.strftime(%Y-%m-%d %H:%M), color: #173177}, remark: {value: 请立即联系老人或前往医院检查。, color: #FF0000} } } response requests.post(url, jsonpayload) if response.json().get(errcode) ! 0: logger.error(fWeChat send failed: {response.text})调用时机在health_backend/health/models.py的HealthRecord.save()方法中def save(self, *args, **kwargs): is_new self._state.adding super().save(*args, **kwargs) if is_new and self.is_abnormal(): # is_abnormal()判断收缩压160或舒张压100 send_wechat_alert.delay(self.id) # 异步触发避免阻塞HTTP响应关键参数说明TEMPLATE_ID_HERE必须在微信公众平台后台申请类型选“医疗服务-健康提醒”touser字段必须是用户关注公众号后产生的openid不能用微信号color字段控制文字颜色红色#FF0000用于异常值蓝色#173177用于常规信息——这是适老化设计的细节颜色本身即语义。3.4 常见问题排查Vue构建、语音播放、微信推送的玄学故障现象1npm run dev启动后页面空白浏览器控制台报错Uncaught SyntaxError: Unexpected token 原因Vue Router使用history模式但开发服务器未配置HTML fallback导致刷新页面时404返回index.html内容HTML文本被当JS解析。解决在vue.config.js中添加module.exports { devServer: { historyApiFallback: true // 关键让所有404请求返回index.html } }现象2点击“播放语音”按钮无反应控制台无报错原因MP3文件路径错误或浏览器策略阻止自动播放Chrome 70要求用户手势触发。解决确认MP3文件位于public/static/sounds/在playAlert()方法中添加用户手势检测playAlert() { if (document.hasFocus()) { // 确保页面获得焦点 this.$refs.alertAudio.currentTime 0 this.$refs.alertAudio.play().catch(e { // 自动播放被阻止时提示用户点击一次 alert(请先点击页面任意位置再尝试播放语音) }) } }现象3微信模板消息发送失败返回{errcode:40001,errmsg:invalid credential}原因get_access_token()函数中缓存的token已过期2小时但未刷新。解决检查health_backend/health/utils.py中的token获取逻辑确保使用requests.Session()复用连接缓存token到Redis或本地文件本项目用cache.set(wechat_access_token, token, 7000)每次调用前校验cache.get(wechat_access_token)是否有效现象4Vue页面中血压数值显示为NaN但Django API返回正常JSON原因src/components/HealthCard.vue中computed属性未处理null值computed: { displaySystolic() { return this.record.systolic.toFixed(0) // 若systolic为nulltoFixed报错 } }解决改为安全写法displaySystolic() { return this.record.systolic ? this.record.systolic.toFixed(0) : -- }4. 数据流闭环验证从设备上报到家属微信通知的端到端走查4.1 模拟设备数据上报用Postman构造真实业务场景别依赖前端表单提交用Postman直接模拟物联网设备行为。新建POST请求URL填http://127.0.0.1:8000/health/api/v1/record/Headers加Content-Type: application/json Authorization: Token your_admin_token_here # 用superuser的Token或注释掉views.py中的permission_classesBody用Raw JSON{ device_id: elderly_001, elderly_user_id: 1, systolic: 172, diastolic: 98, heart_rate: 115, temperature: 36.8, timestamp: 2024-06-15T15:30:00Z, location: room_201 }为什么必须带elderly_user_id因为微信推送需要关联家属而elderly_user_id是外键指向UserProfile模型。若漏传Django会抛IntegrityError且无法触发后续预警。4.2 Django后台实时监控用Django Debug Toolbar抓取SQL与API耗时安装Debug Toolbar仅开发环境pip install django-debug-toolbar在health_backend/settings.py中添加INSTALLED_APPS [debug_toolbar] MIDDLEWARE [debug_toolbar.middleware.DebugToolbarMiddleware] INTERNAL_IPS [127.0.0.1]启动服务后在浏览器地址栏右侧会出现小虫图标。点击进入重点关注SQL tab确认HealthRecord.objects.filter(...).exists()查询是否命中索引device_id和timestamp应建联合索引Views tab查看RecordCreateView.post耗时若500ms需优化is_abnormal()逻辑避免多次DB查询Requests tab确认微信API调用是否成功response.status_code应为2004.3 微信模板消息调试用测试号快速验证推送链路正式公众号需资质审核但本项目提供test_wechat.py脚本供快速验证# 在health_backend目录下运行 python test_wechat.py --openid oABC1234567890 --template_id TEMPLATE_ID_HERE脚本会读取settings.py中的WECHAT_APPID和WECHAT_SECRET调用https://api.weixin.qq.com/cgi-bin/token获取access_token发送测试消息到指定openid输出{errcode:0,errmsg:ok}即成功避坑提示测试号的openid有效期仅7天且每个测试号最多绑定10个openid。务必在test_wechat.py中打印access_token确认其长度100字符——若只有32位说明你误用了APPSECRET当access_token。4.4 前端预警状态同步WebSocket vs 轮询的取舍项目未用WebSocket而是采用setInterval轮询/api/v1/alert/status/每10秒一次。原因很现实社区养老站网络不稳定WebSocket长连接易断开而轮询失败可自动重试。src/utils/alertPoller.js核心代码export default class AlertPoller { constructor() { this.intervalId null this.isPolling false } start() { if (this.isPolling) return this.isPolling true this.intervalId setInterval(() { this.fetchAlertStatus() }, 10000) // 10秒间隔平衡实时性与服务器压力 } async fetchAlertStatus() { try { const res await fetch(/api/v1/alert/status/, { headers: { Authorization: Token ${localStorage.getItem(token)} } }) const data await res.json() if (data.has_unread_alert) { this.triggerAlert(data.alert_info) // 触发前端弹窗语音 } } catch (e) { console.warn(Alert poll failed, retrying..., e) // 网络失败时不中断继续下一轮 } } triggerAlert(alert) { // 1. 显示大字弹窗 // 2. 播放对应MP3 // 3. 记录已读状态到localStorage } }参数说明10000毫秒是经验值——小于5秒增加服务器负载大于30秒老人可能错过黄金干预时间。我在养老院实测过10秒间隔下从设备上报到前端弹窗平均延迟12.3秒完全满足临床预警需求。5. 生产环境部署Docker一键打包与旧笔记本适配技巧5.1 Dockerfile深度解析为什么基础镜像选ubuntu:20.04而非alpine搜索热词里常提“docker部署”但本项目Dockerfile明确使用FROM ubuntu:20.04 # 而非更轻量的alpine:3.18原因直击痛点Alpine的musl libc与PyMySQL、NumPy等C扩展库兼容性差尤其在旧笔记本的Intel Atom处理器上pip install pymysql会编译失败。Ubuntu 20.04的glibc稳定且预装了systemd——这对需要开机自启的服务至关重要。Dockerfile关键段# 安装系统依赖关键 RUN apt-get update apt-get install -y \ python3.8 \ python3.8-venv \ python3.8-dev \ default-libmysqlclient-dev \ rm -rf /var/lib/apt/lists/* # 复制并安装Python依赖 COPY requirements.txt . RUN python3.8 -m venv /opt/venv \ /opt/venv/bin/pip install --upgrade pip \ /opt/venv/bin/pip install -r requirements.txt # 复制Django代码 COPY health_backend /opt/app/health_backend WORKDIR /opt/app/health_backend # 预迁移数据库避免容器启动时首次执行耗时过长 RUN /opt/venv/bin/python manage.py migrate --noinput # 暴露端口 EXPOSE 8000 CMD [/opt/venv/bin/python, manage.py, runserver, 0.0.0.0:8000]5.2 docker-compose.yml配置MySQL持久化与Nginx反向代理docker-compose.yml不是简单堆服务而是针对旧硬件优化version: 3.8 services: db: image: mysql:5.7 restart: unless-stopped environment: MYSQL_ROOT_PASSWORD: rootpass123 MYSQL_DATABASE: elderly_health MYSQL_USER: elderly_app MYSQL_PASSWORD: ElderlyPass2024! volumes: - ./data/mysql:/var/lib/mysql:rw # 关键数据落盘重启不丢 - ./conf/my.cnf:/etc/mysql/conf.d/my.cnf:ro # 降低InnoDB缓冲区适配2GB内存 command: --innodb-buffer-pool-size256M web: build: . restart: unless-stopped depends_on: - db environment: - DJANGO_SETTINGS_MODULEhealth_backend.settings.production - PYTHONUNBUFFERED1 volumes: - ./logs:/opt/app/health_backend/logs:rw - ./staticfiles:/opt/app/health_backend/staticfiles:rw - ./media:/opt/app/health_backend/media:rw ports: - 8000:8000 nginx: image: nginx:1.21 restart: unless-stopped volumes: - ./nginx.conf:/etc/nginx/nginx.conf:ro - ./staticfiles:/opt/app/health_backend/staticfiles:ro - ./media:/opt/app/health_backend/media:ro ports: - 80:80 - 443:443 depends_on: - web其中./conf/my.cnf内容精简[mysqld] innodb_buffer_pool_size 256M # 旧笔记本内存小不能按默认2G配 max_connections 50 # 限制并发防OOM skip-log-bin # 关闭binlog省磁盘IO5.3 旧笔记本部署实操4GB内存机器的生存指南我在一台联想ThinkPad X220i5-2520M, 4GB RAM, Ubuntu 20.04上实测部署关键技巧关闭图形界面节省内存sudo systemctl set-default multi-user.target sudo reboot启动后只剩命令行内存占用从1.8GB降至0.9GB。限制Docker内存避免OOM Killer杀进程编辑/etc/docker/daemon.json{ default-runtime: runc, runtimes: { runc: { path: runc } }, default-ulimits: { nofile: { Name: nofile, Hard: 65536, Soft: 65536 } }, experimental: false, live-restore: true, oom-score-adjust: -500 // 降低Docker进程被OOM Killer优先杀死的概率 }Nginx配置极致精简nginx.confevents { worker_connections 1024; use epoll; # Linux专用高效IO模型 } http { include mime.types; default_type application/octet-stream; sendfile on; keepalive_timeout 0; # 关闭长连接省内存 server { listen 80; location / { proxy_pass http://web:8000; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; } location /static/ { alias /opt/app/health_backend/staticfiles/; } location /media/ { alias /opt/app/health_backend/media/; } } }5.4 常见问题排查Docker启动失败、MySQL连接拒绝、Nginx 502现象1docker-compose up -d后db容器反复重启日志显示mysqld: Cant read dir of /etc/mysql/conf.d/原因./conf/my.cnf文件权限不对或路径不存在。解决执行mkdir -p ./conf touch ./conf/my.cnf再chmod 644 ./conf/my.cnf。现象2web容器日志报django.db.utils.OperationalError: (2003, Cant connect to MySQL server on db)原因Docker网络未就绪web服务启动早于db。解决在docker-compose.yml的web服务下加健康检查healthcheck: test: [CMD, python, manage.py, dbshell, -c, SELECT 1;] interval: 30s timeout: 10s retries: 5现象3浏览器访问http://localhost返回Nginx 502 Bad Gateway原因proxy_pass指向http://web:8000但web容器内Django未监听0.0.0.0:8000。解决确认health_backend/settings/production.py中ALLOWED_HOSTS [localhost, 127.0.0.1, your-server-ip] # 且manage.py中runserver命令为python manage.py runserver 0.0.0.0:80006. 真实场景加固家属微信绑定、离线语音包、血压趋势图的增量开发6.1 家属微信绑定流程从扫码到open_id存储的完整链路当前源码只支持管理员在Django Admin后台手动录入家属wechat_openid但真实场景需要老人子女扫码绑定。我在health_backend/health/views.py中补全了扫码逻辑from django.shortcuts import render, redirect from django.http import JsonResponse, HttpResponse from django.urls import reverse import qrcode from io import BytesIO from PIL import Image, ImageDraw, ImageFont def generate_bind_qr(request, elderly_id): 生成绑定二维码含临时token # 1. 生成7天有效的token import secrets token secrets.token_urlsafe(32) cache.set(fbind_token_{token}, elderly_id, 60*60*24*7) # 2. 构造扫码后跳转的URL微信JS-SDK需HTTPS bind_url request.build_absolute_uri( reverse(wechat_bind_callback) f?token{token} ) # 3. 生成二维码图片带logo qr qrcode.QRCode(version1, box_size10, border4) qr.add_data(bind_url) qr.make(fitTrue) img qr.make_image(fill_colorblack, back_colorwhite) # 添加小程序logo简化版实际用真实logo draw ImageDraw.Draw(img) try: font ImageFont.truetype(/usr/share/fonts/truetype/dejavu/DejaVuSans-Bold.ttf, 20) draw.text((50, 50), 扫码绑定家属, fillblack, fontfont) except: pass # 4. 返回图片 buffer BytesIO() img.save(buffer, formatPNG) return HttpResponse(buffer.getvalue(), content_typeimage/png) def wechat_bind_callback(request): 微信内扫码后跳转的页面 token request.GET.get(token) elderly_id cache.get(fbind_token_{token}) if not elderly_id: return render(request, bind_expired.html) # 渲染微信JS-SDK页面调用wx.login获取code return render(request, bind_page.html, {elderly_id: elderly_id})配套bind_page.html中集成微信JS-SDKscript srchttps://res.wx.qq.com/open/js/jweixin-1.6.0.js/script script wx.config({ debug: false, appId: {{ appid }}, timestamp: {{ timestamp }}, nonceStr: {{ nonceStr }}, signature: {{ signature }}, jsApiList: [openLocation] }); wx.ready(function() { wx.login({ success: function(res) { if (res.code) { p a hrefhttps://download.csdn.net/download/weixin_42874480/90457675 stylecolor:#ec7500;font-size:14px; 本文还有配套的精品资源点击获取 /a img altmenu-r.4af5f7ec.gif srchttps://csdnimg.cn/release/wenkucmsfe/public/img/menu-r.4af5f7ec.gif stylewidth:16px;margin-left:4px;vertical-align:text-bottom;cursor:text; /p
觉得有用,分享给同行:

为您的企业打造数字门面

稳重轻奢商务风格,端正雅致视觉,长效耐看不易过时。

立即咨询 →