mirror of
https://github.com/zebrajr/react.git
synced 2026-01-15 12:15:22 +00:00
Test the node-register hooks in unit tests (#25132)
This commit is contained in:
committed by
GitHub
parent
3f70e68cea
commit
38c5d8a035
@@ -7,4 +7,4 @@
|
||||
* @flow
|
||||
*/
|
||||
|
||||
export * from './src/ReactFlightWebpackNodeRegister';
|
||||
module.exports = require('./src/ReactFlightWebpackNodeRegister');
|
||||
|
||||
@@ -35,6 +35,7 @@
|
||||
"./writer.browser.server": "./writer.browser.server.js",
|
||||
"./node-loader": "./esm/react-server-dom-webpack-node-loader.js",
|
||||
"./node-register": "./node-register.js",
|
||||
"./src/*": "./src/*",
|
||||
"./package.json": "./package.json"
|
||||
},
|
||||
"main": "index.js",
|
||||
|
||||
@@ -57,7 +57,7 @@ module.exports = function register() {
|
||||
},
|
||||
};
|
||||
|
||||
(require: any).extensions['.client.js'] = function(module, path) {
|
||||
Module._extensions['.client.js'] = function(module, path) {
|
||||
const moduleId = url.pathToFileURL(path).href;
|
||||
const moduleReference: {[string]: any} = {
|
||||
$$typeof: MODULE_REFERENCE,
|
||||
|
||||
@@ -17,14 +17,9 @@ global.TextDecoder = require('util').TextDecoder;
|
||||
// TODO: we can replace this with FlightServer.act().
|
||||
global.setImmediate = cb => cb();
|
||||
|
||||
let webpackModuleIdx = 0;
|
||||
let webpackModules = {};
|
||||
let webpackMap = {};
|
||||
global.__webpack_require__ = function(id) {
|
||||
return webpackModules[id];
|
||||
};
|
||||
|
||||
let act;
|
||||
let clientExports;
|
||||
let webpackMap;
|
||||
let Stream;
|
||||
let React;
|
||||
let ReactDOMClient;
|
||||
@@ -35,15 +30,17 @@ let Suspense;
|
||||
describe('ReactFlightDOM', () => {
|
||||
beforeEach(() => {
|
||||
jest.resetModules();
|
||||
webpackModules = {};
|
||||
webpackMap = {};
|
||||
act = require('jest-react').act;
|
||||
const WebpackMock = require('./utils/WebpackMock');
|
||||
clientExports = WebpackMock.clientExports;
|
||||
webpackMap = WebpackMock.webpackMap;
|
||||
|
||||
Stream = require('stream');
|
||||
React = require('react');
|
||||
Suspense = React.Suspense;
|
||||
ReactDOMClient = require('react-dom/client');
|
||||
ReactServerDOMWriter = require('react-server-dom-webpack/writer.node.server');
|
||||
ReactServerDOMReader = require('react-server-dom-webpack');
|
||||
Suspense = React.Suspense;
|
||||
});
|
||||
|
||||
function getTestStream() {
|
||||
@@ -64,22 +61,6 @@ describe('ReactFlightDOM', () => {
|
||||
};
|
||||
}
|
||||
|
||||
function moduleReference(moduleExport) {
|
||||
const idx = webpackModuleIdx++;
|
||||
webpackModules[idx] = {
|
||||
d: moduleExport,
|
||||
};
|
||||
webpackMap['path/' + idx] = {
|
||||
default: {
|
||||
id: '' + idx,
|
||||
chunks: [],
|
||||
name: 'd',
|
||||
},
|
||||
};
|
||||
const MODULE_TAG = Symbol.for('react.module.reference');
|
||||
return {$$typeof: MODULE_TAG, filepath: 'path/' + idx, name: 'default'};
|
||||
}
|
||||
|
||||
async function waitForSuspense(fn) {
|
||||
while (true) {
|
||||
try {
|
||||
@@ -345,7 +326,7 @@ describe('ReactFlightDOM', () => {
|
||||
return <div>{games}</div>;
|
||||
}
|
||||
|
||||
const MyErrorBoundaryClient = moduleReference(MyErrorBoundary);
|
||||
const MyErrorBoundaryClient = clientExports(MyErrorBoundary);
|
||||
|
||||
function ProfileContent() {
|
||||
return (
|
||||
@@ -470,7 +451,7 @@ describe('ReactFlightDOM', () => {
|
||||
return <input />;
|
||||
}
|
||||
|
||||
const InputClient = moduleReference(Input);
|
||||
const InputClient = clientExports(Input);
|
||||
|
||||
// Server
|
||||
|
||||
|
||||
@@ -14,13 +14,9 @@ global.ReadableStream = require('web-streams-polyfill/ponyfill/es6').ReadableStr
|
||||
global.TextEncoder = require('util').TextEncoder;
|
||||
global.TextDecoder = require('util').TextDecoder;
|
||||
|
||||
let webpackModuleIdx = 0;
|
||||
let webpackModules = {};
|
||||
let webpackMap = {};
|
||||
global.__webpack_require__ = function(id) {
|
||||
return webpackModules[id];
|
||||
};
|
||||
|
||||
let clientExports;
|
||||
let webpackMap;
|
||||
let webpackModules;
|
||||
let act;
|
||||
let React;
|
||||
let ReactDOMClient;
|
||||
@@ -32,9 +28,11 @@ let Suspense;
|
||||
describe('ReactFlightDOMBrowser', () => {
|
||||
beforeEach(() => {
|
||||
jest.resetModules();
|
||||
webpackModules = {};
|
||||
webpackMap = {};
|
||||
act = require('jest-react').act;
|
||||
const WebpackMock = require('./utils/WebpackMock');
|
||||
clientExports = WebpackMock.clientExports;
|
||||
webpackMap = WebpackMock.webpackMap;
|
||||
webpackModules = WebpackMock.webpackModules;
|
||||
React = require('react');
|
||||
ReactDOMClient = require('react-dom/client');
|
||||
ReactDOMServer = require('react-dom/server.browser');
|
||||
@@ -43,22 +41,6 @@ describe('ReactFlightDOMBrowser', () => {
|
||||
Suspense = React.Suspense;
|
||||
});
|
||||
|
||||
function moduleReference(moduleExport) {
|
||||
const idx = webpackModuleIdx++;
|
||||
webpackModules[idx] = {
|
||||
d: moduleExport,
|
||||
};
|
||||
webpackMap['path/' + idx] = {
|
||||
default: {
|
||||
id: '' + idx,
|
||||
chunks: [],
|
||||
name: 'd',
|
||||
},
|
||||
};
|
||||
const MODULE_TAG = Symbol.for('react.module.reference');
|
||||
return {$$typeof: MODULE_TAG, filepath: 'path/' + idx, name: 'default'};
|
||||
}
|
||||
|
||||
async function waitForSuspense(fn) {
|
||||
while (true) {
|
||||
try {
|
||||
@@ -249,7 +231,7 @@ describe('ReactFlightDOMBrowser', () => {
|
||||
return <div>{games}</div>;
|
||||
}
|
||||
|
||||
const MyErrorBoundaryClient = moduleReference(MyErrorBoundary);
|
||||
const MyErrorBoundaryClient = clientExports(MyErrorBoundary);
|
||||
|
||||
function ProfileContent() {
|
||||
return (
|
||||
@@ -478,19 +460,19 @@ describe('ReactFlightDOMBrowser', () => {
|
||||
}
|
||||
// The Client build may not have the same IDs as the Server bundles for the same
|
||||
// component.
|
||||
const ClientComponentOnTheClient = moduleReference(ClientComponent);
|
||||
const ClientComponentOnTheServer = moduleReference(ClientComponent);
|
||||
const ClientComponentOnTheClient = clientExports(ClientComponent);
|
||||
const ClientComponentOnTheServer = clientExports(ClientComponent);
|
||||
|
||||
// In the SSR bundle this module won't exist. We simulate this by deleting it.
|
||||
const clientId = webpackMap[ClientComponentOnTheClient.filepath].default.id;
|
||||
const clientId = webpackMap[ClientComponentOnTheClient.filepath]['*'].id;
|
||||
delete webpackModules[clientId];
|
||||
|
||||
// Instead, we have to provide a translation from the client meta data to the SSR
|
||||
// meta data.
|
||||
const ssrMetaData = webpackMap[ClientComponentOnTheServer.filepath].default;
|
||||
const ssrMetaData = webpackMap[ClientComponentOnTheServer.filepath]['*'];
|
||||
const translationMap = {
|
||||
[clientId]: {
|
||||
d: ssrMetaData,
|
||||
'*': ssrMetaData,
|
||||
},
|
||||
};
|
||||
|
||||
|
||||
67
packages/react-server-dom-webpack/src/__tests__/utils/WebpackMock.js
vendored
Normal file
67
packages/react-server-dom-webpack/src/__tests__/utils/WebpackMock.js
vendored
Normal file
@@ -0,0 +1,67 @@
|
||||
/**
|
||||
* Copyright (c) Facebook, Inc. and its affiliates.
|
||||
*
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*/
|
||||
|
||||
'use strict';
|
||||
|
||||
const url = require('url');
|
||||
const Module = require('module');
|
||||
|
||||
let webpackModuleIdx = 0;
|
||||
const webpackModules = {};
|
||||
const webpackMap = {};
|
||||
global.__webpack_require__ = function(id) {
|
||||
return webpackModules[id];
|
||||
};
|
||||
|
||||
const previousLoader = Module._extensions['.client.js'];
|
||||
|
||||
const register = require('react-server-dom-webpack/node-register');
|
||||
// Register node loader
|
||||
register();
|
||||
|
||||
const nodeLoader = Module._extensions['.client.js'];
|
||||
|
||||
if (previousLoader === nodeLoader) {
|
||||
throw new Error(
|
||||
'Expected the Node loader to register the .client.js extension',
|
||||
);
|
||||
}
|
||||
|
||||
Module._extensions['.client.js'] = previousLoader;
|
||||
|
||||
exports.webpackMap = webpackMap;
|
||||
exports.webpackModules = webpackModules;
|
||||
|
||||
exports.clientExports = function clientExports(moduleExports) {
|
||||
const idx = '' + webpackModuleIdx++;
|
||||
webpackModules[idx] = moduleExports;
|
||||
const path = url.pathToFileURL(idx).href;
|
||||
webpackMap[path] = {
|
||||
'': {
|
||||
id: idx,
|
||||
chunks: [],
|
||||
name: '',
|
||||
},
|
||||
'*': {
|
||||
id: idx,
|
||||
chunks: [],
|
||||
name: '*',
|
||||
},
|
||||
};
|
||||
for (const name in moduleExports) {
|
||||
webpackMap[path] = {
|
||||
[name]: {
|
||||
id: idx,
|
||||
chunks: [],
|
||||
name: name,
|
||||
},
|
||||
};
|
||||
}
|
||||
const mod = {exports: {}};
|
||||
nodeLoader(mod, idx);
|
||||
return mod.exports;
|
||||
};
|
||||
@@ -408,7 +408,8 @@ const bundles = [
|
||||
{
|
||||
bundleTypes: [NODE_ES2015],
|
||||
moduleType: RENDERER_UTILS,
|
||||
entry: 'react-server-dom-webpack/node-register',
|
||||
entry: 'react-server-dom-webpack/src/ReactFlightWebpackNodeRegister.js',
|
||||
name: 'react-server-dom-webpack-node-register',
|
||||
global: 'ReactFlightWebpackNodeRegister',
|
||||
minifyWithProdErrorCodes: false,
|
||||
wrapWithModuleBoundaries: false,
|
||||
|
||||
Reference in New Issue
Block a user