• 01 Taro_Mall 开源多端小程序框架设计


    项目介绍

    Taro_Mall是一款多端开源在线商城应用程序,后台是基于litemall基础上进行开发,前端采用Taro框架编写,现已全部完成小程序和h5移动端,后续会对APP,淘宝,头条,百度小程序进行适配。Taro_Mall已经完成了 litemall 前端的所有功能

    扫码体验

    由于小程序没有认证,只发布了一个预览版,只能加15个人,如有需要,请点击小程序申请

    小程序 h5移动端

    项目架构

    项目用Taro做跨端开发框架,Taro基本采用React的写法,项目集成了 redux dva 控制单向数据流,用immer来提供不可变数据,提升整体的性能,减少渲染。

    初始化项目

    taro init Taro_Mall
    

    进入项目目录开始开发,可以选择小程序预览模式,或者 h5 预览模式,若使用微信小程序预览模式,则需要自行下载并打开微信开发者工具,选择预览项目根目录。

    微信小程序编译和发布

    yarn dev:weapp  // 编译预览
    yarn build:weapp // 构建发布
    

    h5编译和发布

    yarn dev:h5  // 编译预览
    yarn build:h5 // 构建发布
    

    其它端可以查看package.json 提供的命令

    到这里,我们已经把项目初始化完毕,接下来我们引入 dva-core 和 immer,引入dva-core包就可以,不需要引入dva包,dva 包是对 dva-core 和路由,请求库等做了一层封装

    yarn add dva-core dva-imme --save
    

    在src 目录下新建 dva.js 文件,文件内容如下, 在创建App的时候,我们把dva-immer插件引入其中。

    import {create} from 'dva-core';
    import {createLogger} from 'redux-logger';
    // import createLoading from 'dva-loading';
    import immer from 'dva-immer';
    
    let app;
    let store = {};
    let dispatch;
    
    
    function createApp(opt) {
      // opt.onAction = [createLogger()];  // 这里可以引入 redux-logger
      app = create(opt);
      // app.use(createLoading({}));
      app.use(immer()); // 引入 immer
    
      if (!global.registered) opt.models.forEach(model => app.model(model));
      global.registered = true;
      app.start();
    
      store = app._store;
      app.getStore = () => store;
    
      dispatch = store.dispatch;
    
      app.dispatch = dispatch;
      if (window) {
        window.g_app = app;
      }
      return app;
    }
    
    export default {
      createApp,
      getDispatch() {
        return app.dispatch;
      },
      dispatch: store.dispatch
    }
    
    

    接下来在入口文件当中引入我们的 dva 文件

    import dva from './dva';
    import models from './models';
    
    const dvaApp = dva.createApp({
      initialState: {},
      models: models,
      onError(e, dispatch) {
        console.log('系统出错了!');
        // dispatch(action("sys/error", e));
      },
    });
    const store = dvaApp.getStore();
    

    我们发现dva创建的时候需要引入models,我们在src目录创建models 来存放我们的 model 文件,来管理状态, 我们看下models 文件下的入口文件

    import home from './home';
    ......
    
    export default [
      home,demo, goods, catalog, search       // 导入我们的模块
    ]
    
    

    我们可以写一个简单的model,例如: demo.js

    import delay from '../utils/delay';
    
    export default {
      namespace: 'demo',
      state: {
        list: [],
        counter: {
          num: 0,
        }
      },
      reducers: {
        add: (state, {payload}) => {
          state.counter.num ++;
        },
    
        dec: (state, {payload}) => {
          state.counter.num --;
        }
    
      },
      effects: {
        *asyncAdd(_, {all, call, put}) {
          yield call(delay, 2000);//增加延迟测试效果
    
          yield put({type: 'add'});
        },
      }
    };
    
    

    接下来,我们要在taro redux的中的Provider传入 store

    <Provider store={store}>
            <Index />
     </Provider>
    

    接下来对请求库做下简单的封装,这里主要封装了对错误消息和统一处理,和提供了get,post方法,如需其它方法,可自行封装

    import Taro from '@tarojs/taro';
    import {showErrorToast} from '../utils/util';
    
    
    /**
     * 封封微信的的request
     */
    function request(url, data = {}, method = "GET") {
      return new Promise(function(resolve, reject) {
        Taro.request({
          url: url,
          data: data,
          method: method,
          header: {
            'Content-Type': 'application/json',
            'X-Litemall-Token': Taro.getStorageSync('token')
          },
          success: function(res) {
    
            if (res.statusCode == 200) {
    
              if (res.data.errno == 501) {
                // 清除登录相关内容
                try {
                  Taro.removeStorageSync('userInfo');
                  Taro.removeStorageSync('token');
                } catch (e) {
                  // Do something when catch error
                }
                // 切换到登录页面
                Taro.navigateTo({
                  url: '/pages/auth/login/login'
                });
              } else if(res.data.errno == 0) {
                resolve(res.data.data);
              } else {
                // Taro.showModal({
                //   title: '错误信息',
                //   content: res.data.errmsg,
                //   showCancel: false
                // });
                showErrorToast(res.data.errmsg);
                reject(res.data.errmsg);
              }
            } else {
              reject(res.errMsg);
            }
    
          },
          fail: function(err) {
            reject(err)
          }
        })
      });
    }
    
    request.get = (url, data) => {
      return request(url, data, 'GET');
    }
    
    request.post = (url, data) => {
      return request(url, data, 'POST');
    }
    
    export default request;
    
    

    现在我们基本就可以用我们熟悉的套路去做开发了

    结束语

    Taro 遵循 React 语法规范的 多端开发 解决方案。当业务要求同时在不同的端都要求有所表现的时候,针对不同的端去编写多套代码的成本显然非常高,这时候只编写一套代码就能够适配到多端的能力就显得极为需要。

    github : Taro_Mall 如果对大家有帮助,请 star 一下

  • 相关阅读:
    Java8中findAny和findFirst的区别
    Lombok使用与原理
    java.util.ConcurrentModificationException异常原因及解决方法
    PacketTooBigException问题解决
    数据库中空字符串和NULL值两个概念的区别
    Java8采用stream、parallelStream迭代的区别
    Spring四大注解
    @Qualifier的作用和应用
    @resource和@autowired的区别是什么
    @Transactional注解详细用法
  • 原文地址:https://www.cnblogs.com/qiaojie/p/12431670.html
Copyright © 2020-2023  润新知