123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842 |
- 'use strict';
- if (process.env.NODE_ENV !== "production") {
- (function() {
- 'use strict';
- function ReactFreshBabelPlugin (babel) {
- var opts = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
- if (typeof babel.env === 'function') {
-
- var env = babel.env();
- if (env !== 'development' && !opts.skipEnvCheck) {
- throw new Error('React Refresh Babel transform should only be enabled in development environment. ' + 'Instead, the environment is: "' + env + '". If you want to override this check, pass {skipEnvCheck: true} as plugin options.');
- }
- }
- var t = babel.types;
- var refreshReg = t.identifier(opts.refreshReg || '$RefreshReg$');
- var refreshSig = t.identifier(opts.refreshSig || '$RefreshSig$');
- var registrationsByProgramPath = new Map();
- function createRegistration(programPath, persistentID) {
- var handle = programPath.scope.generateUidIdentifier('c');
- if (!registrationsByProgramPath.has(programPath)) {
- registrationsByProgramPath.set(programPath, []);
- }
- var registrations = registrationsByProgramPath.get(programPath);
- registrations.push({
- handle: handle,
- persistentID: persistentID
- });
- return handle;
- }
- function isComponentishName(name) {
- return typeof name === 'string' && name[0] >= 'A' && name[0] <= 'Z';
- }
- function findInnerComponents(inferredName, path, callback) {
- var node = path.node;
- switch (node.type) {
- case 'Identifier':
- {
- if (!isComponentishName(node.name)) {
- return false;
- }
-
- callback(inferredName, node, null);
- return true;
- }
- case 'FunctionDeclaration':
- {
-
-
-
- callback(inferredName, node.id, null);
- return true;
- }
- case 'ArrowFunctionExpression':
- {
- if (node.body.type === 'ArrowFunctionExpression') {
- return false;
- }
-
- callback(inferredName, node, path);
- return true;
- }
- case 'FunctionExpression':
- {
-
-
-
- callback(inferredName, node, path);
- return true;
- }
- case 'CallExpression':
- {
- var argsPath = path.get('arguments');
- if (argsPath === undefined || argsPath.length === 0) {
- return false;
- }
- var calleePath = path.get('callee');
- switch (calleePath.node.type) {
- case 'MemberExpression':
- case 'Identifier':
- {
- var calleeSource = calleePath.getSource();
- var firstArgPath = argsPath[0];
- var innerName = inferredName + '$' + calleeSource;
- var foundInside = findInnerComponents(innerName, firstArgPath, callback);
- if (!foundInside) {
- return false;
- }
-
- callback(inferredName, node, path);
- return true;
- }
- default:
- {
- return false;
- }
- }
- }
- case 'VariableDeclarator':
- {
- var init = node.init;
- if (init === null) {
- return false;
- }
- var name = node.id.name;
- if (!isComponentishName(name)) {
- return false;
- }
- switch (init.type) {
- case 'ArrowFunctionExpression':
- case 'FunctionExpression':
-
- break;
- case 'CallExpression':
- {
-
-
- var callee = init.callee;
- var calleeType = callee.type;
- if (calleeType === 'Import') {
- return false;
- } else if (calleeType === 'Identifier') {
- if (callee.name.indexOf('require') === 0) {
- return false;
- } else if (callee.name.indexOf('import') === 0) {
- return false;
- }
-
- }
- break;
- }
- case 'TaggedTemplateExpression':
-
- break;
- default:
- return false;
- }
- var initPath = path.get('init');
- var _foundInside = findInnerComponents(inferredName, initPath, callback);
- if (_foundInside) {
- return true;
- }
- var binding = path.scope.getBinding(name);
- if (binding === undefined) {
- return;
- }
- var isLikelyUsedAsType = false;
- var referencePaths = binding.referencePaths;
- for (var i = 0; i < referencePaths.length; i++) {
- var ref = referencePaths[i];
- if (ref.node && ref.node.type !== 'JSXIdentifier' && ref.node.type !== 'Identifier') {
- continue;
- }
- var refParent = ref.parent;
- if (refParent.type === 'JSXOpeningElement') {
- isLikelyUsedAsType = true;
- } else if (refParent.type === 'CallExpression') {
- var _callee = refParent.callee;
- var fnName = void 0;
- switch (_callee.type) {
- case 'Identifier':
- fnName = _callee.name;
- break;
- case 'MemberExpression':
- fnName = _callee.property.name;
- break;
- }
- switch (fnName) {
- case 'createElement':
- case 'jsx':
- case 'jsxDEV':
- case 'jsxs':
- isLikelyUsedAsType = true;
- break;
- }
- }
- if (isLikelyUsedAsType) {
-
- callback(inferredName, init, initPath);
- return true;
- }
- }
- }
- }
- return false;
- }
- function isBuiltinHook(hookName) {
- switch (hookName) {
- case 'useState':
- case 'React.useState':
- case 'useReducer':
- case 'React.useReducer':
- case 'useEffect':
- case 'React.useEffect':
- case 'useLayoutEffect':
- case 'React.useLayoutEffect':
- case 'useMemo':
- case 'React.useMemo':
- case 'useCallback':
- case 'React.useCallback':
- case 'useRef':
- case 'React.useRef':
- case 'useContext':
- case 'React.useContext':
- case 'useImperativeHandle':
- case 'React.useImperativeHandle':
- case 'useDebugValue':
- case 'React.useDebugValue':
- return true;
- default:
- return false;
- }
- }
- function getHookCallsSignature(functionNode) {
- var fnHookCalls = hookCalls.get(functionNode);
- if (fnHookCalls === undefined) {
- return null;
- }
- return {
- key: fnHookCalls.map(function (call) {
- return call.name + '{' + call.key + '}';
- }).join('\n'),
- customHooks: fnHookCalls.filter(function (call) {
- return !isBuiltinHook(call.name);
- }).map(function (call) {
- return t.cloneDeep(call.callee);
- })
- };
- }
- var hasForceResetCommentByFile = new WeakMap();
- function hasForceResetComment(path) {
- var file = path.hub.file;
- var hasForceReset = hasForceResetCommentByFile.get(file);
- if (hasForceReset !== undefined) {
- return hasForceReset;
- }
- hasForceReset = false;
- var comments = file.ast.comments;
- for (var i = 0; i < comments.length; i++) {
- var cmt = comments[i];
- if (cmt.value.indexOf('@refresh reset') !== -1) {
- hasForceReset = true;
- break;
- }
- }
- hasForceResetCommentByFile.set(file, hasForceReset);
- return hasForceReset;
- }
- function createArgumentsForSignature(node, signature, scope) {
- var key = signature.key,
- customHooks = signature.customHooks;
- var forceReset = hasForceResetComment(scope.path);
- var customHooksInScope = [];
- customHooks.forEach(function (callee) {
-
- var bindingName;
- switch (callee.type) {
- case 'MemberExpression':
- if (callee.object.type === 'Identifier') {
- bindingName = callee.object.name;
- }
- break;
- case 'Identifier':
- bindingName = callee.name;
- break;
- }
- if (scope.hasBinding(bindingName)) {
- customHooksInScope.push(callee);
- } else {
-
-
- forceReset = true;
- }
- });
- var finalKey = key;
- if (typeof require === 'function' && !opts.emitFullSignatures) {
-
-
-
-
-
- finalKey = require('crypto').createHash('sha1').update(key).digest('base64');
- }
- var args = [node, t.stringLiteral(finalKey)];
- if (forceReset || customHooksInScope.length > 0) {
- args.push(t.booleanLiteral(forceReset));
- }
- if (customHooksInScope.length > 0) {
- args.push(
-
- t.functionExpression(null, [], t.blockStatement([t.returnStatement(t.arrayExpression(customHooksInScope))])));
- }
- return args;
- }
- function findHOCCallPathsAbove(path) {
- var calls = [];
- while (true) {
- if (!path) {
- return calls;
- }
- var parentPath = path.parentPath;
- if (!parentPath) {
- return calls;
- }
- if (
- parentPath.node.type === 'AssignmentExpression' && path.node === parentPath.node.right) {
-
- path = parentPath;
- continue;
- }
- if (
- parentPath.node.type === 'CallExpression' && path.node !== parentPath.node.callee) {
- calls.push(parentPath);
- path = parentPath;
- continue;
- }
- return calls;
- }
- }
- var seenForRegistration = new WeakSet();
- var seenForSignature = new WeakSet();
- var seenForOutro = new WeakSet();
- var hookCalls = new WeakMap();
- var HookCallsVisitor = {
- CallExpression: function (path) {
- var node = path.node;
- var callee = node.callee;
-
- var name = null;
- switch (callee.type) {
- case 'Identifier':
- name = callee.name;
- break;
- case 'MemberExpression':
- name = callee.property.name;
- break;
- }
- if (name === null || !/^use[A-Z]/.test(name)) {
- return;
- }
- var fnScope = path.scope.getFunctionParent();
- if (fnScope === null) {
- return;
- }
- var fnNode = fnScope.block;
- if (!hookCalls.has(fnNode)) {
- hookCalls.set(fnNode, []);
- }
- var hookCallsForFn = hookCalls.get(fnNode);
- var key = '';
- if (path.parent.type === 'VariableDeclarator') {
-
- key = path.parentPath.get('id').getSource();
- }
- var args = path.get('arguments');
- if (name === 'useState' && args.length > 0) {
-
- key += '(' + args[0].getSource() + ')';
- } else if (name === 'useReducer' && args.length > 1) {
-
- key += '(' + args[1].getSource() + ')';
- }
- hookCallsForFn.push({
- callee: path.node.callee,
- name: name,
- key: key
- });
- }
- };
- return {
- visitor: {
- ExportDefaultDeclaration: function (path) {
- var node = path.node;
- var decl = node.declaration;
- var declPath = path.get('declaration');
- if (decl.type !== 'CallExpression') {
-
-
-
-
- return;
- }
-
- if (seenForRegistration.has(node)) {
- return;
- }
- seenForRegistration.add(node);
-
-
-
-
-
-
- var inferredName = '%default%';
- var programPath = path.parentPath;
- findInnerComponents(inferredName, declPath, function (persistentID, targetExpr, targetPath) {
- if (targetPath === null) {
-
-
-
-
- return;
- }
- var handle = createRegistration(programPath, persistentID);
- targetPath.replaceWith(t.assignmentExpression('=', handle, targetExpr));
- });
- },
- FunctionDeclaration: {
- enter: function (path) {
- var node = path.node;
- var programPath;
- var insertAfterPath;
- var modulePrefix = '';
- switch (path.parent.type) {
- case 'Program':
- insertAfterPath = path;
- programPath = path.parentPath;
- break;
- case 'TSModuleBlock':
- insertAfterPath = path;
- programPath = insertAfterPath.parentPath.parentPath;
- break;
- case 'ExportNamedDeclaration':
- insertAfterPath = path.parentPath;
- programPath = insertAfterPath.parentPath;
- break;
- case 'ExportDefaultDeclaration':
- insertAfterPath = path.parentPath;
- programPath = insertAfterPath.parentPath;
- break;
- default:
- return;
- }
-
-
- if (path.parent.type === 'TSModuleBlock' || path.parent.type === 'ExportNamedDeclaration') {
- while (programPath.type !== 'Program') {
- if (programPath.type === 'TSModuleDeclaration') {
- if (programPath.parentPath.type !== 'Program' && programPath.parentPath.type !== 'ExportNamedDeclaration') {
- return;
- }
- modulePrefix = programPath.node.id.name + '$' + modulePrefix;
- }
- programPath = programPath.parentPath;
- }
- }
- var id = node.id;
- if (id === null) {
-
- return;
- }
- var inferredName = id.name;
- if (!isComponentishName(inferredName)) {
- return;
- }
-
- if (seenForRegistration.has(node)) {
- return;
- }
- seenForRegistration.add(node);
- var innerName = modulePrefix + inferredName;
-
- findInnerComponents(innerName, path, function (persistentID, targetExpr) {
- var handle = createRegistration(programPath, persistentID);
- insertAfterPath.insertAfter(t.expressionStatement(t.assignmentExpression('=', handle, targetExpr)));
- });
- },
- exit: function (path) {
- var node = path.node;
- var id = node.id;
- if (id === null) {
- return;
- }
- var signature = getHookCallsSignature(node);
- if (signature === null) {
- return;
- }
-
- if (seenForSignature.has(node)) {
- return;
- }
- seenForSignature.add(node);
- var sigCallID = path.scope.generateUidIdentifier('_s');
- path.scope.parent.push({
- id: sigCallID,
- init: t.callExpression(refreshSig, [])
- });
-
- path.get('body').unshiftContainer('body', t.expressionStatement(t.callExpression(sigCallID, [])));
-
-
-
-
- var insertAfterPath = null;
- path.find(function (p) {
- if (p.parentPath.isBlock()) {
- insertAfterPath = p;
- return true;
- }
- });
- if (insertAfterPath === null) {
- return;
- }
- insertAfterPath.insertAfter(t.expressionStatement(t.callExpression(sigCallID, createArgumentsForSignature(id, signature, insertAfterPath.scope))));
- }
- },
- 'ArrowFunctionExpression|FunctionExpression': {
- exit: function (path) {
- var node = path.node;
- var signature = getHookCallsSignature(node);
- if (signature === null) {
- return;
- }
-
- if (seenForSignature.has(node)) {
- return;
- }
- seenForSignature.add(node);
- var sigCallID = path.scope.generateUidIdentifier('_s');
- path.scope.parent.push({
- id: sigCallID,
- init: t.callExpression(refreshSig, [])
- });
-
- if (path.node.body.type !== 'BlockStatement') {
- path.node.body = t.blockStatement([t.returnStatement(path.node.body)]);
- }
- path.get('body').unshiftContainer('body', t.expressionStatement(t.callExpression(sigCallID, [])));
-
- if (path.parent.type === 'VariableDeclarator') {
- var insertAfterPath = null;
- path.find(function (p) {
- if (p.parentPath.isBlock()) {
- insertAfterPath = p;
- return true;
- }
- });
- if (insertAfterPath === null) {
- return;
- }
-
-
-
-
- insertAfterPath.insertAfter(t.expressionStatement(t.callExpression(sigCallID, createArgumentsForSignature(path.parent.id, signature, insertAfterPath.scope))));
- } else {
-
- var paths = [path].concat(findHOCCallPathsAbove(path));
- paths.forEach(function (p) {
- p.replaceWith(t.callExpression(sigCallID, createArgumentsForSignature(p.node, signature, p.scope)));
- });
- }
- }
- },
- VariableDeclaration: function (path) {
- var node = path.node;
- var programPath;
- var insertAfterPath;
- var modulePrefix = '';
- switch (path.parent.type) {
- case 'Program':
- insertAfterPath = path;
- programPath = path.parentPath;
- break;
- case 'TSModuleBlock':
- insertAfterPath = path;
- programPath = insertAfterPath.parentPath.parentPath;
- break;
- case 'ExportNamedDeclaration':
- insertAfterPath = path.parentPath;
- programPath = insertAfterPath.parentPath;
- break;
- case 'ExportDefaultDeclaration':
- insertAfterPath = path.parentPath;
- programPath = insertAfterPath.parentPath;
- break;
- default:
- return;
- }
-
-
- if (path.parent.type === 'TSModuleBlock' || path.parent.type === 'ExportNamedDeclaration') {
- while (programPath.type !== 'Program') {
- if (programPath.type === 'TSModuleDeclaration') {
- if (programPath.parentPath.type !== 'Program' && programPath.parentPath.type !== 'ExportNamedDeclaration') {
- return;
- }
- modulePrefix = programPath.node.id.name + '$' + modulePrefix;
- }
- programPath = programPath.parentPath;
- }
- }
-
- if (seenForRegistration.has(node)) {
- return;
- }
- seenForRegistration.add(node);
- var declPaths = path.get('declarations');
- if (declPaths.length !== 1) {
- return;
- }
- var declPath = declPaths[0];
- var inferredName = declPath.node.id.name;
- var innerName = modulePrefix + inferredName;
- findInnerComponents(innerName, declPath, function (persistentID, targetExpr, targetPath) {
- if (targetPath === null) {
-
-
-
-
- return;
- }
- var handle = createRegistration(programPath, persistentID);
- if (targetPath.parent.type === 'VariableDeclarator') {
-
-
-
-
-
-
-
-
- insertAfterPath.insertAfter(t.expressionStatement(t.assignmentExpression('=', handle, declPath.node.id)));
- } else {
-
- targetPath.replaceWith(t.assignmentExpression('=', handle, targetExpr));
- }
- });
- },
- Program: {
- enter: function (path) {
-
-
-
-
- path.traverse(HookCallsVisitor);
- },
- exit: function (path) {
- var registrations = registrationsByProgramPath.get(path);
- if (registrations === undefined) {
- return;
- }
-
- var node = path.node;
- if (seenForOutro.has(node)) {
- return;
- }
- seenForOutro.add(node);
- registrationsByProgramPath.delete(path);
- var declarators = [];
- path.pushContainer('body', t.variableDeclaration('var', declarators));
- registrations.forEach(function (_ref) {
- var handle = _ref.handle,
- persistentID = _ref.persistentID;
- path.pushContainer('body', t.expressionStatement(t.callExpression(refreshReg, [handle, t.stringLiteral(persistentID)])));
- declarators.push(t.variableDeclarator(handle));
- });
- }
- }
- }
- };
- }
- module.exports = ReactFreshBabelPlugin;
- })();
- }
|