aboutsummaryrefslogtreecommitdiff
path: root/src/js_parser/js_parser.zig
diff options
context:
space:
mode:
Diffstat (limited to 'src/js_parser/js_parser.zig')
-rw-r--r--src/js_parser/js_parser.zig186
1 files changed, 95 insertions, 91 deletions
diff --git a/src/js_parser/js_parser.zig b/src/js_parser/js_parser.zig
index e5add04bf..1c5e63b06 100644
--- a/src/js_parser/js_parser.zig
+++ b/src/js_parser/js_parser.zig
@@ -2958,6 +2958,8 @@ pub fn NewParser(
pub const parser_features = js_parser_features;
const P = @This();
pub const jsx_transform_type: JSXTransformType = js_parser_jsx;
+ const allow_macros = FeatureFlags.is_macro_enabled and jsx_transform_type != .macro;
+ const MacroCallCountType = if (allow_macros) u32 else u0;
macro: MacroState = undefined,
allocator: Allocator,
options: Parser.Options,
@@ -2991,7 +2993,7 @@ pub fn NewParser(
promise_ref: ?Ref = null,
scopes_in_order_visitor_index: usize = 0,
has_classic_runtime_warned: bool = false,
- has_called_macro: bool = false,
+ macro_call_count: MacroCallCountType = 0,
/// Used for transforming export default -> module.exports
has_export_default: bool = false,
@@ -6178,7 +6180,6 @@ pub fn NewParser(
try p.lexer.expectContextualKeyword("from");
_ = try p.parsePath();
try p.lexer.expectOrInsertSemicolon();
- Output.debug("Imported type-only import", .{});
return p.s(S.TypeScript{}, loc);
},
else => {},
@@ -6241,7 +6242,7 @@ pub fn NewParser(
}
}
- const macro_remap = if ((comptime FeatureFlags.is_macro_enabled and jsx_transform_type != .macro) and !is_macro)
+ const macro_remap = if ((comptime allow_macros) and !is_macro)
p.options.macro_context.getRemap(path.text)
else
null;
@@ -11099,7 +11100,7 @@ pub fn NewParser(
if (func.name) |name| {
if (name.ref) |name_ref| {
p.recordDeclaredSymbol(name_ref) catch unreachable;
- const symbol_name = p.symbols.items[name_ref.inner_index].original_name;
+ const symbol_name = p.loadNameFromRef(name_ref);
if (isEvalOrArguments(symbol_name)) {
p.markStrictModeFeature(.eval_or_arguments, js_lexer.rangeOfIdentifier(p.source, name.loc), symbol_name) catch unreachable;
}
@@ -11495,12 +11496,12 @@ pub fn NewParser(
if (e_.tag) |tag| {
e_.tag = p.visitExpr(tag);
- if (comptime FeatureFlags.is_macro_enabled and jsx_transform_type != .macro) {
+ if (comptime allow_macros) {
if (e_.tag.?.data == .e_import_identifier) {
const ref = e_.tag.?.data.e_import_identifier.ref;
if (p.macro.refs.get(ref)) |import_record_id| {
const name = p.symbols.items[ref.inner_index].original_name;
- p.has_called_macro = true;
+ p.macro_call_count += 1;
const record = &p.import_records.items[import_record_id];
// We must visit it to convert inline_identifiers and record usage
const macro_result = (p.options.macro_context.call(
@@ -12175,8 +12176,8 @@ pub fn NewParser(
return _expr;
}
- if (comptime FeatureFlags.is_macro_enabled and jsx_transform_type != .macro) {
- if (p.has_called_macro) {
+ if (comptime allow_macros) {
+ if (p.macro_call_count > 0) {
if (e_.target.data == .e_object and e_.target.data.e_object.was_originally_macro) {
if (e_.target.get(e_.name)) |obj| {
return obj;
@@ -12431,7 +12432,7 @@ pub fn NewParser(
}
}
- if (comptime FeatureFlags.is_macro_enabled and jsx_transform_type != .macro) {
+ if (comptime allow_macros) {
if (is_macro_ref) {
const ref = e_.target.data.e_import_identifier.ref;
const import_record_id = p.macro.refs.get(ref).?;
@@ -12439,7 +12440,7 @@ pub fn NewParser(
const record = &p.import_records.items[import_record_id];
const copied = Expr{ .loc = expr.loc, .data = .{ .e_call = e_ } };
const start_error_count = p.log.msgs.items.len;
- p.has_called_macro = true;
+ p.macro_call_count += 1;
const macro_result =
p.options.macro_context.call(
record.path.text,
@@ -12972,8 +12973,8 @@ pub fn NewParser(
// }
// }
// }
- // if (comptime FeatureFlags.is_macro_enabled and jsx_transform_type != .macro) {
- // if (p.has_called_macro and data.decls[i].value != null and
+ // if (comptime allow_macros) {
+ // if (p.macro_call_count and data.decls[i].value != null and
// data.decls[i].value.?.data == .e_object and data.decls[i].value.?.data.e_object.was_originally_macro)
// {
// p.maybeInlineMacroObject(&data.decls[i], data.decls[i].value.?);
@@ -13339,87 +13340,18 @@ pub fn NewParser(
var val = data.decls[i].value.?;
const was_anonymous_named_expr = p.isAnonymousNamedExpr(val);
- data.decls[i].value = p.visitExpr(val);
+ const prev_macro_call_count = p.macro_call_count;
- // Optionally preserve the name
- switch (data.decls[i].binding.data) {
- .b_identifier => |id| {
- data.decls[i].value = p.maybeKeepExprSymbolName(
- data.decls[i].value.?,
- p.symbols.items[id.ref.inner_index].original_name,
- was_anonymous_named_expr,
- );
- },
- .b_object => |bound_object| {
- if (comptime FeatureFlags.is_macro_enabled and jsx_transform_type != .macro) {
- if (p.has_called_macro and data.decls[i].value != null and
- data.decls[i].value.?.data == .e_object and
- data.decls[i].value.?.data.e_object.was_originally_macro)
- {
- bail: {
- var object = data.decls[i].value.?.data.e_object;
- for (bound_object.properties) |property| {
- if (property.flags.is_spread) break :bail;
- }
- var output_properties = object.properties.slice();
- var end: u32 = 0;
- for (bound_object.properties) |property| {
- if (property.key.asString(p.allocator)) |name| {
- if (object.asProperty(name)) |query| {
- output_properties[end] = output_properties[query.i];
- end += 1;
- }
- }
- }
+ data.decls[i].value = p.visitExpr(val);
- object.properties.len = end;
- }
- }
- }
- },
- .b_array => |bound_array| {
- if (comptime FeatureFlags.is_macro_enabled and jsx_transform_type != .macro) {
- if (p.has_called_macro and data.decls[i].value != null and
- data.decls[i].value.?.data == .e_array and
- data.decls[i].value.?.data.e_array.was_originally_macro)
- {
- bail: {
- var array = data.decls[i].value.?.data.e_array;
- if (bound_array.has_spread) break :bail;
- array.items.len = @minimum(array.items.len, @truncate(u32, bound_array.items.len));
- var slice = array.items.slice();
- outer: for (bound_array.items[0..array.items.len]) |item, item_i| {
- const child_expr = slice[item_i];
- switch (item.binding.data) {
- .b_object => |bound_object| {
- if (child_expr.data != .e_object) continue :outer;
-
- for (bound_object.properties) |property| {
- if (property.flags.is_spread) continue :outer;
- }
- var object = child_expr.data.e_object;
- var output_properties = object.properties.slice();
- var end: u32 = 0;
- for (bound_object.properties) |property| {
- if (property.key.asString(p.allocator)) |name| {
- if (object.asProperty(name)) |query| {
- output_properties[end] = output_properties[query.i];
- end += 1;
- }
- }
- }
-
- object.properties.len = end;
- },
- else => {},
- }
- }
- }
- }
- }
- },
- else => {},
- }
+ p.visitDecl(
+ &data.decls[i],
+ was_anonymous_named_expr,
+ if (comptime allow_macros)
+ prev_macro_call_count != p.macro_call_count
+ else
+ false,
+ );
}
}
@@ -13954,6 +13886,78 @@ pub fn NewParser(
try stmts.append(stmt.*);
}
+ fn visitBindingAndExprForMacro(p: *P, binding: Binding, expr: Expr) void {
+ switch (binding.data) {
+ .b_object => |bound_object| {
+ if (expr.data == .e_object and
+ expr.data.e_object.was_originally_macro)
+ {
+ var object = expr.data.e_object;
+ for (bound_object.properties) |property| {
+ if (property.flags.is_spread) return;
+ }
+ var output_properties = object.properties.slice();
+ var end: u32 = 0;
+ for (bound_object.properties) |property| {
+ if (property.key.asString(p.allocator)) |name| {
+ if (object.asProperty(name)) |query| {
+ switch (query.expr.data) {
+ .e_object, .e_array => p.visitBindingAndExprForMacro(property.value, query.expr),
+ else => {},
+ }
+ output_properties[end] = output_properties[query.i];
+ end += 1;
+ }
+ }
+ }
+
+ object.properties.len = end;
+ }
+ },
+ .b_array => |bound_array| {
+ if (expr.data == .e_array and
+ expr.data.e_array.was_originally_macro and !bound_array.has_spread)
+ {
+ var array = expr.data.e_array;
+
+ array.items.len = @minimum(array.items.len, @truncate(u32, bound_array.items.len));
+ var slice = array.items.slice();
+ for (bound_array.items[0..array.items.len]) |item, item_i| {
+ const child_expr = slice[item_i];
+ if (item.binding.data == .b_missing) {
+ slice[item_i] = p.e(E.Missing{}, expr.loc);
+ continue;
+ }
+
+ p.visitBindingAndExprForMacro(item.binding, child_expr);
+ }
+ }
+ },
+ else => {},
+ }
+ }
+
+ fn visitDecl(p: *P, decl: *Decl, was_anonymous_named_expr: bool, could_be_macro: bool) void {
+ // Optionally preserve the name
+ switch (decl.binding.data) {
+ .b_identifier => |id| {
+ decl.value = p.maybeKeepExprSymbolName(
+ decl.value.?,
+ p.symbols.items[id.ref.inner_index].original_name,
+ was_anonymous_named_expr,
+ );
+ },
+ .b_object, .b_array => {
+ if (comptime allow_macros) {
+ if (could_be_macro and decl.value != null) {
+ p.visitBindingAndExprForMacro(decl.binding, decl.value.?);
+ }
+ }
+ },
+ else => {},
+ }
+ }
+
pub fn markExportedDeclsInsideNamespace(p: *P, ns_ref: Ref, decls: []G.Decl) void {
for (decls) |decl| {
p.markExportedBindingInsideNamespace(ns_ref, decl.binding);