333
schangxiang@126.com
2025-09-19 18966e02fb573c7e2bb0c6426ed792b38b910940
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
"use strict";
 
exports.__esModule = true;
 
var _symbol = require("babel-runtime/core-js/symbol");
 
var _symbol2 = _interopRequireDefault(_symbol);
 
var _plugin = require("../plugin");
 
var _plugin2 = _interopRequireDefault(_plugin);
 
var _babelTypes = require("babel-types");
 
var t = _interopRequireWildcard(_babelTypes);
 
function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key]; } } newObj.default = obj; return newObj; } }
 
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
 
var SUPER_THIS_BOUND = (0, _symbol2.default)("super this bound");
 
var superVisitor = {
  CallExpression: function CallExpression(path) {
    if (!path.get("callee").isSuper()) return;
 
    var node = path.node;
 
    if (node[SUPER_THIS_BOUND]) return;
    node[SUPER_THIS_BOUND] = true;
 
    path.replaceWith(t.assignmentExpression("=", this.id, node));
  }
};
 
exports.default = new _plugin2.default({
  name: "internal.shadowFunctions",
 
  visitor: {
    ThisExpression: function ThisExpression(path) {
      remap(path, "this");
    },
    ReferencedIdentifier: function ReferencedIdentifier(path) {
      if (path.node.name === "arguments") {
        remap(path, "arguments");
      }
    }
  }
});
 
 
function shouldShadow(path, shadowPath) {
  if (path.is("_forceShadow")) {
    return true;
  } else {
    return shadowPath;
  }
}
 
function remap(path, key) {
  var shadowPath = path.inShadow(key);
  if (!shouldShadow(path, shadowPath)) return;
 
  var shadowFunction = path.node._shadowedFunctionLiteral;
 
  var currentFunction = void 0;
  var passedShadowFunction = false;
 
  var fnPath = path.find(function (innerPath) {
    if (innerPath.parentPath && innerPath.parentPath.isClassProperty() && innerPath.key === "value") {
      return true;
    }
    if (path === innerPath) return false;
    if (innerPath.isProgram() || innerPath.isFunction()) {
      currentFunction = currentFunction || innerPath;
    }
 
    if (innerPath.isProgram()) {
      passedShadowFunction = true;
 
      return true;
    } else if (innerPath.isFunction() && !innerPath.isArrowFunctionExpression()) {
      if (shadowFunction) {
        if (innerPath === shadowFunction || innerPath.node === shadowFunction.node) return true;
      } else {
        if (!innerPath.is("shadow")) return true;
      }
 
      passedShadowFunction = true;
      return false;
    }
 
    return false;
  });
 
  if (shadowFunction && fnPath.isProgram() && !shadowFunction.isProgram()) {
    fnPath = path.findParent(function (p) {
      return p.isProgram() || p.isFunction();
    });
  }
 
  if (fnPath === currentFunction) return;
 
  if (!passedShadowFunction) return;
 
  var cached = fnPath.getData(key);
  if (!cached) {
    var id = path.scope.generateUidIdentifier(key);
 
    fnPath.setData(key, id);
    cached = id;
 
    var classPath = fnPath.findParent(function (p) {
      return p.isClass();
    });
    var hasSuperClass = !!(classPath && classPath.node && classPath.node.superClass);
 
    if (key === "this" && fnPath.isMethod({ kind: "constructor" }) && hasSuperClass) {
      fnPath.scope.push({ id: id });
 
      fnPath.traverse(superVisitor, { id: id });
    } else {
      var init = key === "this" ? t.thisExpression() : t.identifier(key);
 
      if (shadowFunction) init._shadowedFunctionLiteral = shadowFunction;
 
      fnPath.scope.push({ id: id, init: init });
    }
  }
 
  var node = t.cloneDeep(cached);
  node.loc = path.node.loc;
 
  return path.replaceWith(node);
}
module.exports = exports["default"];