跳转到内容

微信小程序开发

一、微信小程序生态概述

1.1 什么是微信小程序

微信小程序是一种不需要下载安装即可使用的应用,用户扫一扫或搜一下即可打开。它运行在微信内置的浏览器引擎中,具备接近原生 App 的体验,同时享有微信庞大的用户生态和社交能力。

1.2 小程序与普通网页的区别

对比维度

普通网页

微信小程序

运行环境

浏览器

微信内置 JS Core + WebView

渲染方式

DOM / BOM

WXML + WXSS(类 Vue 数据驱动)

设备能力

受限(需 HTTPS + 用户授权)

丰富(蓝牙、NFC、扫码等原生 API)

包大小限制

无硬性限制

主包 2MB,总包 20MB(含分包)

发布审核

无需审核

需微信审核(1-7 个工作日)

登录体系

自行实现

微信登录(wx.login + code2Session)

1.3 跨端框架简介

微信原生开发使用 WXML/WXSS/JS 技术栈,语法与标准 Web 差异较大。跨端框架可以让开发者使用熟悉的 Vue/React 语法,一套代码同时编译到微信小程序、支付宝小程序、H5、App 等多个平台。

主流跨端框架: Taro(React/Vue/Nerv)、uni-app(Vue 2/3)、mpvue(Vue 2,已停止维护)、WePY(类 Vue 2)、Remax(React)、kbone(Web 转小程序)


二、跨端框架对比与选型

2.1 主流框架对比

框架

技术栈

GitHub Stars

跨端支持

特点

Taro

React / Vue 3 / Nerv

36k+

微信/支付宝/百度/字节/H5/RN

京东出品,社区活跃,生态完善

uni-app

Vue 2 / Vue 3

40k+

微信/支付宝/百度/字节/快应用/H5/App

DCloud 出品,App 端支持最强

mpvue

Vue 2

20k+

微信/百度/字节

美团出品,已停止维护

WePY

类 Vue 2

22k+

微信/支付宝

腾讯出品,2.x 版本较完善

2.2 选型建议

推荐方案:

  • React 技术栈 → Taro(京东维护,社区最活跃的 React 系小程序框架)
  • Vue 技术栈 + 需要 App 端 → uni-app(App 端交付能力最强,插件市场丰富)
  • Vue 技术栈 + 仅小程序/H5 → Taro(Vue 3 支持)或 uni-app 均可
  • 已有 H5 项目想转小程序 → Taro(React 项目)或 uni-app(Vue 项目)

三、项目搭建与工程化

3.1 Taro 项目创建

# 安装 CLI
npm install -g @tarojs/cli

# 创建项目
taro init my-project

# 选择模板:React + TypeScript(推荐)
# 或 Vue 3 + TypeScript

# 进入项目
cd my-project

# 安装依赖
npm install

# 运行微信小程序开发模式
npm run dev:weapp

# 构建微信小程序
npm run build:weapp

3.2 uni-app 项目创建

# 创建项目(Vue 3 + TypeScript)
npx degit dcloudio/uni-preset-vue#vite-ts my-uni-app

# 或使用 HBuilderX 可视化创建

# 安装依赖
cd my-uni-app
npm install

# 运行微信小程序
npm run dev:mp-weixin

# 构建
npm run build:mp-weixin

3.3 项目目录结构(Taro)

src/
├── pages/          # 页面文件
│   └── index/
│       ├── index.tsx       # 页面逻辑
│       ├── index.scss      # 页面样式
│       └── index.config.ts # 页面配置
├── components/     # 公共组件
├── services/       # API 请求封装
├── store/          # 状态管理
├── utils/          # 工具函数
├── app.ts          # 应用入口
├── app.scss        # 全局样式
└── app.config.ts   # 全局配置(路由、窗口等)

3.4 TypeScript 配置

Taro 和 uni-app 均内置 TypeScript 支持。推荐开启 strict 模式以提升代码质量:

{
  "compilerOptions": {
    "strict": true,
    "target": "ES2015",
    "module": "ESNext",
    "moduleResolution": "node",
    "jsx": "react-jsx",
    "paths": {
      "@/*": ["./src/*"]
    },
    "types": ["@tarojs/taro"]
  }
}

四、核心概念

4.1 页面生命周期(Taro)

生命周期

触发时机

常见用途

componentDidShow

页面显示/切入前台

刷新数据、更新状态

componentDidHide

页面隐藏/切入后台

暂停任务、保存状态

componentDidMount

页面首次渲染完成

初始化数据、发起请求

componentWillUnmount

页面卸载

清除定时器、取消订阅

onReady

页面初次渲染完成

获取节点信息

onPullDownRefresh

用户下拉

刷新数据

onReachBottom

页面滚动到底部

加载更多(分页)

onShareAppMessage

用户点击分享

自定义分享内容

onPageScroll

页面滚动

滚动监听(如吸顶效果)

4.2 组件生命周期

组件生命周期与页面类似但不完全相同:

import { Component } from '@tarojs/taro'

class MyComp extends Component {
  // 组件实例化(类似 constructor)
  componentDidMount() {
    // 可以 setState,只执行一次
  }

  // 组件更新
  componentDidUpdate(prevProps) {
    // props 变化时触发
  }

  // 组件卸载
  componentWillUnmount() {
    // 清理工作
  }

  // 对应小程序 ready 生命周期
  ready() {
    // 组件布局完成,可获取节点
  }
}

4.3 路由与导航

API

Taro 等价方法

说明

wx.navigateTo

Taro.navigateTo

打开新页面(保留当前页,最多 10 层)

wx.redirectTo

Taro.redirectTo

关闭当前页,打开新页面(不可返回)

wx.switchTab

Taro.switchTab

跳转到 tabBar 页面(关闭所有非 tabBar 页面)

wx.navigateBack

Taro.navigateBack

返回上一页(delta 指定返回层数)

wx.reLaunch

Taro.reLaunch

关闭所有页面,打开新页面

import Taro from '@tarojs/taro'

// 基本跳转
Taro.navigateTo({ url: '/pages/detail/index?id=123' })

// 带参数跳转
Taro.navigateTo({
  url: `/pages/detail/index?id=${item.id}&name=${item.name}`
})

// 目标页面接收参数
import { useRouter } from '@tarojs/taro'
const router = useRouter()
const { id, name } = router.params

4.4 WXML/WXSS 基础

虽然使用跨端框架,但了解原生基础有助于理解编译产物和调试:

  • WXML:类似 HTML 的标记语言,支持数据绑定 {{ }}、条件渲染 wx:if、列表渲染 wx:for
  • WXSS:类似 CSS,支持大部分 CSS 属性,新增 rpx 单位(750rpx = 屏幕宽度)
  • rpx 响应式单位:1rpx = 屏幕宽度/750,在不同设备上自动缩放

五、组件化开发

5.1 Taro 自定义组件

// components/UserCard/index.tsx
import { Component } from '@tarojs/taro'
import { View, Text, Image } from '@tarojs/components'

interface UserCardProps {
  name: string
  avatar: string
  onTap?: () => void
}

export default class UserCard extends Component<UserCardProps> {
  static defaultProps = {
    name: '',
    avatar: ''
  }

  render() {
    const { name, avatar, onTap } = this.props
    return (
      <View className="user-card" onClick={onTap}>
        <Image src={avatar} className="avatar" />
        <Text>{name}</Text>
      </View>
    )
  }
}

5.2 组件通信方式

方式

方向

适用场景

示例

Props

父 → 子

父组件向子组件传递数据

普通数据传递

事件回调

子 → 父

子组件通知父组件

onChange、onTap 回调

Taro.eventCenter

任意组件

跨组件/跨页面通信

全局事件总线

状态管理

全局

复杂应用的状态共享

Redux / Vuex / Pinia

Context/Provide

祖先 → 后代

深层嵌套的透传

主题、语言、用户信息

5.3 组件配置

每个组件可以有自己的配置文件,设置样式隔离等选项:

// components/UserCard/index.config.ts
export default {
  component: true,
  // 样式隔离:isolated(完全隔离)/ apply-shared(页面影响组件)/ shared(互相影响)
  styleIsolation: 'isolated',
}

六、常用 UI 组件库

6.1 组件库对比

组件库

框架

出品方

适用框架

特点

NutUI

Vue 3

京东

Taro(Vue)/ uni-app

电商场景组件丰富,设计精美

TDesign

React / Vue

腾讯

Taro

企业级设计语言,组件全面

Vant Weapp

原生

有赞

原生 / Taro

社区最活跃的小程序组件库

uView

Vue 2/3

社区

uni-app

uni-app 生态最丰富的组件库

6.2 NutUI 快速上手(Taro + Vue)

npm install @nutui/nutui-taro
// app.ts — 按需引入
import { createApp } from 'vue'
import { Button, Cell, Icon } from '@nutui/nutui-taro'
import '@nutui/nutui-taro/dist/style.css'

const app = createApp(App)
app.use(Button).use(Cell).use(Icon)

七、状态管理

7.1 Taro(React)— Zustand 轻量方案

// store/useUserStore.ts
import { create } from 'zustand'

interface UserStore {
  userInfo: UserInfo | null
  isLogin: boolean
  login: () => Promise<void>
  logout: () => void
}

export const useUserStore = create<UserStore>((set) => ({
  userInfo: null,
  isLogin: false,
  login: async () => {
    const res = await Taro.login()
    set({ userInfo: res.data, isLogin: true })
  },
  logout: () => set({ userInfo: null, isLogin: false }),
}))

7.2 uni-app — Pinia(Vue 3)

// store/user.ts
import { defineStore } from 'pinia'

export const useUserStore = defineStore('user', {
  state: () => ({
    userInfo: null as UserInfo | null,
    token: ''
  }),
  getters: {
    isLogin: (state) => !!state.token
  },
  actions: {
    async login() {
      const res = await uni.login()
      this.token = res.token
    },
    logout() {
      this.token = ''
      this.userInfo = null
    }
  }
})

八、API 调用与网络请求

8.1 请求封装

// utils/request.ts
import Taro from '@tarojs/taro'

const BASE_URL = 'https://api.example.com'

const request = async <T>(options: Taro.request.Option): Promise<T> => {
  const { url, data, method = 'GET', header = {} } = options

  const token = Taro.getStorageSync('token')
  if (token) {
    header['Authorization'] = `Bearer ${token}`
  }

  try {
    const res = await Taro.request({
      url: `${BASE_URL}${url}`,
      data,
      method,
      header: { 'Content-Type': 'application/json', ...header }
    })

    if (res.statusCode === 200) {
      return res.data as T
    }

    if (res.statusCode === 401) {
      Taro.removeStorageSync('token')
      Taro.reLaunch({ url: '/pages/login/index' })
    }
    throw new Error(`请求失败: ${res.statusCode}`)
  } catch (err) {
    Taro.showToast({ title: '网络异常', icon: 'none' })
    throw err
  }
}

export const get = <T>(url: string, data?: any) =>
  request<T>({ url, data, method: 'GET' })
export const post = <T>(url: string, data?: any) =>
  request<T>({ url, data, method: 'POST' })

8.2 微信登录流程

微信小程序登录流程(关键):

  1. 调用 wx.login() 获取临时 code
  2. 将 code 发送到后端服务器
  3. 后端调用 code2Session 获取 openid 和 session_key
  4. 后端生成自定义 token 返回给前端
  5. 前端存储 token,后续请求携带 token 鉴权

8.3 常用微信 API 速查

分类

API

说明

用户信息

wx.getUserProfile

获取用户头像、昵称(需用户主动触发)

定位

wx.getLocation

获取用户位置(需授权)

支付

wx.requestPayment

调起微信支付

存储

wx.setStorageSync

本地缓存(上限 10MB)

图片

wx.chooseImage

选择图片(拍照或相册)

扫码

wx.scanCode

扫描二维码/条码

分享

wx.showShareMenu

设置分享功能

订阅消息

wx.requestSubscribeMessage

请求订阅消息授权


九、分包与性能优化

9.1 分包策略

小程序总包限制 20MB,主包限制 2MB。合理使用分包可以解决包体积问题:

// app.config.ts
export default {
  pages: [
    'pages/index/index',
    'pages/login/index'
  ],
  subPackages: [
    {
      root: 'packageA',
      pages: [
        'pages/detail/index',
        'pages/order/index'
      ]
    },
    {
      root: 'packageB',
      pages: [
        'pages/profile/index',
        'pages/settings/index'
      ]
    }
  ],
  preloadRule: {
    'pages/index/index': {
      network: 'all',
      packages: ['packageA']
    }
  }
}

9.2 性能优化清单

性能优化要点:

  • 减少 setData 调用频率:合并多次 setData 为一次,避免一次性传递大量数据
  • 图片优化:使用 WebP 格式,懒加载图片,合理设置图片尺寸
  • 长列表优化:使用虚拟列表(recycle-view / VirtualList)渲染大数据列表
  • 按需加载:路由懒加载、组件动态引入、分包独立加载
  • 缓存策略:本地缓存不变数据,减少网络请求
  • 避免频繁触发:对 scroll、resize 等事件使用节流/防抖
  • 骨架屏:首屏加载时使用骨架屏提升感知性能

9.3 常见性能问题与解决

问题

原因

影响

解决方案

首屏白屏时间长

主包过大 / 请求阻塞

用户体验差

分包 + 预加载 + 骨架屏 + 接口并行

页面滚动卡顿

setData 频繁 / 数据量大

交互不流畅

diff 数据后增量更新,使用 WXS 响应事件

内存占用高

图片未释放 / 长列表

小程序崩溃

图片懒加载 + 虚拟列表 + 及时清理


十、云开发

10.1 微信云开发简介

微信云开发是微信官方提供的 Serverless 解决方案,无需搭建服务器即可使用云端能力:

  • 云数据库:MongoDB 类型的 JSON 数据库,支持聚合查询
  • 云存储:文件存储,自带 CDN 加速
  • 云函数:运行在 Node.js 环境中的服务端代码
  • 云调用:云函数内直接调用微信开放接口

10.2 云开发初始化

// app.ts
import Taro from '@tarojs/taro'

componentDidMount() {
  if (Taro.cloud) {
    Taro.cloud.init({
      env: 'your-env-id',
      traceUser: true
    })
  }
}

10.3 云函数示例

// cloud/functions/getUser/index.js
const cloud = require('wx-server-sdk')
cloud.init({ env: cloud.DYNAMIC_CURRENT_ENV })

exports.main = async (event, context) => {
  const { OPENID } = cloud.getWXContext()
  const db = cloud.database()

  const user = await db.collection('users')
    .where({ _openid: OPENID })
    .get()

  return { code: 0, data: user.data[0] || null }
}

注意: 云开发在某些跨端框架中(如 Taro H5 端)不可用,仅限小程序端运行。建议通过条件编译处理平台差异。


十一、调试与发布

11.1 开发调试

  • 微信开发者工具:编译预览、模拟器、真机调试、性能面板
  • Taro CLI 调试npm run dev:weapp 实时编译,开发者工具自动刷新
  • uni-app 调试npm run dev:mp-weixin,同样支持热更新
  • vConsole:真机调试时可在小程序内打开调试面板(开发版/体验版自动开启)

11.2 版本管理

版本类型

人数限制

说明

开发版

开发者本人

上传后自动成为开发版,仅上传者可见

体验版

最多 20 人

在后台手动指定某个版本为体验版

审核版

微信审核人员

提交审核后等待微信审核(1-7 个工作日)

线上版

所有用户

审核通过后发布的全量版本

11.3 发布流程

  1. 在 IDE 中点击"上传",填写版本号和项目备注
  2. 登录微信公众平台 → 版本管理
  3. 选择开发版 → 设为体验版(可选,供测试验证)
  4. 提交审核 → 填写审核信息(功能截图、测试账号等)
  5. 等待审核通过 → 点击"发布"上线

发布建议:

  • 首次提交审核需要提供测试账号
  • 涉及社交、UGC 内容需要对应类目的资质
  • 建议设置分阶段发布(5% → 20% → 50% → 100%),降低线上风险
  • 保留上一版本的代码备份,以便紧急回滚

十二、最佳实践总结

12.1 开发规范

  • 统一使用 TypeScript,享受类型安全
  • API 请求统一封装,集中管理错误处理和 token 刷新
  • 组件按功能拆分,保持单一职责
  • 合理使用分包,主包只保留核心页面
  • 使用条件编译处理跨平台差异(#ifdef WEAPP / #ifndef WEAPP

12.2 安全注意事项

  • AppSecret 只能存放在服务端,禁止在前端代码中出现
  • 敏感数据使用微信加密数据解密
  • 接口请求使用 HTTPS,验证服务器证书
  • openid 和 session_key 不要暴露在 URL 参数中

12.3 常用资源链接

  • Taro 官方文档:https://taro-docs.jd.com
  • uni-app 官方文档:https://uniapp.dcloud.net.cn
  • 微信小程序官方文档:https://developers.weixin.qq.com/miniprogram/dev
  • 微信公众平台:https://mp.weixin.qq.com
  • NutUI 文档:https://nutui.jd.com
  • TDesign 小程序:https://tdesign.tencent.com/miniprogram