未验证 提交 bc403af0 编写于 作者: J Jens Meindertsma 提交者: GitHub

Update with-msw example (#20335)

* Update with-msw example

* Update README

* Update examples/with-msw/README.md

* lint fix
Co-authored-by: NLuis Alvarez D <luis@vercel.com>
Co-authored-by: Nkodiakhq[bot] <49736102+kodiakhq[bot]@users.noreply.github.com>
上级 d434f1dd
NEXT_PUBLIC_API_MOCKING=enabled
NEXT_PUBLIC_API_MOCKING=enabled
......@@ -8,7 +8,7 @@ In this example we integrate Mock Service Worker with Next by following the next
1. Setup a [Service Worker instance](./mocks/browser.js) that would intercept all runtime client-side requests via `setupWorker` function.
1. Setup a ["server" instance](./mocks/server.js) to intercept any server/build time requests (e.g. the one happening in `getServerSideProps`) via `setupServer` function.
Mocking is enabled using the `NEXT_PUBLIC_API_MOCKING` environment variable, which for the sake of the example is saved inside `.env` instead of `.env.development`. In a real app you should move the variable to `.env.development` because mocking should only be done for development.
Mocking is enabled using the `NEXT_PUBLIC_API_MOCKING` environment variable. By default, mocking is enabled for both development and production. This allows you to have working preview deployments before implementing an actual API. To disable MSW for a specific environment, change the environment variable value in the file corresponding to the environment from `enabled` to `disabled`.
## Deploy your own
......
......@@ -8,9 +8,9 @@
},
"license": "MIT",
"dependencies": {
"msw": "^0.21.2",
"msw": "^0.24.2",
"next": "latest",
"react": "^16.13.1",
"react-dom": "^16.13.1"
"react": "^17.0.1",
"react-dom": "^17.0.1"
}
}
// Enable API mocking in all environments except production.
// This is recommended for real-world apps.
if (process.env.NODE_ENV !== 'production') {
if (process.env.NEXT_PUBLIC_API_MOCKING === 'enabled') {
require('../mocks')
}
......
import { useState } from 'react'
export default function Home({ book, inProduction }) {
export default function Home({ book }) {
const [reviews, setReviews] = useState(null)
const handleGetReviews = () => {
......@@ -10,18 +10,6 @@ export default function Home({ book, inProduction }) {
.then(setReviews)
}
if (inProduction) {
return (
<div>
<p>
This example does not work in production, as MSW is not intended for
use in production. In a real-world app, your request will hit the
actual backend instead.
</p>
</div>
)
}
return (
<div>
<img src={book.imageUrl} alt={book.title} width="250" />
......@@ -44,21 +32,12 @@ export default function Home({ book, inProduction }) {
export async function getServerSideProps() {
// Server-side requests are mocked by `mocks/server.js`.
// In a real-world app this request would hit the actual backend.
try {
const res = await fetch('https://my.backend/book')
const book = await res.json()
const res = await fetch('https://my.backend/book')
const book = await res.json()
return {
props: {
book,
},
}
} catch (error) {
return {
props: {
inProduction: true,
},
}
return {
props: {
book,
},
}
}
......@@ -7,7 +7,7 @@
/* eslint-disable */
/* tslint:disable */
const INTEGRITY_CHECKSUM = 'd1e0e502f550d40a34bee90822e4bf98'
const INTEGRITY_CHECKSUM = '65d33ca82955e1c5928aed19d1bdf3f9'
const bypassHeaderName = 'x-msw-bypass'
let clients = {}
......@@ -74,11 +74,22 @@ self.addEventListener('message', async function (event) {
}
})
self.addEventListener('fetch', async function (event) {
self.addEventListener('fetch', function (event) {
const { clientId, request } = event
const requestClone = request.clone()
const getOriginalResponse = () => fetch(requestClone)
// Bypass navigation requests.
if (request.mode === 'navigate') {
return
}
// Bypass mocking if the current client isn't present in the internal clients map
// (i.e. has the mocking disabled).
if (!clients[clientId]) {
return
}
// Opening the DevTools triggers the "only-if-cached" request
// that cannot be handled by the worker. Bypass such requests.
if (request.cache === 'only-if-cached' && request.mode !== 'same-origin') {
......@@ -89,20 +100,15 @@ self.addEventListener('fetch', async function (event) {
new Promise(async (resolve, reject) => {
const client = await event.target.clients.get(clientId)
if (
// Bypass mocking when no clients active
!client ||
// Bypass mocking if the current client has mocking disabled
!clients[clientId] ||
// Bypass mocking for navigation requests
request.mode === 'navigate'
) {
// Bypass mocking when the request client is not active.
if (!client) {
return resolve(getOriginalResponse())
}
// Bypass requests with the explicit bypass header
if (requestClone.headers.get(bypassHeaderName) === 'true') {
const modifiedHeaders = serializeHeaders(requestClone.headers)
// Remove the bypass header to comply with the CORS preflight check
delete modifiedHeaders[bypassHeaderName]
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册