连接世界:网络请求 `wx.request`
连接世界:网络请求 wx.request
所属专栏:《微信小程序-实战笔记30讲》
作者:码力无边
前言
到目前为止,我们应用中的所有数据——无论是用户信息、商品列表还是配置项——都还是“写死”在前端代码里的。这在真实世界中显然是行不通的。一个真正有生命力的应用,它的数据应该是动态的、来自远方服务器的。
为了获取这些数据,小程序需要具备与服务器通信的能力。这个能力的核心,就是我们今天要学习的网络请求API——wx.request
。
wx.request
就像是小程序伸向互联网的一根“天线”,通过它,我们可以:
- 从服务器**获取(GET)**最新的新闻列表、商品详情。
- 向服务器**提交(POST)**用户的注册信息、订单数据。
- **更新(PUT)或删除(DELETE)**服务器上的资源。
掌握wx.request
,意味着你的小程序将不再是一个“单机应用”,而是真正融入了客户端-服务器(Client-Server)架构,拥有了无限扩展的可能性。
一、发起你的第一次网络请求
wx.request
的使用方式非常直观,它接受一个对象作为参数,你可以在这个对象里详细配置这次请求的所有信息。
1. 基本的GET请求
GET请求是最常见的一种请求,通常用于从服务器获取数据。
动手实践 - 获取在线的笑话数据:
很多网站提供了免费的API接口供开发者测试。我们以一个随机笑话接口为例:https://api.vvhan.com/api/joke
在页面的JS文件中:
// pages/network/network.js
Page({data: {joke: '正在加载笑话...'},onLoad: function() {this.getJoke();},getJoke: function() {wx.request({url: 'https://api.vvhan.com/api/joke', // 接口地址method: 'GET', // 请求方法success: (res) => { // 请求成功的回调函数console.log('请求成功,服务器返回:', res);// res.data 中包含了服务器返回的实际数据if (res.statusCode === 200) { // HTTP状态码为200表示成功this.setData({joke: res.data.joke });} else {// 其他状态码,表示可能出现问题this.setData({joke: '获取笑话失败了...'});}},fail: (err) => { // 请求失败的回调函数console.error('请求失败:', err);this.setData({joke: '网络出错了,请稍后再试。'});},complete: () => { // 请求完成的回调函数(无论成功失败都会执行)console.log('请求已完成。');}});}
})
WXML:
<view>{{joke}}</view>
<button bindtap="getJoke">换一个</button>
回调函数解析:
success
: 当服务器成功响应时触发。它的参数res
是一个对象,包含了data
(服务器返回的数据)、statusCode
(HTTP状态码)、header
(响应头)等信息。fail
: 当请求因网络问题或DNS解析失败等原因未能送达服务器时触发。complete
: 类似于try...catch...finally
中的finally
,无论请求是成功还是失败,最后都会执行。通常用于隐藏加载提示(loading)。
2. 发起POST请求
POST请求通常用于向服务器提交数据,比如提交表单、创建新资源等。
与GET请求的主要区别在于,POST请求需要通过data
参数传递要提交的数据,并且可能需要设置header
(请求头)来告诉服务器数据的格式。
示例 - 模拟提交用户反馈:
function submitFeedback(content) {wx.request({url: 'https://your-api.com/feedback',method: 'POST',data: { // 要提交的数据userId: 'user123',feedbackContent: content,timestamp: Date.now()},header: {'content-type': 'application/json' // 默认值,告知服务器我们发送的是JSON格式数据// 'Authorization': 'Bearer YOUR_TOKEN' // 如果需要登录凭证,通常放在这里},success: (res) => {if (res.data.code === 0) {wx.showToast({ title: '提交成功!' });} else {wx.showToast({ title: res.data.message, icon: 'none' });}},fail: (err) => {wx.showToast({ title: '网络错误', icon: 'none' });}})
}
二、跨域与合法域名配置
这是一个非常重要且常见的“坑”!
出于安全考虑,小程序只允许向在后台配置过的“合法域名”发起网络请求。如果你尝试请求一个未配置的域名,开发者工具的控制台会报一个类似这样的错误:
url "https://some-random-api.com" is not in the list of domain names...
如何配置合法域名?
- 登录你的微信小程序后台。
- 进入 开发 -> 开发管理 -> 开发设置。
- 找到“服务器域名”设置项。
- 在
request合法域名
中,点击修改,然后添加你需要请求的域名(例如api.vvhan.com
)。 - 域名必须是HTTPS协议的。
开发阶段小技巧:在微信开发者工具的右上角,“详情” -> “本地设置”中,可以勾选“不校验合法域名、web-view(业务域名)、TLS 版本以及 HTTPS 证书”。这样可以在开发时临时绕过域名校验,方便调试第三方接口。但请务必记住,在发布小程序前,一定要将所有用到的域名都配置到后台,并取消这个勾选!
三、封装你的网络请求模块
在实际项目中,我们会有大量的网络请求。如果每次都写一遍冗长的wx.request
,代码会非常重复,且难以维护。例如,每个请求可能都需要:
- 显示
wx.showLoading
加载提示。 - 在请求头中携带用户的登录凭证(Token)。
- 对返回的数据进行统一的错误处理(如登录失效、服务器错误等)。
因此,将网络请求封装成一个独立的模块是项目开发的最佳实践。
动手实践 - 创建一个简单的request.js
模块:
-
在项目根目录下创建一个
utils
文件夹,在其中新建request.js
文件。// utils/request.js const BASE_URL = 'https://your-api-base-url.com'; // 你的API基础路径const request = (options) => {return new Promise((resolve, reject) => {wx.showLoading({title: '加载中...',mask: true,});wx.request({url: BASE_URL + options.url,method: options.method || 'GET',data: options.data || {},header: {// 在这里可以统一添加认证信息,如Token// 'Authorization': wx.getStorageSync('token') || ''},success: (res) => {// 在这里可以进行统一的业务错误判断if (res.statusCode === 200) {// 假设 code 为 0 是业务成功if (res.data.code === 0) {resolve(res.data.data); // 返回核心数据} else {// 其他业务错误wx.showToast({ title: res.data.message, icon: 'none' });reject(res.data);}} else {// HTTP状态码错误wx.showToast({ title: `请求错误 ${res.statusCode}`, icon: 'none' });reject(res);}},fail: (err) => {wx.showToast({ title: '网络连接失败', icon: 'none' });reject(err);},complete: () => {wx.hideLoading();}});}); };// 导出封装好的request函数 export default request;
这里我们使用了
Promise
,让异步代码可以写得更优雅。 -
在页面中使用封装好的请求函数:
// pages/somepage/somepage.js import request from '../../utils/request';Page({async getProductList() {try {const productList = await request({url: '/products',method: 'GET',data: { page: 1, size: 10 }});console.log(productList);// 更新页面数据} catch (error) {console.error('获取商品列表失败', error);}} })
通过封装,页面中的代码变得极其简洁、清晰,并且所有请求的公共逻辑都集中在一个地方,方便未来统一修改和维护。
结语
今天,我们为小程序成功安装了连接世界的“天线”——wx.request
。我们不仅学会了如何发起GET和POST请求,还理解了合法域名的重要性,并掌握了封装网络请求这一至关重要的工程化技巧。
现在,你的小程序已经可以从服务器获取动态数据,并向服务器提交信息了。但数据获取后,往往需要在本地进行一些临时的“仓储”,比如用户的登录状态、一些不常变化的基础配置等,以避免频繁的网络请求。
下一讲,我们将学习小程序的本地存储 Storage
API,为你的应用打造一个轻便可靠的“本地小仓库”。
我们下篇见!