fusee-framework 2.7.0 → 2.7.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (61) hide show
  1. package/README.md +98 -26
  2. package/bin/create-fusee-linux +0 -0
  3. package/bin/create-fusee-mac-arm64 +0 -0
  4. package/bin/create-fusee-mac-intel +0 -0
  5. package/bin/create-fusee-win.exe +0 -0
  6. package/framework/auto-import-preset.js +20 -12
  7. package/framework/auto-imports.d.ts +68 -39
  8. package/framework/core/compiler.js +310 -310
  9. package/framework/core/component-core.js +445 -0
  10. package/framework/core/component.js +11 -440
  11. package/framework/core/composable.js +29 -29
  12. package/framework/core/h.js +119 -44
  13. package/framework/core/jsx-helpers.js +11 -2
  14. package/framework/core/jsx-runtime.js +73 -73
  15. package/framework/core/rust-compiler/pkg/fusee_compiler_bg.wasm +0 -0
  16. package/framework/core/store.js +333 -333
  17. package/framework/globals.js +42 -0
  18. package/framework/index.js +22 -55
  19. package/framework/router/file-router.js +184 -184
  20. package/framework/server/actions.js +183 -183
  21. package/framework/server/generate-manifest.js +3 -3
  22. package/framework/types/component.d.ts +97 -86
  23. package/framework/types/index.d.ts +118 -117
  24. package/package.json +83 -80
  25. package/framework/core/rust-compiler/Cargo.toml +0 -31
  26. package/framework/core/rust-compiler/README.md +0 -69
  27. package/framework/core/rust-compiler/pkg/README.md +0 -69
  28. package/framework/core/rust-compiler/pkg/fusee_compiler.d.ts +0 -6
  29. package/framework/core/rust-compiler/pkg/fusee_compiler.js +0 -9
  30. package/framework/core/rust-compiler/pkg/fusee_compiler_bg.js +0 -137
  31. package/framework/core/rust-compiler/pkg/fusee_compiler_bg.wasm.d.ts +0 -11
  32. package/framework/core/rust-compiler/pkg/package.json +0 -18
  33. package/framework/core/rust-compiler/src/ast.rs +0 -274
  34. package/framework/core/rust-compiler/src/errors.rs +0 -204
  35. package/framework/core/rust-compiler/src/generator.rs +0 -583
  36. package/framework/core/rust-compiler/src/lexer.rs +0 -414
  37. package/framework/core/rust-compiler/src/lib.rs +0 -87
  38. package/framework/core/rust-compiler/src/main_compiler.rs +0 -165
  39. package/framework/core/rust-compiler/src/parser.rs +0 -516
  40. package/framework/core/rust-compiler/src/ssr_generator.rs +0 -688
  41. package/framework/core/rust-compiler/src/transformer.rs +0 -562
  42. package/framework/core/rust-compiler/src/utils.rs +0 -10
  43. package/framework/engine-go/actions.go +0 -112
  44. package/framework/engine-go/cmd/server/main.go +0 -233
  45. package/framework/engine-go/comet/comet.go +0 -41
  46. package/framework/engine-go/comet/fragment.go +0 -51
  47. package/framework/engine-go/dispatcher.go +0 -120
  48. package/framework/engine-go/elements.go +0 -248
  49. package/framework/engine-go/evalexpr/evalexpr.go +0 -733
  50. package/framework/engine-go/go.mod +0 -3
  51. package/framework/engine-go/hydration.go +0 -43
  52. package/framework/engine-go/load-helpers.go +0 -29
  53. package/framework/engine-go/manifest.go +0 -41
  54. package/framework/engine-go/reactive.go +0 -123
  55. package/framework/engine-go/render.go +0 -635
  56. package/framework/engine-go/reqcontext.go +0 -48
  57. package/framework/engine-go/router.go +0 -85
  58. package/framework/engine-go/rustast/rustast.go +0 -317
  59. package/framework/engine-go/ssr.go +0 -103
  60. package/framework/engine-go/static-assets.go +0 -139
  61. package/framework/node_modules/.vite/vitest/da39a3ee5e6b4b0d3255bfef95601890afd80709/results.json +0 -1
@@ -1,583 +0,0 @@
1
- use crate::args;
2
- use crate::ast::*;
3
- use crate::errors::{CompileError, ErrorCode};
4
- use once_cell::sync::Lazy;
5
- use std::collections::{HashMap, HashSet};
6
-
7
- const DEFAULT_RUNTIME: &str = "fusee/runtime/h.js";
8
-
9
- pub struct GenerateOptions {
10
- pub source: String,
11
- pub runtime_path: Option<String>,
12
- }
13
-
14
- pub fn generate(root: &RootNode, options: GenerateOptions) -> Result<String, CompileError> {
15
- let mut gen = Generator::new(&options.source, options.runtime_path.as_deref());
16
- gen.generate(root)
17
- }
18
-
19
- struct OrderedSet {
20
- items: Vec<String>,
21
- seen: HashSet<String>,
22
- }
23
-
24
- impl OrderedSet {
25
- fn new(initial: &[&str]) -> Self {
26
- let mut s = OrderedSet {
27
- items: Vec::new(),
28
- seen: HashSet::new(),
29
- };
30
- for i in initial {
31
- s.add(i);
32
- }
33
- s
34
- }
35
- fn add(&mut self, s: &str) {
36
- if self.seen.insert(s.to_string()) {
37
- self.items.push(s.to_string());
38
- }
39
- }
40
- fn join(&self, sep: &str) -> String {
41
- self.items.join(sep)
42
- }
43
- }
44
-
45
- struct Generator<'a> {
46
- source: &'a str,
47
- runtime_path: String,
48
- imports: OrderedSet,
49
- hoisted_lookup: HashMap<NodeId, String>,
50
- hoisted_order: Vec<(NodeId, String)>,
51
- local_scopes: Vec<HashSet<String>>,
52
- }
53
-
54
- impl<'a> Generator<'a> {
55
- fn new(source: &'a str, runtime_path: Option<&str>) -> Self {
56
- Generator {
57
- source,
58
- runtime_path: runtime_path.unwrap_or(DEFAULT_RUNTIME).to_string(),
59
- imports: OrderedSet::new(&["h", "hText", "createComponent", "_effect", "_batch"]),
60
- hoisted_lookup: HashMap::new(),
61
- hoisted_order: Vec::new(),
62
- local_scopes: Vec::new(),
63
- }
64
- }
65
-
66
- fn generate(&mut self, root: &RootNode) -> Result<String, CompileError> {
67
- for (idx, id) in root.hoisted.iter().enumerate() {
68
- let name = format!("_s{}", idx);
69
- self.hoisted_lookup.insert(*id, name.clone());
70
- self.hoisted_order.push((*id, name));
71
- }
72
-
73
- let mut id_to_node: HashMap<NodeId, &ElementNode> = HashMap::new();
74
- for c in &root.children {
75
- collect_element_refs(c, &mut id_to_node);
76
- }
77
-
78
- let hoisted_order = self.hoisted_order.clone();
79
- let mut hoisted_decls = Vec::new();
80
- for (id, name) in &hoisted_order {
81
- if let Some(&node) = id_to_node.get(id) {
82
- let code = self.gen_element(node, true)?;
83
- hoisted_decls.push(format!("const {} = {}", name, code));
84
- }
85
- }
86
-
87
- let children = self.gen_children(&root.children)?;
88
-
89
- let import_list = self.imports.join(", ");
90
- let mut output = vec![format!("import {{ {} }} from '{}'", import_list, self.runtime_path), String::new(), ];
91
- if !hoisted_decls.is_empty() {
92
- output.extend(hoisted_decls);
93
- output.push(String::new());
94
- }
95
- output.push("export function render(_ctx, _components) {".to_string());
96
- output.push(" return [".to_string());
97
- output.push(
98
- children
99
- .iter()
100
- .map(|l| format!(" {}", l))
101
- .collect::<Vec<_>>()
102
- .join(",\n"),
103
- );
104
- output.push(" ]".to_string());
105
- output.push("}".to_string());
106
-
107
- Ok(output.join("\n"))
108
- }
109
-
110
- fn gen_children(&mut self, children: &[Node]) -> Result<Vec<String>, CompileError> {
111
- let mut out = Vec::new();
112
- for child in children {
113
- if let Some(for_dir) = find_for_dir(child) {
114
- out.push(self.gen_for_node(child, for_dir)?);
115
- } else {
116
- out.push(self.gen_node(child, false)?);
117
- }
118
- }
119
- Ok(out)
120
- }
121
-
122
- fn gen_node(&mut self, node: &Node, in_hoist: bool) -> Result<String, CompileError> {
123
- if !in_hoist {
124
- if let Node::Element(e) = node {
125
- if let Some(name) = self.hoisted_lookup.get(&e.id) {
126
- return Ok(name.clone());
127
- }
128
- }
129
- }
130
-
131
- match node {
132
- Node::Text(t) => Ok(self.gen_text(t)),
133
- Node::Interpolation(i) => Ok(self.gen_interpolation(i)),
134
- Node::Element(e) => self.gen_element(e, false),
135
- Node::Component(c) => self.gen_component(c),
136
- Node::SlotOutlet(s) => self.gen_slot_outlet(s),
137
- Node::If(i) => self.gen_if(i),
138
- other => Err(CompileError::new(
139
- ErrorCode::UnknownNodeType,
140
- other.loc().clone(),
141
- self.source,
142
- args!(node_type_name(other)),
143
- )),
144
- }
145
- }
146
-
147
- fn gen_text(&self, node: &TextNode) -> String {
148
- format!("hText({})", json_string(&node.content))
149
- }
150
-
151
- fn gen_interpolation(&mut self, node: &InterpolationNode) -> String {
152
- self.imports.add("_effect");
153
- let expr = &node.expression.content;
154
- if node.expression.is_static {
155
- format!("hText(String({}))", expr)
156
- } else {
157
- format!("hText(() => String({}))", self.wrap_expr(expr))
158
- }
159
- }
160
-
161
- fn gen_element(&mut self, node: &ElementNode, in_hoist: bool) -> Result<String, CompileError> {
162
- let tag = json_string(&node.tag);
163
- let props = self.gen_props(&node.props)?;
164
- let children = self.gen_children_array(&node.children, in_hoist)?;
165
- let mut args = vec![tag, props, children];
166
- if node.is_static {
167
- args.push("true".to_string());
168
- }
169
- Ok(format!("h({})", args.join(", ")))
170
- }
171
-
172
- fn gen_component(&mut self, node: &ComponentNode) -> Result<String, CompileError> {
173
- self.imports.add("createComponent");
174
- let name = json_string(&node.name);
175
- let props = self.gen_component_props(&node.props)?;
176
- let slots = self.gen_slots(&node.slots)?;
177
- Ok(format!(
178
- "createComponent({}, _components[{}], {}, {})",
179
- name, name, props, slots
180
- ))
181
- }
182
-
183
- fn gen_slot_outlet(&mut self, node: &SlotOutletNode) -> Result<String, CompileError> {
184
- self.imports.add("hSlot");
185
- let name = json_string(&node.slot_name);
186
- let fallback = self.gen_children_array(&node.fallback, false)?;
187
- Ok(format!("hSlot(_ctx._slots, {}, {})", name, fallback))
188
- }
189
-
190
- fn gen_if(&mut self, node: &IfNode) -> Result<String, CompileError> {
191
- self.imports.add("hIf");
192
- let mut branches = Vec::new();
193
- for branch in &node.branches {
194
- let cond = match &branch.condition {
195
- Some(c) => self.wrap_expr(&c.content),
196
- None => "true".to_string(),
197
- };
198
- let node_str = self.gen_node(&branch.node, false)?;
199
- branches.push(format!("[() => {}, () => [{}]]", cond, node_str));
200
- }
201
- Ok(format!("hIf([\n {}\n ])", branches.join(",\n ")))
202
- }
203
-
204
- fn gen_props(&mut self, props: &[Prop]) -> Result<String, CompileError> {
205
- if props.is_empty() {
206
- return Ok("{}".to_string());
207
- }
208
- let mut entries = Vec::new();
209
- for prop in props {
210
- match prop {
211
- Prop::Attribute(a) => entries.push(self.gen_attr_entry(a)),
212
- Prop::Binding(b) => entries.push(self.gen_binding_entry(b)),
213
- Prop::Event(e) => entries.push(self.gen_event_entry(e)),
214
- Prop::Directive(d) => self.gen_directive_entries(d, &mut entries)?,
215
- }
216
- }
217
- Ok(format!("{{\n {}\n }}", entries.join(",\n ")))
218
- }
219
-
220
- fn gen_attr_entry(&self, prop: &AttributeNode) -> String {
221
- let value = match &prop.value {
222
- Some(v) => json_string(v),
223
- None => "true".to_string(),
224
- };
225
- format!("{}: {}", json_string(&prop.name), value)
226
- }
227
-
228
- fn gen_binding_entry(&mut self, prop: &BindingNode) -> String {
229
- let expr = self.wrap_expr(&prop.expression.content);
230
- if prop.is_prop {
231
- format!("{}: () => {}", json_string(&format!("prop:{}", prop.name)), expr)
232
- } else {
233
- format!("{}: () => {}", json_string(&prop.name), expr)
234
- }
235
- }
236
-
237
- fn gen_event_entry(&mut self, prop: &EventNode) -> String {
238
- let key = json_string(&format!("@{}", prop.name));
239
- let handler_js = self.gen_handler_expr(&prop.expression.content);
240
- let mods = json_array(&prop.modifiers);
241
- format!("{}: {{ handler: {}, modifiers: {} }}", key, handler_js, mods)
242
- }
243
-
244
- fn gen_handler_expr(&self, expr: &str) -> String {
245
- if is_simple_identifier(expr.trim()) {
246
- format!("_ctx.{}", expr.trim())
247
- } else {
248
- format!("($event) => {{ {} }}", expr)
249
- }
250
- }
251
-
252
- fn gen_directive_entries(&mut self, dir: &DirectiveNode, entries: &mut Vec<String>, ) -> Result<(), CompileError> {
253
- match dir.name.as_str() {
254
- "if" | "else-if" | "else" | "for" => {}
255
- "show" => {
256
- let expr = self.wrap_expr(&dir.expression.as_ref().unwrap().content);
257
- entries.push(format!("'f-show': () => {}", expr));
258
- }
259
- "model" => {
260
- let expr = dir.expression.as_ref().unwrap().content.clone();
261
- entries.push(format!("'f-model': () => _ctx.{}", expr));
262
- entries.push(format!(
263
- "'@input': {{ handler: ($e) => {{ _ctx.{}($e.target.value) }}, modifiers: [] }}",
264
- expr
265
- ));
266
- }
267
- "html" => {
268
- let expr = self.wrap_expr(&dir.expression.as_ref().unwrap().content);
269
- entries.push(format!("'f-html': () => {}", expr));
270
- }
271
- "ref" => {
272
- let name = dir.expression.as_ref().unwrap().content.trim().to_string();
273
- entries.push(format!("'f-ref': {}", json_string(&name)));
274
- }
275
- "once" => {
276
- entries.push("'f-once': true".to_string());
277
- }
278
- other => {
279
- let value = match &dir.expression {
280
- Some(e) => format!("() => {}", self.wrap_expr(&e.content)),
281
- None => "true".to_string(),
282
- };
283
- entries.push(format!("{}: {}", json_string(&format!("f-{}", other)), value));
284
- }
285
- }
286
- Ok(())
287
- }
288
-
289
- fn gen_component_props(&mut self, props: &[Prop]) -> Result<String, CompileError> {
290
- if props.is_empty() {
291
- return Ok("{}".to_string());
292
- }
293
- let mut entries = Vec::new();
294
- for prop in props {
295
- match prop {
296
- Prop::Attribute(a) => {
297
- let value = match &a.value {
298
- Some(v) => json_string(v),
299
- None => "true".to_string(),
300
- };
301
- entries.push(format!("{}: {}", json_string(&a.name), value));
302
- }
303
- Prop::Binding(b) => {
304
- let expr = self.wrap_expr(&b.expression.content);
305
- entries.push(format!("{}: () => {}", json_string(&b.name), expr));
306
- }
307
- Prop::Event(e) => {
308
- let handler_js = self.gen_handler_expr(&e.expression.content);
309
- entries.push(format!("{}: {}", json_string(&format!("on:{}", e.name)), handler_js));
310
- }
311
- Prop::Directive(_) => {}
312
- }
313
- }
314
- Ok(format!("{{ {} }}", entries.join(", ")))
315
- }
316
-
317
- fn gen_slots(&mut self, slots: &[(String, Vec<Node>)]) -> Result<String, CompileError> {
318
- if slots.is_empty() {
319
- return Ok("{}".to_string());
320
- }
321
- let mut entries = Vec::new();
322
- for (name, children) in slots {
323
- let children_js = self.gen_children_array(children, false)?;
324
- entries.push(format!("{}: () => {}", json_string(name), children_js));
325
- }
326
- Ok(format!("{{ {} }}", entries.join(", ")))
327
- }
328
-
329
- fn gen_children_array(&mut self, children: &[Node], in_hoist: bool) -> Result<String, CompileError> {
330
- if children.is_empty() {
331
- return Ok("[]".to_string());
332
- }
333
- let mut expanded = Vec::new();
334
- for child in children {
335
- if let Some(for_dir) = find_for_dir(child) {
336
- expanded.push(self.gen_for_node(child, for_dir)?);
337
- } else {
338
- expanded.push(self.gen_node(child, in_hoist)?);
339
- }
340
- }
341
- if expanded.len() == 1 {
342
- Ok(format!("[{}]", expanded[0]))
343
- } else {
344
- Ok(format!("[\n {}\n ]", expanded.join(",\n ")))
345
- }
346
- }
347
-
348
- fn gen_for_node(&mut self, node: &Node, for_dir: &DirectiveNode) -> Result<String, CompileError> {
349
- self.imports.add("hFor");
350
- let for_arg = for_dir.arg.as_ref().expect("f-for must have parsed arg");
351
- let item = for_arg.item.clone();
352
- let index = for_arg.index.clone();
353
- let source_js = self.wrap_expr(&for_arg.source);
354
-
355
- let mut scope = HashSet::new();
356
- scope.insert(item.clone());
357
- if let Some(idx) = &index {
358
- scope.insert(idx.clone());
359
- }
360
- self.local_scopes.push(scope);
361
-
362
- let props = node.props().cloned().unwrap_or_default();
363
- let inner_props: Vec<Prop> = props
364
- .into_iter()
365
- .filter(|p| !matches!(p, Prop::Directive(d) if d.name == "for"))
366
- .collect();
367
-
368
- let key_binding = inner_props
369
- .iter()
370
- .find_map(|p| p.as_binding().filter(|b| b.name == "key"));
371
- let key_expr = key_binding
372
- .map(|b| b.expression.content.clone())
373
- .unwrap_or_else(|| "undefined".to_string());
374
-
375
- let inner_node = with_props(node.clone(), inner_props);
376
- let item_param = match &index {
377
- Some(idx) => format!("{}, {}", item, idx),
378
- None => item.clone(),
379
- };
380
- let item_param_str = format!("({})", item_param);
381
- let inner_js = self.gen_node(&inner_node, false)?;
382
- let key_js = self.wrap_expr(&key_expr);
383
-
384
- self.local_scopes.pop();
385
-
386
- Ok(format!(
387
- "hFor(\n () => {},\n {} => {},\n {} => {}\n )",
388
- source_js, item_param_str, inner_js, item_param_str, key_js
389
- ))
390
- }
391
-
392
- fn is_local(&self, id: &str) -> bool {
393
- self.local_scopes.iter().any(|s| s.contains(id))
394
- }
395
-
396
- fn wrap_expr(&mut self, expr: &str) -> String {
397
- if expr.contains("_ctx.") {
398
- return expr.to_string();
399
- }
400
- if is_dotted_identifier_path(expr.trim()) {
401
- let id = expr.trim().to_string();
402
- let root_var = id.split('.').next().unwrap_or("");
403
- if self.is_local(root_var) {
404
- return id;
405
- }
406
- return format!(
407
- "(typeof _ctx.{} === 'function' && _ctx.{}.isSignal ? _ctx.{}() : _ctx.{})",
408
- id, id, id, id
409
- );
410
- }
411
- self.rewrite_expr(expr)
412
- }
413
-
414
- fn rewrite_expr(&self, expr: &str) -> String {
415
- let chars: Vec<char> = expr.chars().collect();
416
- let mut out = String::new();
417
- let mut i = 0;
418
- let mut skip_next_identifier = false;
419
-
420
- while i < chars.len() {
421
- let c = chars[i];
422
- if c.is_ascii_alphabetic() || c == '_' || c == '$' {
423
- let start = i;
424
- let mut j = i;
425
- while j < chars.len()
426
- && (chars[j].is_ascii_alphanumeric() || chars[j] == '_' || chars[j] == '$')
427
- {
428
- j += 1;
429
- }
430
- let id: String = chars[start..j].iter().collect();
431
-
432
- if skip_next_identifier {
433
- out.push_str(&id);
434
- skip_next_identifier = false;
435
- i = j;
436
- continue;
437
- }
438
-
439
- let preceded_by_dot_or_word = start > 0
440
- && (chars[start - 1] == '.'
441
- || chars[start - 1].is_ascii_alphanumeric()
442
- || chars[start - 1] == '_'
443
- || chars[start - 1] == '$');
444
-
445
- let mut preceded_by_colon = false;
446
- if start > 0 {
447
- let mut p = start - 1;
448
- while p > 0 && chars[p].is_whitespace() {
449
- p -= 1;
450
- }
451
- if chars[p] == ':' {
452
- preceded_by_colon = true;
453
- }
454
- }
455
-
456
- let mut k = j;
457
- while k < chars.len() && chars[k].is_whitespace() {
458
- k += 1;
459
- }
460
- let followed_by_colon = k < chars.len() && chars[k] == ':';
461
-
462
- if preceded_by_dot_or_word || preceded_by_colon || followed_by_colon {
463
- out.push_str(&id);
464
- } else if GENERATOR_GLOBALS.contains(id.as_str()) {
465
- out.push_str(&id);
466
- if id == "as" || id == "satisfies" {
467
- skip_next_identifier = true;
468
- }
469
- } else if self.is_local(&id) {
470
- out.push_str(&id);
471
- } else {
472
- out.push_str("_ctx.");
473
- out.push_str(&id);
474
- }
475
- i = j;
476
- } else {
477
- out.push(c);
478
- i += 1;
479
- }
480
- }
481
-
482
- out
483
- }
484
- }
485
-
486
- fn node_type_name(node: &Node) -> &'static str {
487
- match node {
488
- Node::Root(_) => "Root",
489
- Node::Element(_) => "Element",
490
- Node::Component(_) => "Component",
491
- Node::Text(_) => "Text",
492
- Node::Interpolation(_) => "Interpolation",
493
- Node::SlotOutlet(_) => "SlotOutlet",
494
- Node::SlotContent(_) => "SlotContent",
495
- Node::If(_) => "If",
496
- }
497
- }
498
-
499
- fn find_for_dir(node: &Node) -> Option<&DirectiveNode> {
500
- node.props()?
501
- .iter()
502
- .find_map(|p| p.as_directive().filter(|d| d.name == "for"))
503
- }
504
-
505
- fn with_props(node: Node, props: Vec<Prop>) -> Node {
506
- match node {
507
- Node::Element(mut e) => {
508
- e.props = props;
509
- Node::Element(e)
510
- }
511
- Node::Component(mut c) => {
512
- c.props = props;
513
- Node::Component(c)
514
- }
515
- other => other,
516
- }
517
- }
518
-
519
- fn collect_element_refs<'a>(node: &'a Node, out: &mut HashMap<NodeId, &'a ElementNode>) {
520
- match node {
521
- Node::Element(e) => {
522
- out.insert(e.id, e);
523
- for c in &e.children {
524
- collect_element_refs(c, out);
525
- }
526
- }
527
- Node::Component(c) => {
528
- for (_, children) in &c.slots {
529
- for child in children {
530
- collect_element_refs(child, out);
531
- }
532
- }
533
- }
534
- Node::If(i) => {
535
- for b in &i.branches {
536
- collect_element_refs(&b.node, out);
537
- }
538
- }
539
- _ => {}
540
- }
541
- }
542
-
543
- fn json_string(s: &str) -> String {
544
- serde_json::to_string(s).unwrap_or_else(|_| "\"\"".to_string())
545
- }
546
-
547
- fn json_array(items: &[String]) -> String {
548
- serde_json::to_string(items).unwrap_or_else(|_| "[]".to_string())
549
- }
550
-
551
- fn is_simple_identifier(s: &str) -> bool {
552
- let mut chars = s.chars();
553
- match chars.next() {
554
- Some(c) if c.is_ascii_alphabetic() || c == '_' || c == '$' => {}
555
- _ => return false,
556
- }
557
- chars.all(|c| c.is_ascii_alphanumeric() || c == '_' || c == '$')
558
- }
559
-
560
- fn is_dotted_identifier_path(s: &str) -> bool {
561
- if s.is_empty() {
562
- return false;
563
- }
564
- let mut chars = s.chars();
565
- match chars.next() {
566
- Some(c) if c.is_ascii_alphabetic() || c == '_' || c == '$' => {}
567
- _ => return false,
568
- }
569
- chars.all(|c| c.is_ascii_alphanumeric() || c == '_' || c == '$' || c == '.')
570
- }
571
-
572
- static GENERATOR_GLOBALS: Lazy<HashSet<&'static str>> = Lazy::new(|| {
573
- [
574
- "true", "false", "null", "undefined", "NaN", "Infinity", "Array", "Object", "String",
575
- "Number", "Boolean", "Date", "Math", "JSON", "Promise", "Map", "Set", "Symbol",
576
- "parseInt", "parseFloat", "isNaN", "isFinite", "console", "typeof", "instanceof", "void",
577
- "delete", "new", "return", "if", "else", "for", "while", "do", "switch", "case", "break",
578
- "continue", "function", "class", "const", "let", "var", "import", "export", "default",
579
- "this", "as", "satisfies",
580
- ]
581
- .into_iter()
582
- .collect()
583
- });