Tacomall Documentation

repository·master·Indexed 20 days ago

https://github.com/realjerrytang/tacomall

An open-source, cross-platform new retail e-commerce system built with Spring Boot 3, Vue 3, and UniApp. The system includes a Vue.js management admin, a Spring Boot backend server, a Flutter 2.0 and Vue 3 cashier application, and a UniApp mini-program mall. It supports member distribution, regional agency, product retail, and integrated payment methods like WeChat Pay and CCB scan-to-pay.

Tokens
17.7K
Snippets
77
Records
83
Agent score
72%

What's inside Tacomall

  1. Overview of Tacomall Project Structure

    master

    Tacomall is a new retail e-commerce system featuring member distribution, regional agency, and product retail. The project is divided into four main modules:

    • admin: A management backend developed with Vue.js for managing products, members, permissions, and orders.
    • server: A multi-module Spring Boot backend providing API services for all frontend applications.
    • cashier: A cross-platform cashier application built with Flutter 2.0 and Vue 3 + Vite. It supports WeChat Pay, CCB scan-to-pay, inventory management, stocktaking, and marketing activities.
    • ma: A mini-program mall developed using UniApp.
  2. Set up the Tacomall Development Environment

    master

    To run Tacomall locally for development, ensure you have the following installed:

    • Docker and Docker Compose
    • Python >= 3.10
    • Node.js

    Step 1: Database Setup

    Start the MySQL container using Docker Compose:

    docker-compose up --build -d mysql

    Step 2: Initialize Database

    Import the SQL schema into your MySQL instance:

    cd ./server/tacomall.sql && mysql -u username -p tacomall < tacomall.sql

    (Note: Replace username with your actual MySQL username)

    Step 3: Start the Admin Backend

    Navigate to the admin directory, install dependencies, and start the development server:

    cd ./admin && npm install && npm run dev

    Step 4: Start the Server

    Open the server directory in an IDE like VS Code or IntelliJ IDEA to run the Spring Boot application.

    docker-compose up --build -d mysql
    cd ./server/tacomall.sql && mysql -u username -p tacomall < tacomall.sql
    cd ./admin && npm install && npm run dev
  3. Implement WeChat Login in tacomall-ma

    master

    The login page uses uni.login to obtain a WeChat code, which is then sent to the backend via the Member.sendApi method using the wxLogin endpoint.

    Workflow:

    1. Trigger uni.login to get the code.
    2. Call Member.sendApi('wxLogin', ...) with the following payload:
      • params.code: The code from uni.login.
      • params.appid: The MP_APPID from your config.
      • params.invite: An optional invitation string retrieved from page load options.
    3. On success (status: true), the response provides a token and an isNew flag.
    4. Store the token in localCache using the TOKEN_KEY.
    5. Call getMemberInfo() to refresh user data.
    6. Redirect the user:
      • If isNew is true: Redirect to /pages/profile/initial/index.
      • If isNew is false: Redirect to /pages/index/index.

    Note: The page supports an invite parameter passed via URL/route options during onLoad.

    // Conceptual implementation of the login logic
    const login = (e) => {
      uni.login({
        success(loginRes) {
          const { code } = loginRes;
          Member.sendApi('wxLogin', {
            params: { 
              code, 
              appid: MP_APPID, 
              invite: invite.value 
            }, 
            body: {}
          }, { errorTip: 'Login failed' }).then(res => {
            const { status, data } = res;
            if (status) {
              const { token, isNew } = data;
              localCache.set(TOKEN_KEY, token);
              getMemberInfo();
              // Navigation logic based on isNew flag
              isNew ? rep('/pages/profile/initial/index') : swi('/pages/index/index');
            }
          });
        }
      });
    }
  4. Configure the WeChat Mini Program project settings

    master

    The project.config.json file defines the configuration for the WeChat Mini Program project. It controls compilation types, library versions, and build-time settings like ES6 support and minification.

    {
      "appid": "wx0038a1d24bb9eb99",
      "compileType": "miniprogram",
      "libVersion": "2.25.4",
      "packOptions": {
        "ignore": [],
        "include": []
      },
      "setting": {
        "coverView": true,
        "es6": true,
        "postcss": true,
        "minified": true,
        "enhance": true,
        "showShadowRootInWxmlPanel": true,
        "packNpmRelationList": [],
        "babelSetting": {
          "ignore": [],
          "disablePlugins": [],
          "outputPath": ""
        }
      },
      "condition": {},
      "editorSetting": {
        "tabIndent": "insertSpaces",
        "tabSize": 2
      }
    }
  5. Configure dependency transpilation in vue.config.js

    master

    In the ma package, you can use the transpileDependencies option in vue.config.js to ensure specific dependencies are processed by Babel. This is necessary for libraries that ship as ES6+ code to ensure compatibility with older browsers. For this project, uview-plus is explicitly included in the transpilation list.

    module.exports = {
      transpileDependencies: [
        'uview-plus'
      ],
    };
  6. Configure history URL settings

    master

    The default export of the configuration module provides settings for URL history management:

    • historyUrlKey: The key used to store history in local storage (default: "local-url-history").
    • historyUrlSize: The maximum number of history entries to keep (default: 10).
    import config from '@/config';
    
    console.log(config.historyUrlKey); // "local-url-history"
    console.log(config.historyUrlSize); // 10
  7. Configure environment variables for Docker Compose

    master

    The docker-compose.yml file uses several environment variables to parameterize the service builds, container names, ports, and database configurations. You must define these variables in your environment (e.g., in a .env file) before running docker-compose up.

    Core Variables

    • PROJECT_NAME: Used as a prefix for all container names (e.g., ${PROJECT_NAME}_mysql).
    • IMAGES_ROOT: The base path for building service images and mounting configuration volumes.
    • SPRING_PROFILE: Sets the Spring Boot profile for the open, admin, and ma services.

    Service-Specific Variables

    MySQL

    • PORT_MYSQL: The host port mapped to container port 3306.
    • MYSQL_ROOT_PASSWORD: The root password for the MySQL instance.
    • MYSQL_DATABASE: The name of the initial database to create.

    Redis

    • PORT_REDIS: The host port mapped to container port 6379.

    Nginx

    • PORT_NGINX: The host port mapped to container port 80.

    Application Services (open, admin, ma)

    Each service has a corresponding port variable:

    • PORT_OPEN: Mapped to container port 4000.
    • PORT_ADMIN: Mapped to container port 4001.
    • PORT_MA: Mapped to container port 4002.
  8. Extract year and month from a date

    master

    Use getYear(d) and getMonth(d) to extract date components from a date object or string. Note that getMonth(d) returns a 1-based month (1-12).

    import { getYear, getMonth } from 'ma/src/utils/fn';
    
    const year = getYear(new Date());
    const month = getMonth(new Date());
  9. Initialize the job dashboard line chart

    master

    The lineChartInit(data) function uses ECharts to render a line chart representing job status trends over time. It targets an HTML element with the ID lineChart.

    Chart Configuration:

    • Title: Uses I18n.job_dashboard_date_report.
    • Legend: Displays statuses for I18n.joblog_status_suc, I18n.joblog_status_fail, and I18n.joblog_status_running.
    • X-Axis: Categorical data provided by data.content.triggerDayList.
    • Series: Three stacked line series with area styles:
      • Success: data.content.triggerDayCountSucList (Color: #00A65A)
      • Failure: data.content.triggerDayCountFailList (Color: #c23632)
      • Running: data.content.triggerDayCountRunningList (Color: #F39C12)
    /**
     * line Chart Init
     */
    function lineChartInit(data) {
        // ... configuration object construction ...
        var lineChart = echarts.init(document.getElementById('lineChart'));
        lineChart.setOption(option);
    }
  10. Get the current day of the week as a Chinese character

    master

    The getWeek() function returns the current day of the week as a single Chinese character string:

    • (Sunday)
    • (Monday)
    • (Tuesday)
    • (Wednesday)
    • (Thursday)
    • (Friday)
    • (Saturday)
    import { getWeek } from 'ma/src/utils/fn';
    
    const dayStr = getWeek(); // e.g., "一" for Monday
  11. Fetch and refresh chart data via freshChartDate()

    master

    The freshChartDate(startDate, endDate) function performs an AJAX POST request to retrieve job dashboard report data for a specific time range. It expects the server to return a JSON object containing chart data. Upon a successful response (code 200), it triggers the initialization of both line and pie charts.

    API Endpoint:

    • URL: {base_url}/chartInfo
    • Method: POST
    • Payload Parameters:
      • startDate: Formatted as YYYY-MM-DD HH:mm:ss
      • endDate: Formatted as YYYY-MM-DD HH:mm:ss

    Response Structure (Success): The response should include a content object with the following fields used for charting:

    • triggerDayList: Array of dates for the X-axis.
    • triggerDayCountSucList: Array of success counts for the line chart.
    • triggerDayCountFailList: Array of failure counts for the line chart.
    • triggerDayCountRunningList: Array of running counts for the line chart.
    • triggerCountSucTotal: Total success count for the pie chart.
    • triggerCountFailTotal: Total failure count for the pie chart.
    • triggerCountRunningTotal: Total running count for the pie chart.
    /**
     * fresh Chart Date
     *
     * @param startDate
     * @param endDate
     */
    function freshChartDate(startDate, endDate) {
        $.ajax({
            type : 'POST',
            url : base_url + '/chartInfo',
            data : {
                'startDate':startDate.format('YYYY-MM-DD HH:mm:ss'),
                'endDate':endDate.format('YYYY-MM-DD HH:mm:ss')
            },
            dataType : "json",
            success : function(data){
                if (data.code == 200) {
                    lineChartInit(data)
                    pieChartInit(data);
                } else {
                    // Error handling with layer.open
                }
            }
        });
    }