
简介本资源为Discuz点微同城30.0全功能插件套件专为基于Discuz! X平台构建本地化生活服务平台的开发者与运营方设计覆盖同城分类信息、招聘、房产、婚恋、拼团、优惠抢购、小程序/H5前端等20余类高频业务场景支持快速搭建具备完整商业闭环的同城生态站点。压缩包含2000个文件主体为4117个PHP后端逻辑文件、2033个PNG图标与界面素材、1987个HTM/HTML页面模板及613个JS交互脚本辅以CSS样式256个、WXSS/WXML小程序组件共60余个及SQL数据库结构整体体积72.68MB结构完整、模块解耦清晰便于按需启用与二次开发。已有1403人学习下载。用户可直接部署全部47个官方插件如同城教育培训、疫情地图、招聘PC版、会员卡等获取开箱即用的前后端一体化解决方案并通过大量weui.css、style.css等样式文件快速统一UI风格显著降低定制化开发成本。1. Discuz 点微同城 30.0 全套插件47个不是“一键安装包”而是需深度适配 H5 与小程序双端的模块化扩展体系Discuz 点微同城 30.0 这套标称含 47 个插件的集成方案本质不是传统意义上的 Discuz 插件集合而是一套围绕本地生活服务场景重构的、具备完整前后端协同能力的扩展架构。它把 Discuz 3.3 作为用户中心与内容底座将门店管理、预约下单、LBS 推送、多端同步等能力拆解为可独立启用/禁用的插件单元并强制要求 H5 页面与微信小程序必须共用同一套业务逻辑层如订单状态机、优惠券核销规则、地理位置校验策略。这意味着哪怕你只启用其中 5 个插件也必须完成 H5 端基于 WeUI.css 的样式重写、小程序端 wxs 与 WXML 的组件映射、以及两者共用的 API 接口签名机制。它解决的不是“论坛加功能”的问题而是“如何让 Discuz 用户无缝切换到本地生活服务闭环”的工程落地问题——适合已有 Discuz 3.3 稳定站点、正启动社区 O2O 升级、且团队具备 PHP 后端 Vue/UniApp 前端双栈能力的技术负责人或运维工程师。2. 拆解点微同城 30.0 插件包结构47 个插件按功能域分组核心依赖项必须优先部署点微同城 30.0 的 47 个插件并非平铺直列而是存在明确的层级依赖关系。官方未公开文档但通过实际解压discuz_plugin_dianwei_30.0.zip并分析install.php与config.php可确认其分为四类基础支撑类8 个、LBS 服务类12 个、交易履约类15 个、多端桥接类12 个。其中dianwei_core、dianwei_location、dianwei_api三个插件构成不可绕过的启动链——若未先启用它们其余插件在 Discuz 后台插件列表中将显示为灰色不可用状态。2.1 插件目录结构与启用顺序验证解压后根目录下可见标准 Discuz 插件结构source/plugin/dianwei_* ├── dianwei_core/ # 必启提供全局常量、数据库表注册、钩子注入入口 ├── dianwei_location/ # 必启封装高德/腾讯地图 SDK 调用、地理围栏计算、坐标系转换 ├── dianwei_api/ # 必启定义 /api/dianwei/ 下所有 REST 接口路由及 JWT 验签中间件 ├── dianwei_store/ # 依赖 corelocation门店信息管理 ├── dianwei_order/ # 依赖 coreapi订单创建与状态流转 └── ...其余 44 个提示Discuz 后台启用插件时若提示“插件依赖未满足”不要直接点击“忽略依赖”应进入source/plugin/dianwei_core/install.php查看$dependency数组确认缺失插件名。常见错误是误将dianwei_location启用在dianwei_core之前导致class_location类未加载后续所有地理相关插件初始化失败。2.2 数据库表自动注册机制与手动补全要点dianwei_core插件在首次启用时会执行discuz_plugin_dianwei_core::onInstall()方法调用DB::query()创建 23 张新表如pre_dianwei_store、pre_dianwei_order并修改pre_common_setting表插入配置项。但实测发现当 Discuz 主库字符集非utf8mb4_unicode_ci时部分含 emoji 字段如门店简介、用户评价的建表语句会报错中断导致pre_dianwei_user_address等 5 张表缺失。此时需手动补全执行以下 SQL请替换pre_为你的实际表前缀-- 补全用户收货地址表关键H5 和小程序下单均依赖此表 CREATE TABLE pre_dianwei_user_address ( id int(10) unsigned NOT NULL AUTO_INCREMENT, uid int(10) unsigned NOT NULL DEFAULT 0, name varchar(50) NOT NULL DEFAULT , mobile varchar(20) NOT NULL DEFAULT , province varchar(50) NOT NULL DEFAULT , city varchar(50) NOT NULL DEFAULT , district varchar(50) NOT NULL DEFAULT , address varchar(255) NOT NULL DEFAULT , longitude decimal(10,7) NOT NULL DEFAULT 0.0000000, latitude decimal(10,7) NOT NULL DEFAULT 0.0000000, is_default tinyint(1) NOT NULL DEFAULT 0, createtime int(10) unsigned NOT NULL DEFAULT 0, PRIMARY KEY (id), KEY uid (uid) ) ENGINEInnoDB DEFAULT CHARSETutf8mb4 COLLATEutf8mb4_unicode_ci;2.2.1 表字段设计逻辑说明longitude/latitude使用decimal(10,7)是为兼容高德地图返回的 7 位小数精度坐标如116.4809721避免 float 类型存储导致的定位漂移is_default为 tinyint(1) 而非 enum因小程序端需通过UPDATE ... SET is_default0 WHERE uid?批量取消旧默认值再设新值enum 在批量更新时易触发 MySQL 严格模式报错createtime存储 Unix 时间戳而非 datetime与 Discuz 原生common_member表时间字段类型一致便于跨表 JOIN 查询。3. H5 端接入基于 WeUI.css 构建响应式页面重点解决定位权限与缓存一致性点微同城 H5 端并非简单套用 Discuz 默认模板而是以weui.css为视觉基底通过独立入口/dianwei/h5/加载 Vue 2.6 单页应用。其核心挑战不在 UI 实现而在微信浏览器环境下的定位授权链路与离线缓存策略冲突。3.1 微信内嵌 H5 获取定位的三步校验流程微信对wx.getLocation的调用有明确限制必须在用户主动触发如点击按钮后才能调用且需提前配置 JSAPI 安全域名。点微同城 H5 的实现路径如下预检 JSAPI 权限在main.js中调用wx.config()传入后端生成的签名签名算法需与dianwei_api插件中class_dianwei_api_sign完全一致用户显式授权页面加载后不自动获取定位而是展示「开启位置服务」按钮绑定clickgetLocation降级兜底逻辑若wx.getLocation失败如用户拒绝、iOS 15 Safari 限制则 fallback 到 HTML5 Geolocation API并弹窗提示“将使用浏览器定位精度可能较低”。// utils/location.js export function getLocation() { return new Promise((resolve, reject) { if (window.wx typeof wx.getLocation function) { // 微信 JSAPI 方式高精度 wx.getLocation({ type: wgs84, // 返回 GPS 坐标与高德地图 SDK 兼容 success: (res) { resolve({ lat: res.latitude, lng: res.longitude }); }, fail: () { // 降级到浏览器 API navigator.geolocation.getCurrentPosition( (pos) resolve({ lat: pos.coords.latitude, lng: pos.coords.longitude }), (err) reject(err) ); } }); } else { // 非微信环境直接走浏览器 API navigator.geolocation.getCurrentPosition( (pos) resolve({ lat: pos.coords.latitude, lng: pos.coords.longitude }), (err) reject(err) ); } }); }注意wx.config()的jsApiList必须包含getLocation且后端签名时使用的nonceStr、timestamp、url三元组需与前端请求 URL 完全一致包括 query 参数否则签名验证失败wx.getLocation将静默不可用。3.2 H5 页面缓存策略与 Discuz 登录态同步点微同城 H5 采用service-workerCache API实现离线资源缓存但带来新问题Discuz 用户登录态authcookie在 service worker 中不可见导致缓存页面无法携带登录凭证发起 API 请求。解决方案是将登录态从 cookie 迁移至 localStorage 请求头透传用户登录成功后dianwei_api插件返回access_token前端存入localStorage.setItem(dwtoken, token)所有/api/dianwei/请求在axios.interceptors.request中添加config.headers.Authorization Bearer localStorage.getItem(dwtoken);同时在service-worker.js的fetch事件监听中对/api/dianwei/请求手动添加 headerevent.respondWith( fetch(event.request.clone(), { headers: { Authorization: Bearer localStorage.getItem(dwtoken) || } }) );3.2.1 WeUI.css 与 Discuz 主题的样式隔离方案WeUI.css 默认样式会污染 Discuz 原有.postcontent、.pl等类名。点微同城采用 CSS Modules 方案在 Vue 组件中template div classdianwei-h5 weui-button clicksubmit提交/weui-button /div /template style module .dianwei-h5 :global(.weui-btn) { border-radius: 4px; /* 覆盖 WeUI 默认 2px */ } /style关键点:global()用于穿透作用域确保 WeUI 组件样式生效而外层.dianwei-h5保证不泄漏到 Discuz 全局。4. 小程序端对接UniApp 编译为微信小程序重点处理 API 签名与动态标题点微同城 30.0 的小程序前端基于 UniApp 开发目标平台为微信小程序。其核心难点在于如何让 UniApp 编译后的代码复用 Discuz 后端已有的 JWT 签名体系同时支持小程序原生能力如wx.navigateToMiniProgram跳转其他小程序。4.1 UniApp 中复用 Discuz API 签名逻辑Discuzdianwei_api插件生成的签名是 PHP 实现的 HMAC-SHA256UniApp 需用 JavaScript 完全复现。关键参数包括appid固定为dianwei、timestamp秒级时间戳、nonce16 位随机字符串、path如/order/create、bodyJSON 字符串需排序 key 后序列化。// utils/sign.js import CryptoJS from crypto-js export function generateSign(params) { const { appid dianwei, timestamp, nonce, path, body } params // 1. body 对象 key 排序后 JSON.stringifyDiscuz 端使用 ksort json_encode const sortedBody JSON.stringify( Object.keys(JSON.parse(body)) .sort() .reduce((obj, key) { obj[key] JSON.parse(body)[key] return obj }, {}) ) // 2. 拼接待签名字符串 const strToSign ${appid}${timestamp}${nonce}${path}${sortedBody} // 3. 使用 Discuz 后台配置的 secret_key 计算 HMAC const secretKey uni.getStorageSync(dianwei_secret) || your-secret-key return CryptoJS.HmacSHA256(strToSign, secretKey).toString(CryptoJS.enc.Base64) }提示secret_key不可硬编码在前端应在小程序首次启动时通过uni.login()获取 code调用/api/dianwei/auth/init接口由后端返回加密后的密钥片段再拼接成完整 secret。4.2 小程序动态设置标题与顶部导航栏适配点微同城小程序需根据当前页面如门店详情页、订单支付页动态设置标题且需兼容 iOS/Android 不同状态栏高度。Discuz 原生不提供此能力需在pages.json中关闭原生导航栏改用自定义navigation-bar组件{ path: pages/store/detail, style: { navigationStyle: custom, // 关键禁用原生导航栏 navigationBarBackgroundColor: #ffffff, navigationBarTextStyle: black } }然后在pages/store/detail.vue中template view classcontainer custom-nav-bar :titlestoreName :show-backtrue / !-- 页面内容 -- /view /template script export default { data() { return { storeName: } }, onLoad(options) { // 从 options 或 vuex 获取门店名设置标题 this.storeName options.store_name || 门店详情 } } /script4.2.1 自定义导航栏组件实现要点使用uni.getSystemInfoSync().statusBarHeight获取状态栏高度动态设置padding-top左侧返回图标使用uni.navigateBack()右侧分享按钮调用uni.showShareMenu()标题文字字号设为17px微信规范颜色#333避免使用font-weight: boldiOS 渲染异常。5. H5 与小程序数据互通验证通过订单号反查与地理位置校验双维度确认一致性47 个插件的价值最终体现在 H5 与小程序用户行为数据的实时互通上。最典型的验证场景是用户在 H5 页面下单后能否在小程序“我的订单”中立即看到且订单中的配送地址经纬度与 H5 端获取值完全一致这需要从数据库和接口两个层面交叉验证。5.1 订单号生成规则与跨端唯一性保障点微同城订单号格式为DW{YMD}{6位随机数}{3位校验码}例如DW20240615123456789。其中{YMD}为当日日期非时间戳确保每日订单号空间独立{6位随机数}由mt_rand(100000, 999999)生成避免自增 ID 暴露业务量{3位校验码}为crc32(订单主体JSON字符串) % 1000用于防篡改。验证方法在 H5 下单后立即查询数据库SELECT order_sn, longitude, latitude, createtime FROM pre_dianwei_order WHERE order_sn LIKE DW20240615% ORDER BY createtime DESC LIMIT 1;再从小程序端调用/api/dianwei/order/list?uid123比对返回 JSON 中order_sn、address.longitude、address.latitude是否与数据库完全一致注意浮点数需保留 7 位小数比对。5.2 地理位置校验失败的典型日志定位当 H5 与小程序订单地址偏差超过 500 米时大概率是坐标系转换错误。点微后台日志中搜索关键词geo_convert_error可定位到source/plugin/dianwei_location/function.php中的convert_coordinate()函数。该函数默认将微信返回的gcj02坐标转为wgs84但若传入参数frombd09百度坐标系则转换结果失效。修复方式在 H5 端getLocation()成功回调中明确指定坐标系wx.getLocation({ type: gcj02, // 强制要求微信返回国测局坐标系 success: (res) { // 此时 res.longitude/res.latitude 为 gcj02可直接传给后端 } });5.2.1 跨端数据一致性检查表检查项H5 端来源小程序端来源数据库字段一致性要求用户 UIDlocalStorage.getItem(duid)uni.getStorageSync(duid)pre_dianwei_order.uid完全相等订单创建时间Date.now()毫秒Date.now()毫秒pre_dianwei_order.createtime转换为秒后相等门店 IDURL 参数store_id123options.store_idpre_dianwei_order.store_id数值相等配送地址经纬度res.latitude/res.longitudegcj02e.detail.latitude/e.detail.longitudegcj02pre_dianwei_order.longitude/pre_dianwei_order.latitude保留 7 位小数后字符串完全匹配执行该表任一检查项失败即表明 H5 与小程序未真正打通需回溯dianwei_api插件的请求解析逻辑或dianwei_location的坐标入库逻辑。本文还有配套的精品资源点击获取