likes
comments
collection
share

简单说说前端项目中可用的 API Mocking 策略

作者站长头像
站长
· 阅读数 37

在 dev.to 上看到一篇文章《API Mocking Strategies for JavaScript Applications》,介绍前端项目中的 API Mocking 策略,阅读后有些收获,在这里给大家做下简单概述。

传统 Mock 的两个可选方向

网页中一个典型的网页请求是这样的:

简单说说前端项目中可用的 API Mocking 策略

如果要对我们的项目下手进行 Mock,有两个可选的方向。一个是 Mock Request Client(window.fetch 或 window.XMLHttpRequest),一个是 Mock 服务器。

Mock Request Client

对 Mock Request Client 而言,其原理比较简单,类似下面这样:

window.fetch = (init, input) => {
  // Respond with a mocked response
  // any time our code calls "window.fetch".
  return new Response('hello')
}

就是重写了 Fetch API,请求并不会真的发送,浏览器中也不会看到请求发出。效果类似下面这样:

简单说说前端项目中可用的 API Mocking 策略

像下面这些库都是使用的这个策略:

网页端是通过重写 window.fetch/window.XMLHttpRequest,而 Node.js 端则是通过重写 http/https 模块来实现请求拦截 Mock 的。

Mock 服务器

Mock Request Client 的在浏览器上的一个明显弊端,就是其实我们并没有真正调用 Fetch API/XMLHttpRequest API,就直接返回 Mock 结果了。

因此,我们有了一个可选方案,就是去替换请求路径中的 server 部分,变成这样:

简单说说前端项目中可用的 API Mocking 策略

反馈到代码上,我们就要这样写:

const IS_TEST = process.env.NODE_ENV === 'test'

fetch(
  IS_TEST
    // Communicate with a local mock server while testing.
    ? 'http://localhost:3000/api'
    : 'https://api.backend.com'
  )

这就有点类似测试环境服务器了。虽然解决了能走到请求 API、看到请求的问题,这里列举了一些,可以用作这类似用途的库。

但是这需要我们多加一个判断条件,增加了一个 Mock 服务器,多了编写和维护的服务器的运营成本。

因此,选择那种方案,我们要根据实际情况,去做取舍。

如果我们把前端项目中的请求分成:客户端(浏览器)请求和服务端请求。虽然,服务端请求现在还是只能老一套,只能通过重写 http/https 模块来实现请求拦截和 Mock,那么客户端请求因为有了 Service Worker 的介入带来了 Mock 曙光。

客户端请求 Mock 新方式:Service Worker API

Service Worker API 可以实现客户端请求的 Mock 新方式:在能看到网页请求发出的同时(开发者工具中能看到请求地址),还能做请求响应数据的 Mock。

简单点说,就是监听网页中的 fetch 事件。

// main.js

if ('serviceWorker' in navigator) {
  window.addEventListener('load', function() {
    // 注册 Service Worker
    navigator.serviceWorker.register('/service-worker.js')
      .then(function(registration) {
        console.log('Service Worker registered with scope:', registration.scope);
      })
      .catch(function(error) {
        console.log('Service Worker registration failed:', error);
      });
  });
}

// service-worker.js

// 拦截请求(fetch 事件会在网页中每发生一次数据请求时触发)
self.addEventListener('fetch', event => {
  event.respondWith(
    new Response('Hello from the Service Worker!')
  );
});

体实现原理,可以参考这篇文章:《Use Service Workers to manage network requests》

Mock Service Worker(又叫 mwsjs)就是通过 Service Worker API 来做客户端请求 Mock 的(当然服务端还是借助重写 http/https 模块的方式)。

import { setupWorker, rest } from 'msw'

const worker = setupWorker(
  rest.post('/login', async (req, res, ctx) => {
    const { username } = await req.json()

    return res(
      ctx.json({
        username,
        firstName: 'John'
      })
    )
  }),
)

worker.start()

关于 mwsjs 的使用,可以参考我写的文章《mswjs:在浏览器和 Node 环境中轻松做 API Mocking》了解。

感谢你阅读到这里,Happy Coding!

转载自:https://juejin.cn/post/7250318612510195769
评论
请登录