最新公告
  • 欢迎您光临起源地模板网,本站秉承服务宗旨 履行“站长”责任,销售只是起点 服务永无止境!立即加入钻石VIP
  • uni-app+微信云开发,全栈个人小程序的搭建

    正文概述 掘金(咸鱼翻身翻两次)   2021-03-08   619

    前言

    微信云开发是微信平台功能已经出来挺久了,最近看了下云开发文档,准备动手写个小程序练练手。

    前端模块使用以前写过的一个用uni-app搭建的一个项目,云开发模块就是重新搭建。

    1、创建微信小程序

    首先在微信开发工具创建小程序,填入你的appid,后端服务选择小程序云开发。

    uni-app+微信云开发,全栈个人小程序的搭建

    创建完毕,目录结构如下:

    cloudfunctions 是云函数目录,miniprogram是小程序前端模块。

    uni-app+微信云开发,全栈个人小程序的搭建

    因为前端模块我要使用uni-app,所以得进行改造。
    miniprogram目录删除,把 vue-cli 创建 uni-app 项目代码复制进来,不懂怎么创建uni-app项目的点这里。

    安装依赖npm i,运行npm run dev:mp-weixin,最终目录如下:

    uni-app+微信云开发,全栈个人小程序的搭建

    2、重新指定小程序前端模块目录

    修改uni-app的打包输出路径:
    dev 模式编译出的各平台代码存放于根目录下的 /dist/dev/目录下,
    build 模式编译出的各平台代码存放于根目录下的 /dist/build/ 目录下,
    对于要固定的小程序目录很不友好,我们得固定输出目录。

    修改package.jsonscriptsdev:mp-weixinbuild:mp-weixin命令:

    
    "build:mp-weixin": "cross-env NODE_ENV=production UNI_PLATFORM=mp-weixin UNI_OUTPUT_DIR=dist/build/mp-weixin vue-cli-service uni-build",
         
    "dev:mp-weixin": "cross-env NODE_ENV=development UNI_PLATFORM=mp-weixin UNI_OUTPUT_DIR=dist/build/mp-weixin vue-cli-service uni-build --watch",
        
    

    添加UNI_OUTPUT_DIR=dist/build/mp-weixin,指定输出目录为dist/build/mp-weixin

    再修改project.config.json文件,把前端模块指定到dist/build/mp-weixin

     "miniprogramRoot": "dist/build/mp-weixin/",
    

    修改完成,打开微信开发工具,小程序就可以运行了。

    3、云开发

    初始化

    在云开发设置面板,新建个环境,后面的env取环境ID

    uni-app+微信云开发,全栈个人小程序的搭建

    小程序端

    在src/main.js 添加初始化方法

    wx.cloud.init({
      env: '5175aa',  //环境
      traceUser: true, //是否在将用户访问记录到用户管理中,在控制台中可见
    })
    

    云函数端

    // 初始化 cloud
    cloud.init({
      // API 调用都保持和云函数当前所在环境一致
      // env: cloud.DYNAMIC_CURRENT_ENV
      env: '5175aa'
    })
    

    4、编写第一个云函数

    云函数

    我们把cloudfunctions文件夹下的文件都删除,新建个main云函数:

    config.json

    {
      "permissions": {
        "openapi": []
      }
    }
    
    

    package.json

    {
      "name": "echo",
      "version": "1.0.0",
      "description": "",
      "main": "index.js",
      "scripts": {
        "test": "echo \"Error: no test specified\" && exit 1"
      },
      "author": "",
      "license": "ISC",
      "dependencies": {
        "wx-server-sdk": "~2.4.0"
      }
    }
    
    

    index.js

    // 云函数入口文件
    const cloud = require('wx-server-sdk')
    
    cloud.init({
      // API 调用都保持和云函数当前所在环境一致
      // env: cloud.DYNAMIC_CURRENT_ENV
      env: '5175aa'
    })
    
    // 云函数入口函数
    exports.main = async (event, context) => {
      const wxContext = cloud.getWXContext()
    
      return {
        event,
        openid: wxContext.OPENID,
        appid: wxContext.APPID,
        unionid: wxContext.UNIONID,
      }
    }
    
    

    uni-app+微信云开发,全栈个人小程序的搭建

    一个云函数就完成了,我们现在可以进行本地调试,或者上传到云端部署。 uni-app+微信云开发,全栈个人小程序的搭建

    本地调试步骤

    需要进入cloudfunctions/main目录下,安装依赖 npm i 再右键选择开启云函数本地调试

    上传到云端部署

    uni-app+微信云开发,全栈个人小程序的搭建

    小程序端调用

    wx.cloud.callFunction({
      // 云函数名称
      name: 'mian',
      // 传给云函数的参数
      data: {
        a: 1,
        b: 2,
      },
      success: function(res) {
        console.log(res.result.sum) // 3
      },
      fail: console.error
    })
    

    当然,Promise 风格的调用也是支持的:

    wx.cloud.callFunction({
      // 云函数名称
      name: 'main',
      // 传给云函数的参数
      data: {
        a: 1,
        b: 2,
      },
    })
    .then(res => {
      console.log(res.result) // 3
    })
    .catch(console.error)
    

    请求成功。

    5、云函数路由优化tcb-router

    云函数也有不少缺点:

    • 一个微信小程序只能创建50个云函数,不能满足复杂业务需求。

    • 每个云函数都都需要维护一份package.json

    所以我们需要用tcb-router进行优化,tcb-router是一个koa风格的云函数路由库。

    安装tcb-router

    cloudfunctions/main目录下

    npm i tcb-router -S

    cloudfunctions/main/index.js修改成:

    const cloud = require('wx-server-sdk')
    const TcbRouter = require('tcb-router')
    cloud.init({
      // API 调用都保持和云函数当前所在环境一致
      // env: cloud.DYNAMIC_CURRENT_ENV
      env: '5175aa'
    })
    
    // 云函数入口函数
    exports.main = async(event, context) => {
      const app = new TcbRouter({
        event
      })
     //全局中间件
      app.use(async(ctx, next) => {
        console.log('进入全局中间件')
        await next()
        console.log('退出全局中间件')
      })
      app.router('add', async(ctx, next) => {
        ctx.body = {
          data: '新增成功'
        }
      })	
      app.router('movie', async(ctx, next) => {
        ctx.body = {
          data: '输出'
        }
      })
      return app.serve()
    }
    
    

    小程序端调用

       wx.cloud.callFunction({
          name: 'main',
          data: {
            $url: 'add'
          },
        }).then((res) => {
          console.log(res)
        })
        
        wx.cloud.callFunction({
          name: 'main',
          data: {
            $url: 'movie'
          },
        }).then((res) => {
          console.log(res)
        })
    
    

    云函数模块化

    我们可以把路由的实现抽离成一个个js文件:

    cloudfunctions/main下新建common/index.js

    exports.login = async (ctx, next) => {
      console.log(ctx.cloud)
      console.log(ctx.db)
      ctx.body = {
         data: '输出'
      }
    }
    
    

    cloudfunctions/main/index.js中,用require导入,并且可以把clouddb对象挂载到ctx对象下,在实现模块就可以使用ctx.cloudctx.db调用对象

    // 云函数模板
    // 部署:在 cloud-functions/login 文件夹右击选择 “上传并部署”
    
    const cloud = require('wx-server-sdk')
    const TcbRouter = require('tcb-router');
    
    // 公共模块
    const common = require('./common/index')
    
    // 初始化 cloud
    cloud.init({
      // API 调用都保持和云函数当前所在环境一致
      // env: cloud.DYNAMIC_CURRENT_ENV
      env: '5175aa'
    })
    const db = cloud.database()
    
    exports.main = async (event, context) => {
      const app = new TcbRouter({event});
      // app.use 表示该中间件会适用于所有的路由
      app.use(async (ctx, next) => {
        ctx.db = db;
        ctx.cloud = cloud;
        console.log('进入全局中间件')
        await next()
        console.log('退出全局中间件')
      });
    
      //授权登录
      app.router('/login', common.login)
    
    
      return app.serve();
    }
    
    

    6、全局异常捕捉中间件

    到现在为止,可以进行应用开发了,但使用过koa的人都知道,我们还差个全局异常捕捉中间件,来统一处理服务器报错问题。

    新建个工具类utils/index.js

    module.exports = {
      // 手动报错
      throwError(code = 400, msg = '服务器错误') {
        const err = new Error(msg);
        err.code = code;
        err.msg = msg;
        throw err;
      },
    };
    

    cloudfunctions/main/index.js

    const utils = require('./utils/index')
    
    // app.use 表示该中间件会适用于所有的路由
      app.use(async (ctx, next) => {
        ctx.db = db;
        ctx.cloud = cloud;
        ctx.utils=utils  //挂载工具类
        try {
          await next();  //在下个环节报错就抛出错误
        } catch (err) {
          // 手动抛出异常 throwError函数触发
          if (err.msg) {
            ctx.body = {
              code: err.code,
              data: '',
              msg: err.msg,
            };
          } else {
          //自动报错
            ctx.body = {
              code: 500,
              data: '',
              msg: '服务器内部错误:' + err,
            };
          }
    
        }
      });
    

    测试

    手动抛出异常

    exports.login = async (ctx, next) => {
    
      ctx.uilts.throwError('500','手动抛出异常')
      
      ctx.body = {
         data: '输出'
      }
    }
    

    返回成功 uni-app+微信云开发,全栈个人小程序的搭建

    内部错误异常

    exports.login = async (ctx, next) => {
    
      console.log(a);  //错误  不存在a变量
      
      ctx.body = {
         data: '输出'
      }
    }
    

    返回成功 uni-app+微信云开发,全栈个人小程序的搭建

    7、数据库的增、删、查、改

    云开发的数据库,前端和云函数都可以进行操作,但在前端进行数据库操作有比较大的缺点:

    • 请求列表数据,直接操作数据库每次只能返回20条,云函数的话可以返回100条;
    • 还有就是直接调用数据库,所有的增删改查运算操作都是在手机本地运行的,数据量大的话,会耗用用户流量,而云函数则是在微信服务器上运算的。
    • 安全问题,可能会被恶意攻击

    所以还是在云函数进行数据库操作。

    初始化

    在云开发面板,新建个集合user(表)

    uni-app+微信云开发,全栈个人小程序的搭建

    在云函数初始化

    const db = cloud.database()
    

    插入数据

    db.collection('user').add({
      // data 字段表示需新增的 JSON 数据
      data: {
        // _id: 'todo-identifiant-aleatoire', // 可选自定义 _id,在此处场景下用数据库自动分配的就可以了
        description: "learn cloud database",
        due: new Date("2018-09-01"),
        tags: [
          "cloud",
          "database"
        ],
        // 为待办事项添加一个地理位置(113°E,23°N)
        location: new db.Geo.Point(113, 23),
        done: false
      },
      success: function(res) {
        // res 是一个对象,其中有 _id 字段标记刚创建的记录的 id
        console.log(res)
      }
    })
    

    获取一个记录的数据

    db.collection('user').doc('todo-identifiant-aleatoire').get().then(res => {
      // res.data 包含该记录的数据
      console.log(res.data)
    })
    
    

    获取多个记录的数据

    我们也可以一次性获取多条记录。通过调用集合上的 where 方法可以指定查询条件,再调用 get 方法即可只返回满足指定查询条件的记录,比如获取用户的所有未完成的待办事项:

    db.collection('user').where({
      _openid: 'user-open-id',
      done: false
    })
    .get({
      success: function(res) {
        // res.data 是包含以上定义的两条记录的数组
        console.log(res.data)
      }
    })
    

    更新数据

    db.collection('user').doc('todo-identifiant-aleatoire').update({
      // data 传入需要局部更新的数据
      data: {
        // 表示将 done 字段置为 true
        done: true
      },
      success: function(res) {
        console.log(res.data)
      }
    })
    

    删除一条记录

    
    db.collection('user').doc('todo-identifiant-aleatoire').remove({
      success: function(res) {
        console.log(res.data)
      }
    })
    

    更多用法可以去查看微信官方文档


    起源地下载网 » uni-app+微信云开发,全栈个人小程序的搭建

    常见问题FAQ

    免费下载或者VIP会员专享资源能否直接商用?
    本站所有资源版权均属于原作者所有,这里所提供资源均只能用于参考学习用,请勿直接商用。若由于商用引起版权纠纷,一切责任均由使用者承担。更多说明请参考 VIP介绍。
    提示下载完但解压或打开不了?
    最常见的情况是下载不完整: 可对比下载完压缩包的与网盘上的容量,若小于网盘提示的容量则是这个原因。这是浏览器下载的bug,建议用百度网盘软件或迅雷下载。若排除这种情况,可在对应资源底部留言,或 联络我们.。
    找不到素材资源介绍文章里的示例图片?
    对于PPT,KEY,Mockups,APP,网页模版等类型的素材,文章内用于介绍的图片通常并不包含在对应可供下载素材包内。这些相关商业图片需另外购买,且本站不负责(也没有办法)找到出处。 同样地一些字体文件也是这种情况,但部分素材会在素材包内有一份字体下载链接清单。
    模板不会安装或需要功能定制以及二次开发?
    请QQ联系我们

    发表评论

    还没有评论,快来抢沙发吧!

    如需帝国cms功能定制以及二次开发请联系我们

    联系作者

    请选择支付方式

    ×
    迅虎支付宝
    迅虎微信
    支付宝当面付
    余额支付
    ×
    微信扫码支付 0 元