@tishlang/tish 1.9.1 → 1.10.0
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.
- package/bin/tish +0 -0
- package/crates/js_to_tish/src/transform/expr.rs +8 -6
- package/crates/js_to_tish/src/transform/stmt.rs +12 -13
- package/crates/tish/Cargo.toml +1 -1
- package/crates/tish/src/cargo_native_registry.rs +4 -1
- package/crates/tish/src/main.rs +11 -8
- package/crates/tish/tests/integration_test.rs +145 -7
- package/crates/tish_ast/src/ast.rs +3 -9
- package/crates/tish_build_utils/src/lib.rs +43 -15
- package/crates/tish_builtins/src/array.rs +2 -3
- package/crates/tish_builtins/src/construct.rs +15 -28
- package/crates/tish_builtins/src/globals.rs +18 -16
- package/crates/tish_builtins/src/helpers.rs +1 -4
- package/crates/tish_builtins/src/lib.rs +1 -0
- package/crates/tish_builtins/src/object.rs +10 -10
- package/crates/tish_builtins/src/string.rs +1 -3
- package/crates/tish_builtins/src/symbol.rs +83 -0
- package/crates/tish_compile/src/codegen.rs +123 -138
- package/crates/tish_compile/src/lib.rs +25 -3
- package/crates/tish_compile/src/resolve.rs +6 -3
- package/crates/tish_compile/src/types.rs +6 -6
- package/crates/tish_compile_js/src/codegen.rs +50 -29
- package/crates/tish_compile_js/src/tests_jsx.rs +44 -0
- package/crates/tish_core/src/console_style.rs +9 -0
- package/crates/tish_core/src/json.rs +17 -7
- package/crates/tish_core/src/macros.rs +2 -2
- package/crates/tish_core/src/value.rs +192 -4
- package/crates/tish_cranelift_runtime/Cargo.toml +4 -0
- package/crates/tish_eval/src/eval.rs +135 -73
- package/crates/tish_eval/src/http.rs +18 -12
- package/crates/tish_eval/src/lib.rs +29 -0
- package/crates/tish_eval/src/regex.rs +1 -1
- package/crates/tish_eval/src/value.rs +89 -4
- package/crates/tish_eval/src/value_convert.rs +30 -8
- package/crates/tish_fmt/src/lib.rs +4 -1
- package/crates/tish_lexer/src/lib.rs +7 -2
- package/crates/tish_llvm/src/lib.rs +2 -2
- package/crates/tish_lsp/src/builtin_goto.rs +111 -10
- package/crates/tish_lsp/src/import_goto.rs +35 -22
- package/crates/tish_lsp/src/main.rs +118 -85
- package/crates/tish_native/src/build.rs +187 -10
- package/crates/tish_native/src/lib.rs +92 -8
- package/crates/tish_parser/src/lib.rs +77 -0
- package/crates/tish_parser/src/parser.rs +71 -74
- package/crates/tish_pg/src/error.rs +1 -1
- package/crates/tish_pg/src/lib.rs +61 -73
- package/crates/tish_resolve/src/lib.rs +283 -158
- package/crates/tish_resolve/src/pos.rs +10 -2
- package/crates/tish_runtime/Cargo.toml +3 -0
- package/crates/tish_runtime/src/http.rs +39 -39
- package/crates/tish_runtime/src/http_fetch.rs +12 -12
- package/crates/tish_runtime/src/lib.rs +26 -43
- package/crates/tish_runtime/src/native_promise.rs +0 -11
- package/crates/tish_runtime/src/promise.rs +14 -1
- package/crates/tish_runtime/src/promise_io.rs +1 -4
- package/crates/tish_runtime/src/ws.rs +40 -27
- package/crates/tish_runtime/tests/fetch_readable_stream.rs +10 -8
- package/crates/tish_ui/src/jsx.rs +6 -4
- package/crates/tish_ui/src/lib.rs +2 -2
- package/crates/tish_ui/src/runtime/hooks.rs +5 -15
- package/crates/tish_ui/src/runtime/mod.rs +16 -17
- package/crates/tish_vm/Cargo.toml +2 -0
- package/crates/tish_vm/src/vm.rs +218 -153
- package/crates/tish_wasm/src/lib.rs +33 -7
- package/crates/tish_wasm_runtime/Cargo.toml +4 -1
- package/crates/tish_wasm_runtime/src/lib.rs +2 -1
- package/crates/tishlang_cargo_bindgen/src/classify.rs +1 -3
- package/crates/tishlang_cargo_bindgen/src/discover.rs +10 -5
- package/crates/tishlang_cargo_bindgen/src/infer.rs +18 -8
- package/crates/tishlang_cargo_bindgen/src/lib.rs +25 -26
- package/crates/tishlang_cargo_bindgen/src/main.rs +41 -38
- package/crates/tishlang_cargo_bindgen/src/metadata.rs +4 -1
- package/justfile +3 -3
- package/package.json +1 -1
- package/platform/darwin-arm64/tish +0 -0
- package/platform/darwin-x64/tish +0 -0
- package/platform/linux-arm64/tish +0 -0
- package/platform/linux-x64/tish +0 -0
- package/platform/win32-x64/tish.exe +0 -0
|
@@ -560,15 +560,13 @@ pub fn compile_project_full(
|
|
|
560
560
|
message: e,
|
|
561
561
|
span: None,
|
|
562
562
|
})?;
|
|
563
|
-
let native_build =
|
|
564
|
-
&merged.program,
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
|
|
570
|
-
span: None,
|
|
571
|
-
})?;
|
|
563
|
+
let native_build =
|
|
564
|
+
resolve::compute_native_build_artifacts(&merged.program, root, &native_modules).map_err(
|
|
565
|
+
|e| CompileError {
|
|
566
|
+
message: e,
|
|
567
|
+
span: None,
|
|
568
|
+
},
|
|
569
|
+
)?;
|
|
572
570
|
let mut all_features: Vec<String> = features.to_vec();
|
|
573
571
|
for f in resolve::extract_native_import_features(&merged.program) {
|
|
574
572
|
if !all_features.contains(&f) {
|
|
@@ -731,12 +729,9 @@ impl Codegen {
|
|
|
731
729
|
for _ in 0..8 {
|
|
732
730
|
let mut changed = false;
|
|
733
731
|
for (name, ann) in &raw {
|
|
734
|
-
let resolved =
|
|
735
|
-
ann,
|
|
736
|
-
|
|
737
|
-
);
|
|
738
|
-
let prev: Option<crate::types::RustType> =
|
|
739
|
-
self.type_aliases.get(name).cloned();
|
|
732
|
+
let resolved =
|
|
733
|
+
crate::types::RustType::from_annotation_with_aliases(ann, &self.type_aliases);
|
|
734
|
+
let prev: Option<crate::types::RustType> = self.type_aliases.get(name).cloned();
|
|
740
735
|
if prev.as_ref() != Some(&resolved) {
|
|
741
736
|
self.type_aliases.insert(name.clone(), resolved);
|
|
742
737
|
changed = true;
|
|
@@ -791,8 +786,11 @@ impl Codegen {
|
|
|
791
786
|
fn emit_named_struct_decls(&mut self) {
|
|
792
787
|
// Snapshot keys + values so we can mutate `self` (writing the
|
|
793
788
|
// emitted source) inside the loop.
|
|
794
|
-
let mut entries: Vec<(String, crate::types::RustType)> =
|
|
795
|
-
|
|
789
|
+
let mut entries: Vec<(String, crate::types::RustType)> = self
|
|
790
|
+
.type_aliases
|
|
791
|
+
.iter()
|
|
792
|
+
.map(|(k, v)| (k.clone(), v.clone()))
|
|
793
|
+
.collect();
|
|
796
794
|
entries.sort_by(|a, b| a.0.cmp(&b.0));
|
|
797
795
|
let mut emitted_any = false;
|
|
798
796
|
for (name, ty) in entries {
|
|
@@ -928,7 +926,7 @@ impl Codegen {
|
|
|
928
926
|
}
|
|
929
927
|
};
|
|
930
928
|
format!(
|
|
931
|
-
"{{ let _ns = {}; match _ns {{ Value::Object(ref _o) => _o.borrow().get({:?}).cloned().unwrap_or(Value::Null), _ => Value::Null }} }}",
|
|
929
|
+
"{{ let _ns = {}; match _ns {{ Value::Object(ref _o) => _o.borrow().strings.get({:?}).cloned().unwrap_or(Value::Null), _ => Value::Null }} }}",
|
|
932
930
|
init_expr, export_name
|
|
933
931
|
)
|
|
934
932
|
})
|
|
@@ -954,8 +952,9 @@ impl Codegen {
|
|
|
954
952
|
// latter dispatches into `http_serve_per_worker`, which
|
|
955
953
|
// calls onWorker once per accept thread to build that
|
|
956
954
|
// thread's handler.
|
|
957
|
-
"serve" => Some("Value::native(|args: &[Value]| { let handler = args.get(1).cloned().unwrap_or(Value::Null); match handler { Value::Function(f) => tish_http_serve(args, move |req_args| f(req_args)), Value::Object(ref opts) => { let factory = opts.borrow().get(
|
|
955
|
+
"serve" => Some("Value::native(|args: &[Value]| { let handler = args.get(1).cloned().unwrap_or(Value::Null); match handler { Value::Function(f) => tish_http_serve(args, move |req_args| f(req_args)), Value::Object(ref opts) => { let factory = opts.borrow().strings.get(\"onWorker\").cloned().unwrap_or(Value::Null); tishlang_runtime::http_serve_per_worker(args, factory) }, _ => Value::Null } })"),
|
|
958
956
|
"Promise" => Some("tish_promise_object()"),
|
|
957
|
+
"Symbol" => Some("tish_symbol_object()"),
|
|
959
958
|
_ => None,
|
|
960
959
|
},
|
|
961
960
|
"tish:timers" if self.has_feature("timers") => match export_name {
|
|
@@ -970,8 +969,8 @@ impl Codegen {
|
|
|
970
969
|
"cwd" => Some("Value::native(|args: &[Value]| tish_process_cwd(args))"),
|
|
971
970
|
"exec" => Some("Value::native(|args: &[Value]| tish_process_exec(args))"),
|
|
972
971
|
"argv" => Some("Value::Array(VmRef::new(std::env::args().map(|s| Value::String(s.into())).collect()))"),
|
|
973
|
-
"env" => Some("Value::
|
|
974
|
-
"process" => Some("{ let mut m = ObjectMap::default(); m.insert(Arc::from(\"exit\"), Value::native(|args: &[Value]| tish_process_exit(args))); m.insert(Arc::from(\"cwd\"), Value::native(|args: &[Value]| tish_process_cwd(args))); m.insert(Arc::from(\"exec\"), Value::native(|args: &[Value]| tish_process_exec(args))); m.insert(Arc::from(\"argv\"), Value::Array(VmRef::new(std::env::args().map(|s| Value::String(s.into())).collect()))); m.insert(Arc::from(\"env\"), Value::
|
|
972
|
+
"env" => Some("Value::object(std::env::vars().map(|(k,v)| (Arc::from(k.as_str()), Value::String(v.into()))).collect())"),
|
|
973
|
+
"process" => Some("{ let mut m = ObjectMap::default(); m.insert(Arc::from(\"exit\"), Value::native(|args: &[Value]| tish_process_exit(args))); m.insert(Arc::from(\"cwd\"), Value::native(|args: &[Value]| tish_process_cwd(args))); m.insert(Arc::from(\"exec\"), Value::native(|args: &[Value]| tish_process_exec(args))); m.insert(Arc::from(\"argv\"), Value::Array(VmRef::new(std::env::args().map(|s| Value::String(s.into())).collect()))); m.insert(Arc::from(\"env\"), Value::object(std::env::vars().map(|(k,v)| (Arc::from(k.as_str()), Value::String(v.into()))).collect::<ObjectMap>())); Value::object(m) }"),
|
|
975
974
|
_ => None,
|
|
976
975
|
},
|
|
977
976
|
"tish:ws" if self.has_feature("ws") => match export_name {
|
|
@@ -1226,7 +1225,7 @@ impl Codegen {
|
|
|
1226
1225
|
self.write("use std::cell::RefCell;\n");
|
|
1227
1226
|
self.write("use std::rc::Rc;\n");
|
|
1228
1227
|
self.write("use std::sync::Arc;\n");
|
|
1229
|
-
self.write("use tishlang_runtime::{console_debug as tish_console_debug, console_info as tish_console_info, console_log as tish_console_log, console_warn as tish_console_warn, console_error as tish_console_error, boolean as tish_boolean, decode_uri as tish_decode_uri, encode_uri as tish_encode_uri, string_escape_html_impl as tish_escape_html, in_operator as tish_in_operator, is_finite as tish_is_finite, is_nan as tish_is_nan, json_parse as tish_json_parse, json_stringify as tish_json_stringify, math_abs as tish_math_abs, math_ceil as tish_math_ceil, math_floor as tish_math_floor, math_max as tish_math_max, math_min as tish_math_min, math_round as tish_math_round, math_sqrt as tish_math_sqrt, parse_float as tish_parse_float, parse_int as tish_parse_int, math_random as tish_math_random, math_pow as tish_math_pow, math_sin as tish_math_sin, math_cos as tish_math_cos, math_tan as tish_math_tan, math_log as tish_math_log, math_exp as tish_math_exp, math_sign as tish_math_sign, math_trunc as tish_math_trunc, date_now as tish_date_now, array_is_array as tish_array_is_array, string_from_char_code as tish_string_from_char_code, object_assign as tish_object_assign, object_keys as tish_object_keys, object_values as tish_object_values, object_entries as tish_object_entries, object_from_entries as tish_object_from_entries, tish_construct, tish_uint8_array_constructor, tish_audio_context_constructor, register_static_route as tish_register_static_route, ObjectMap, TishError, Value, VmRef};\n");
|
|
1228
|
+
self.write("use tishlang_runtime::{console_debug as tish_console_debug, console_info as tish_console_info, console_log as tish_console_log, console_warn as tish_console_warn, console_error as tish_console_error, boolean as tish_boolean, decode_uri as tish_decode_uri, encode_uri as tish_encode_uri, string_escape_html_impl as tish_escape_html, in_operator as tish_in_operator, is_finite as tish_is_finite, is_nan as tish_is_nan, json_parse as tish_json_parse, json_stringify as tish_json_stringify, math_abs as tish_math_abs, math_ceil as tish_math_ceil, math_floor as tish_math_floor, math_max as tish_math_max, math_min as tish_math_min, math_round as tish_math_round, math_sqrt as tish_math_sqrt, parse_float as tish_parse_float, parse_int as tish_parse_int, math_random as tish_math_random, math_pow as tish_math_pow, math_sin as tish_math_sin, math_cos as tish_math_cos, math_tan as tish_math_tan, math_log as tish_math_log, math_exp as tish_math_exp, math_sign as tish_math_sign, math_trunc as tish_math_trunc, date_now as tish_date_now, array_is_array as tish_array_is_array, string_from_char_code as tish_string_from_char_code, object_assign as tish_object_assign, object_keys as tish_object_keys, object_values as tish_object_values, object_entries as tish_object_entries, object_from_entries as tish_object_from_entries, symbol_object as tish_symbol_object, tish_construct, tish_uint8_array_constructor, tish_audio_context_constructor, register_static_route as tish_register_static_route, ObjectMap, TishError, Value, VmRef};\n");
|
|
1230
1229
|
if self.program_has_jsx {
|
|
1231
1230
|
self.write("use tishlang_ui::{fragment_value, install_thread_local_host, native_create_root, native_use_state, ui_h, ui_text, HeadlessHost};\n");
|
|
1232
1231
|
}
|
|
@@ -1295,7 +1294,7 @@ impl Codegen {
|
|
|
1295
1294
|
self.indent += 1;
|
|
1296
1295
|
|
|
1297
1296
|
// Initialize builtins
|
|
1298
|
-
self.writeln("let mut console = Value::
|
|
1297
|
+
self.writeln("let mut console = Value::object(ObjectMap::from([");
|
|
1299
1298
|
self.indent += 1;
|
|
1300
1299
|
self.writeln("(Arc::from(\"debug\"), Value::native(|args: &[Value]| { tish_console_debug(args); Value::Null })),");
|
|
1301
1300
|
self.writeln("(Arc::from(\"info\"), Value::native(|args: &[Value]| { tish_console_info(args); Value::Null })),");
|
|
@@ -1303,147 +1302,145 @@ impl Codegen {
|
|
|
1303
1302
|
self.writeln("(Arc::from(\"warn\"), Value::native(|args: &[Value]| { tish_console_warn(args); Value::Null })),");
|
|
1304
1303
|
self.writeln("(Arc::from(\"error\"), Value::native(|args: &[Value]| { tish_console_error(args); Value::Null })),");
|
|
1305
1304
|
self.indent -= 1;
|
|
1306
|
-
self.writeln("]))
|
|
1307
|
-
self.writeln(
|
|
1308
|
-
|
|
1309
|
-
);
|
|
1310
|
-
self.writeln(
|
|
1311
|
-
|
|
1312
|
-
);
|
|
1313
|
-
self.writeln(
|
|
1314
|
-
"let parseFloat = Value::native(|args: &[Value]| tish_parse_float(args));",
|
|
1315
|
-
);
|
|
1316
|
-
self.writeln(
|
|
1317
|
-
"let decodeURI = Value::native(|args: &[Value]| tish_decode_uri(args));",
|
|
1318
|
-
);
|
|
1319
|
-
self.writeln(
|
|
1320
|
-
"let encodeURI = Value::native(|args: &[Value]| tish_encode_uri(args));",
|
|
1321
|
-
);
|
|
1305
|
+
self.writeln("]));");
|
|
1306
|
+
self.writeln("let Boolean = Value::native(|args: &[Value]| tish_boolean(args));");
|
|
1307
|
+
self.writeln("let parseInt = Value::native(|args: &[Value]| tish_parse_int(args));");
|
|
1308
|
+
self.writeln("let parseFloat = Value::native(|args: &[Value]| tish_parse_float(args));");
|
|
1309
|
+
self.writeln("let decodeURI = Value::native(|args: &[Value]| tish_decode_uri(args));");
|
|
1310
|
+
self.writeln("let encodeURI = Value::native(|args: &[Value]| tish_encode_uri(args));");
|
|
1322
1311
|
self.writeln(
|
|
1323
1312
|
r#"let registerStaticRoute = Value::native(|args: &[Value]| { let path = match args.get(0) { Some(Value::String(s)) => s.to_string(), _ => return Value::Null }; let body = match args.get(1) { Some(Value::String(s)) => s.as_bytes().to_vec(), _ => return Value::Null }; let ct = match args.get(2) { Some(Value::String(s)) => s.to_string(), _ => "application/octet-stream".to_string() }; tish_register_static_route(&path, &body, &ct); Value::Null });"#,
|
|
1324
1313
|
);
|
|
1325
1314
|
self.writeln(
|
|
1326
1315
|
"let htmlEscape = Value::native(|args: &[Value]| tish_escape_html(args.first().unwrap_or(&Value::Null)));",
|
|
1327
1316
|
);
|
|
1328
|
-
self.writeln(
|
|
1329
|
-
"let isFinite = Value::native(|args: &[Value]| tish_is_finite(args));",
|
|
1330
|
-
);
|
|
1317
|
+
self.writeln("let isFinite = Value::native(|args: &[Value]| tish_is_finite(args));");
|
|
1331
1318
|
self.writeln("let isNaN = Value::native(|args: &[Value]| tish_is_nan(args));");
|
|
1332
1319
|
self.writeln("let Infinity = Value::Number(f64::INFINITY);");
|
|
1333
1320
|
self.writeln("let NaN = Value::Number(f64::NAN);");
|
|
1334
|
-
self.writeln("let Math = Value::
|
|
1321
|
+
self.writeln("let Math = Value::object(ObjectMap::from([");
|
|
1335
1322
|
self.indent += 1;
|
|
1323
|
+
self.writeln("(Arc::from(\"abs\"), Value::native(|args: &[Value]| tish_math_abs(args))),");
|
|
1336
1324
|
self.writeln(
|
|
1337
|
-
"(Arc::from(\"
|
|
1338
|
-
);
|
|
1339
|
-
self.writeln("(Arc::from(\"sqrt\"), Value::native(|args: &[Value]| tish_math_sqrt(args))),");
|
|
1340
|
-
self.writeln(
|
|
1341
|
-
"(Arc::from(\"min\"), Value::native(|args: &[Value]| tish_math_min(args))),",
|
|
1325
|
+
"(Arc::from(\"sqrt\"), Value::native(|args: &[Value]| tish_math_sqrt(args))),",
|
|
1342
1326
|
);
|
|
1327
|
+
self.writeln("(Arc::from(\"min\"), Value::native(|args: &[Value]| tish_math_min(args))),");
|
|
1328
|
+
self.writeln("(Arc::from(\"max\"), Value::native(|args: &[Value]| tish_math_max(args))),");
|
|
1343
1329
|
self.writeln(
|
|
1344
|
-
"(Arc::from(\"
|
|
1330
|
+
"(Arc::from(\"floor\"), Value::native(|args: &[Value]| tish_math_floor(args))),",
|
|
1345
1331
|
);
|
|
1346
|
-
self.writeln("(Arc::from(\"floor\"), Value::native(|args: &[Value]| tish_math_floor(args))),");
|
|
1347
|
-
self.writeln("(Arc::from(\"ceil\"), Value::native(|args: &[Value]| tish_math_ceil(args))),");
|
|
1348
|
-
self.writeln("(Arc::from(\"round\"), Value::native(|args: &[Value]| tish_math_round(args))),");
|
|
1349
|
-
self.writeln("(Arc::from(\"random\"), Value::native(|args: &[Value]| tish_math_random(args))),");
|
|
1350
1332
|
self.writeln(
|
|
1351
|
-
"(Arc::from(\"
|
|
1333
|
+
"(Arc::from(\"ceil\"), Value::native(|args: &[Value]| tish_math_ceil(args))),",
|
|
1352
1334
|
);
|
|
1353
1335
|
self.writeln(
|
|
1354
|
-
"(Arc::from(\"
|
|
1336
|
+
"(Arc::from(\"round\"), Value::native(|args: &[Value]| tish_math_round(args))),",
|
|
1355
1337
|
);
|
|
1356
1338
|
self.writeln(
|
|
1357
|
-
"(Arc::from(\"
|
|
1339
|
+
"(Arc::from(\"random\"), Value::native(|args: &[Value]| tish_math_random(args))),",
|
|
1358
1340
|
);
|
|
1341
|
+
self.writeln("(Arc::from(\"pow\"), Value::native(|args: &[Value]| tish_math_pow(args))),");
|
|
1342
|
+
self.writeln("(Arc::from(\"sin\"), Value::native(|args: &[Value]| tish_math_sin(args))),");
|
|
1343
|
+
self.writeln("(Arc::from(\"cos\"), Value::native(|args: &[Value]| tish_math_cos(args))),");
|
|
1344
|
+
self.writeln("(Arc::from(\"tan\"), Value::native(|args: &[Value]| tish_math_tan(args))),");
|
|
1345
|
+
self.writeln("(Arc::from(\"log\"), Value::native(|args: &[Value]| tish_math_log(args))),");
|
|
1346
|
+
self.writeln("(Arc::from(\"exp\"), Value::native(|args: &[Value]| tish_math_exp(args))),");
|
|
1359
1347
|
self.writeln(
|
|
1360
|
-
"(Arc::from(\"
|
|
1348
|
+
"(Arc::from(\"sign\"), Value::native(|args: &[Value]| tish_math_sign(args))),",
|
|
1361
1349
|
);
|
|
1362
1350
|
self.writeln(
|
|
1363
|
-
"(Arc::from(\"
|
|
1351
|
+
"(Arc::from(\"trunc\"), Value::native(|args: &[Value]| tish_math_trunc(args))),",
|
|
1364
1352
|
);
|
|
1365
|
-
self.writeln(
|
|
1366
|
-
"(Arc::from(\"exp\"), Value::native(|args: &[Value]| tish_math_exp(args))),",
|
|
1367
|
-
);
|
|
1368
|
-
self.writeln("(Arc::from(\"sign\"), Value::native(|args: &[Value]| tish_math_sign(args))),");
|
|
1369
|
-
self.writeln("(Arc::from(\"trunc\"), Value::native(|args: &[Value]| tish_math_trunc(args))),");
|
|
1370
1353
|
self.writeln("(Arc::from(\"PI\"), Value::Number(std::f64::consts::PI)),");
|
|
1371
1354
|
self.writeln("(Arc::from(\"E\"), Value::Number(std::f64::consts::E)),");
|
|
1372
1355
|
self.indent -= 1;
|
|
1373
|
-
self.writeln("]))
|
|
1374
|
-
self.writeln("let JSON = Value::
|
|
1356
|
+
self.writeln("]));");
|
|
1357
|
+
self.writeln("let JSON = Value::object(ObjectMap::from([");
|
|
1375
1358
|
self.indent += 1;
|
|
1376
|
-
self.writeln(
|
|
1359
|
+
self.writeln(
|
|
1360
|
+
"(Arc::from(\"parse\"), Value::native(|args: &[Value]| tish_json_parse(args))),",
|
|
1361
|
+
);
|
|
1377
1362
|
self.writeln("(Arc::from(\"stringify\"), Value::native(|args: &[Value]| tish_json_stringify(args))),");
|
|
1378
1363
|
self.indent -= 1;
|
|
1379
|
-
self.writeln("]))
|
|
1364
|
+
self.writeln("]));");
|
|
1380
1365
|
|
|
1381
|
-
self.writeln("let Array = Value::
|
|
1366
|
+
self.writeln("let Array = Value::object(ObjectMap::from([");
|
|
1382
1367
|
self.indent += 1;
|
|
1383
|
-
self.writeln(
|
|
1368
|
+
self.writeln(
|
|
1369
|
+
"(Arc::from(\"isArray\"), Value::native(|args: &[Value]| tish_array_is_array(args))),",
|
|
1370
|
+
);
|
|
1384
1371
|
self.indent -= 1;
|
|
1385
|
-
self.writeln("]))
|
|
1372
|
+
self.writeln("]));");
|
|
1386
1373
|
|
|
1387
|
-
self.writeln("let String = Value::
|
|
1374
|
+
self.writeln("let String = Value::object(ObjectMap::from([");
|
|
1388
1375
|
self.indent += 1;
|
|
1389
1376
|
self.writeln("(Arc::from(\"fromCharCode\"), Value::native(|args: &[Value]| tish_string_from_char_code(args))),");
|
|
1390
1377
|
self.indent -= 1;
|
|
1391
|
-
self.writeln("]))
|
|
1378
|
+
self.writeln("]));");
|
|
1392
1379
|
|
|
1393
|
-
self.writeln("let Date = Value::
|
|
1380
|
+
self.writeln("let Date = Value::object(ObjectMap::from([");
|
|
1394
1381
|
self.indent += 1;
|
|
1395
|
-
self.writeln(
|
|
1396
|
-
"(Arc::from(\"now\"), Value::native(|args: &[Value]| tish_date_now(args))),",
|
|
1397
|
-
);
|
|
1382
|
+
self.writeln("(Arc::from(\"now\"), Value::native(|args: &[Value]| tish_date_now(args))),");
|
|
1398
1383
|
self.indent -= 1;
|
|
1399
|
-
self.writeln("]))
|
|
1384
|
+
self.writeln("]));");
|
|
1400
1385
|
|
|
1401
|
-
self.writeln("let
|
|
1386
|
+
self.writeln("let Symbol = tish_symbol_object();");
|
|
1387
|
+
|
|
1388
|
+
self.writeln("let Object = Value::object(ObjectMap::from([");
|
|
1402
1389
|
self.indent += 1;
|
|
1403
|
-
self.writeln(
|
|
1404
|
-
|
|
1405
|
-
|
|
1406
|
-
self.writeln(
|
|
1390
|
+
self.writeln(
|
|
1391
|
+
"(Arc::from(\"assign\"), Value::native(|args: &[Value]| tish_object_assign(args))),",
|
|
1392
|
+
);
|
|
1393
|
+
self.writeln(
|
|
1394
|
+
"(Arc::from(\"keys\"), Value::native(|args: &[Value]| tish_object_keys(args))),",
|
|
1395
|
+
);
|
|
1396
|
+
self.writeln(
|
|
1397
|
+
"(Arc::from(\"values\"), Value::native(|args: &[Value]| tish_object_values(args))),",
|
|
1398
|
+
);
|
|
1399
|
+
self.writeln(
|
|
1400
|
+
"(Arc::from(\"entries\"), Value::native(|args: &[Value]| tish_object_entries(args))),",
|
|
1401
|
+
);
|
|
1407
1402
|
self.writeln("(Arc::from(\"fromEntries\"), Value::native(|args: &[Value]| tish_object_from_entries(args))),");
|
|
1408
1403
|
self.indent -= 1;
|
|
1409
|
-
self.writeln("]))
|
|
1404
|
+
self.writeln("]));");
|
|
1410
1405
|
|
|
1411
1406
|
self.writeln("let Uint8Array = tish_uint8_array_constructor();");
|
|
1412
1407
|
self.writeln("let AudioContext = tish_audio_context_constructor();");
|
|
1413
1408
|
|
|
1414
1409
|
if self.has_feature("process") {
|
|
1415
|
-
self.writeln("let process = Value::
|
|
1410
|
+
self.writeln("let process = Value::object({");
|
|
1416
1411
|
self.indent += 1;
|
|
1417
1412
|
self.writeln("let mut p = ObjectMap::default();");
|
|
1418
1413
|
self.writeln("p.insert(Arc::from(\"exit\"), Value::native(|args: &[Value]| tish_process_exit(args)));");
|
|
1419
1414
|
self.writeln("p.insert(Arc::from(\"cwd\"), Value::native(|args: &[Value]| tish_process_cwd(args)));");
|
|
1420
1415
|
self.writeln("p.insert(Arc::from(\"exec\"), Value::native(|args: &[Value]| tish_process_exec(args)));");
|
|
1421
1416
|
self.writeln("let argv: Vec<Value> = std::env::args().map(|s| Value::String(s.into())).collect();");
|
|
1422
|
-
self.writeln(
|
|
1423
|
-
"p.insert(Arc::from(\"argv\"), Value::Array(VmRef::new(argv)));",
|
|
1424
|
-
);
|
|
1417
|
+
self.writeln("p.insert(Arc::from(\"argv\"), Value::Array(VmRef::new(argv)));");
|
|
1425
1418
|
self.writeln("let mut env_obj = ObjectMap::default();");
|
|
1426
1419
|
self.writeln("for (key, value) in std::env::vars() {");
|
|
1427
1420
|
self.indent += 1;
|
|
1428
1421
|
self.writeln("env_obj.insert(Arc::from(key.as_str()), Value::String(value.into()));");
|
|
1429
1422
|
self.indent -= 1;
|
|
1430
1423
|
self.writeln("}");
|
|
1431
|
-
self.writeln(
|
|
1432
|
-
"p.insert(Arc::from(\"env\"), Value::Object(VmRef::new(env_obj)));",
|
|
1433
|
-
);
|
|
1424
|
+
self.writeln("p.insert(Arc::from(\"env\"), Value::object(env_obj));");
|
|
1434
1425
|
self.writeln("p");
|
|
1435
1426
|
self.indent -= 1;
|
|
1436
|
-
self.writeln("})
|
|
1427
|
+
self.writeln("});");
|
|
1437
1428
|
}
|
|
1438
1429
|
|
|
1439
1430
|
if self.has_feature("timers") {
|
|
1440
|
-
self.writeln(
|
|
1431
|
+
self.writeln(
|
|
1432
|
+
"let setTimeout = Value::native(|args: &[Value]| tish_timer_set_timeout(args));",
|
|
1433
|
+
);
|
|
1441
1434
|
self.writeln("let clearTimeout = Value::native(|args: &[Value]| tish_timer_clear_timeout(args));");
|
|
1442
|
-
self.writeln(
|
|
1435
|
+
self.writeln(
|
|
1436
|
+
"let setInterval = Value::native(|args: &[Value]| tish_timer_set_interval(args));",
|
|
1437
|
+
);
|
|
1443
1438
|
self.writeln("let clearInterval = Value::native(|args: &[Value]| tish_timer_clear_interval(args));");
|
|
1444
1439
|
}
|
|
1445
1440
|
if self.has_feature("http") {
|
|
1446
|
-
self.writeln(
|
|
1441
|
+
self.writeln(
|
|
1442
|
+
"let fetch = Value::native(|args: &[Value]| tish_fetch_promise(args.to_vec()));",
|
|
1443
|
+
);
|
|
1447
1444
|
self.writeln("let fetchAll = Value::native(|args: &[Value]| tish_fetch_all_promise(args.to_vec()));");
|
|
1448
1445
|
if self.is_async {
|
|
1449
1446
|
self.writeln("let Promise = tish_promise_object();");
|
|
@@ -1461,10 +1458,12 @@ impl Codegen {
|
|
|
1461
1458
|
self.writeln("let handler = args.get(1).cloned().unwrap_or(Value::Null);");
|
|
1462
1459
|
self.writeln("match handler {");
|
|
1463
1460
|
self.indent += 1;
|
|
1464
|
-
self.writeln(
|
|
1461
|
+
self.writeln(
|
|
1462
|
+
"Value::Function(f) => tish_http_serve(args, move |req_args| f(req_args)),",
|
|
1463
|
+
);
|
|
1465
1464
|
self.writeln("Value::Object(ref opts) => {");
|
|
1466
1465
|
self.indent += 1;
|
|
1467
|
-
self.writeln("let factory = opts.borrow().get(
|
|
1466
|
+
self.writeln("let factory = opts.borrow().strings.get(\"onWorker\").cloned().unwrap_or(Value::Null);");
|
|
1468
1467
|
self.writeln("tishlang_runtime::http_serve_per_worker(args, factory)");
|
|
1469
1468
|
self.indent -= 1;
|
|
1470
1469
|
self.writeln("},");
|
|
@@ -1476,28 +1475,18 @@ impl Codegen {
|
|
|
1476
1475
|
}
|
|
1477
1476
|
|
|
1478
1477
|
if self.has_feature("fs") {
|
|
1478
|
+
self.writeln("let readFile = Value::native(|args: &[Value]| tish_read_file(args));");
|
|
1479
|
+
self.writeln("let writeFile = Value::native(|args: &[Value]| tish_write_file(args));");
|
|
1479
1480
|
self.writeln(
|
|
1480
|
-
"let
|
|
1481
|
-
);
|
|
1482
|
-
self.writeln(
|
|
1483
|
-
"let writeFile = Value::native(|args: &[Value]| tish_write_file(args));",
|
|
1484
|
-
);
|
|
1485
|
-
self.writeln("let fileExists = Value::native(|args: &[Value]| tish_file_exists(args));");
|
|
1486
|
-
self.writeln(
|
|
1487
|
-
"let isDir = Value::native(|args: &[Value]| tish_is_dir(args));",
|
|
1488
|
-
);
|
|
1489
|
-
self.writeln(
|
|
1490
|
-
"let readDir = Value::native(|args: &[Value]| tish_read_dir(args));",
|
|
1491
|
-
);
|
|
1492
|
-
self.writeln(
|
|
1493
|
-
"let mkdir = Value::native(|args: &[Value]| tish_mkdir(args));",
|
|
1481
|
+
"let fileExists = Value::native(|args: &[Value]| tish_file_exists(args));",
|
|
1494
1482
|
);
|
|
1483
|
+
self.writeln("let isDir = Value::native(|args: &[Value]| tish_is_dir(args));");
|
|
1484
|
+
self.writeln("let readDir = Value::native(|args: &[Value]| tish_read_dir(args));");
|
|
1485
|
+
self.writeln("let mkdir = Value::native(|args: &[Value]| tish_mkdir(args));");
|
|
1495
1486
|
}
|
|
1496
1487
|
|
|
1497
1488
|
if self.has_feature("regex") {
|
|
1498
|
-
self.writeln(
|
|
1499
|
-
"let RegExp = Value::native(|args: &[Value]| regexp_new(args));",
|
|
1500
|
-
);
|
|
1489
|
+
self.writeln("let RegExp = Value::native(|args: &[Value]| regexp_new(args));");
|
|
1501
1490
|
}
|
|
1502
1491
|
|
|
1503
1492
|
if self.program_has_jsx {
|
|
@@ -1505,10 +1494,10 @@ impl Codegen {
|
|
|
1505
1494
|
self.writeln("let Fragment = fragment_value();");
|
|
1506
1495
|
self.writeln("let h = Value::native(|args: &[Value]| ui_h(args));");
|
|
1507
1496
|
self.writeln("let text = Value::native(|args: &[Value]| ui_text(args));");
|
|
1497
|
+
self.writeln("let useState = Value::native(|args: &[Value]| native_use_state(args));");
|
|
1508
1498
|
self.writeln(
|
|
1509
|
-
"let
|
|
1499
|
+
"let createRoot = Value::native(|args: &[Value]| native_create_root(args));",
|
|
1510
1500
|
);
|
|
1511
|
-
self.writeln("let createRoot = Value::native(|args: &[Value]| native_create_root(args));");
|
|
1512
1501
|
}
|
|
1513
1502
|
|
|
1514
1503
|
// Polars, Egui etc. are emitted via VarDecl from import { X } from 'tish:...'
|
|
@@ -1622,10 +1611,7 @@ impl Codegen {
|
|
|
1622
1611
|
};
|
|
1623
1612
|
if self.refcell_wrapped_vars.contains(name.as_ref()) {
|
|
1624
1613
|
// Closure-mutated: same Rc<RefCell<T>> pattern as Value (assignments use borrow_mut)
|
|
1625
|
-
self.writeln(&format!(
|
|
1626
|
-
"let {} = VmRef::new({});",
|
|
1627
|
-
escaped_name, expr_str
|
|
1628
|
-
));
|
|
1614
|
+
self.writeln(&format!("let {} = VmRef::new({});", escaped_name, expr_str));
|
|
1629
1615
|
self.rc_cell_storage_define(name.as_ref());
|
|
1630
1616
|
} else {
|
|
1631
1617
|
let type_str = rust_type.to_rust_type_str();
|
|
@@ -1653,10 +1639,7 @@ impl Codegen {
|
|
|
1653
1639
|
} else {
|
|
1654
1640
|
expr_str.to_string()
|
|
1655
1641
|
};
|
|
1656
|
-
self.writeln(&format!(
|
|
1657
|
-
"let {} = VmRef::new({});",
|
|
1658
|
-
escaped_name, init_val
|
|
1659
|
-
));
|
|
1642
|
+
self.writeln(&format!("let {} = VmRef::new({});", escaped_name, init_val));
|
|
1660
1643
|
self.rc_cell_storage_define(name.as_ref());
|
|
1661
1644
|
} else if clone_needed {
|
|
1662
1645
|
self.writeln(&format!(
|
|
@@ -2036,6 +2019,7 @@ impl Codegen {
|
|
|
2036
2019
|
"setInterval",
|
|
2037
2020
|
"clearInterval",
|
|
2038
2021
|
"Promise",
|
|
2022
|
+
"Symbol",
|
|
2039
2023
|
"RegExp",
|
|
2040
2024
|
"Polars",
|
|
2041
2025
|
]
|
|
@@ -2136,6 +2120,7 @@ impl Codegen {
|
|
|
2136
2120
|
"setInterval",
|
|
2137
2121
|
"clearInterval",
|
|
2138
2122
|
"Promise",
|
|
2123
|
+
"Symbol",
|
|
2139
2124
|
"RegExp",
|
|
2140
2125
|
"Polars",
|
|
2141
2126
|
// Free-standing global functions used inside user-defined
|
|
@@ -2409,7 +2394,7 @@ impl Codegen {
|
|
|
2409
2394
|
match &prop.value {
|
|
2410
2395
|
DestructElement::Ident(name, _) => {
|
|
2411
2396
|
self.writeln(&format!(
|
|
2412
|
-
"{} {} = match &({}) {{ Value::Object(ref _o) => _o.borrow().get({:?}).cloned().unwrap_or(Value::Null), _ => Value::Null }};",
|
|
2397
|
+
"{} {} = match &({}) {{ Value::Object(ref _o) => _o.borrow().strings.get({:?}).cloned().unwrap_or(Value::Null), _ => Value::Null }};",
|
|
2413
2398
|
mutability,
|
|
2414
2399
|
Self::escape_ident(name.as_ref()),
|
|
2415
2400
|
value_expr,
|
|
@@ -2419,7 +2404,7 @@ impl Codegen {
|
|
|
2419
2404
|
DestructElement::Pattern(nested) => {
|
|
2420
2405
|
let nested_var = format!("_nested_obj_{}", key);
|
|
2421
2406
|
self.writeln(&format!(
|
|
2422
|
-
"let {} = match &({}) {{ Value::Object(ref _o) => _o.borrow().get({:?}).cloned().unwrap_or(Value::Null), _ => Value::Null }};",
|
|
2407
|
+
"let {} = match &({}) {{ Value::Object(ref _o) => _o.borrow().strings.get({:?}).cloned().unwrap_or(Value::Null), _ => Value::Null }};",
|
|
2423
2408
|
nested_var, value_expr, key
|
|
2424
2409
|
));
|
|
2425
2410
|
self.emit_destruct_bindings(nested, &nested_var, mutability, span)?;
|
|
@@ -2980,7 +2965,7 @@ impl Codegen {
|
|
|
2980
2965
|
if has_spread {
|
|
2981
2966
|
let args_code = self.emit_call_args(args)?;
|
|
2982
2967
|
return Ok(format!(
|
|
2983
|
-
"{{ let _callee =
|
|
2968
|
+
"{{ let _callee = ({}).clone(); let _spread_args = {}; tishlang_runtime::value_call(&_callee, _spread_args.as_slice()) }}",
|
|
2984
2969
|
callee_expr, args_code
|
|
2985
2970
|
));
|
|
2986
2971
|
}
|
|
@@ -2994,8 +2979,8 @@ impl Codegen {
|
|
|
2994
2979
|
.join(", ");
|
|
2995
2980
|
format!(
|
|
2996
2981
|
"({{\n\
|
|
2997
|
-
{} let _callee =
|
|
2998
|
-
{}
|
|
2982
|
+
{} let _callee = ({}).clone();\n\
|
|
2983
|
+
{} tishlang_runtime::value_call(&_callee, &[{}])\n\
|
|
2999
2984
|
{}}})",
|
|
3000
2985
|
" ".repeat(self.indent),
|
|
3001
2986
|
callee_expr,
|
|
@@ -3160,11 +3145,11 @@ impl Codegen {
|
|
|
3160
3145
|
}
|
|
3161
3146
|
ObjectProp::Spread(e) => {
|
|
3162
3147
|
let val = self.emit_expr(e)?;
|
|
3163
|
-
parts.push(format!("if let Value::Object(ref _spread) = {} {{ for (k, v) in _spread.borrow().iter() {{ _obj.insert(Arc::clone(k), v.clone()); }} }}", val));
|
|
3148
|
+
parts.push(format!("if let Value::Object(ref _spread) = {} {{ for (k, v) in _spread.borrow().strings.iter() {{ _obj.insert(Arc::clone(k), v.clone()); }} }}", val));
|
|
3164
3149
|
}
|
|
3165
3150
|
}
|
|
3166
3151
|
}
|
|
3167
|
-
format!("{{ let mut _obj: ObjectMap = ObjectMap::default(); {} Value::
|
|
3152
|
+
format!("{{ let mut _obj: ObjectMap = ObjectMap::default(); {} Value::object(_obj) }}", parts.join(" "))
|
|
3168
3153
|
} else {
|
|
3169
3154
|
let mut parts = Vec::new();
|
|
3170
3155
|
for prop in props {
|
|
@@ -3178,7 +3163,7 @@ impl Codegen {
|
|
|
3178
3163
|
}
|
|
3179
3164
|
}
|
|
3180
3165
|
format!(
|
|
3181
|
-
"Value::
|
|
3166
|
+
"Value::object(ObjectMap::from([{}]))",
|
|
3182
3167
|
parts.join(", ")
|
|
3183
3168
|
)
|
|
3184
3169
|
}
|
|
@@ -3274,7 +3259,8 @@ impl Codegen {
|
|
|
3274
3259
|
Value::Number(_) => \"number\".into(), Value::String(_) => \"string\".into(), \
|
|
3275
3260
|
Value::Bool(_) => \"boolean\".into(), Value::Null => \"null\".into(), \
|
|
3276
3261
|
Value::Array(_) => \"object\".into(), Value::Object(_) => \"object\".into(), \
|
|
3277
|
-
Value::Function(_) => \"function\".into(), _ => \"
|
|
3262
|
+
Value::Function(_) => \"function\".into(), Value::Symbol(_) => \"symbol\".into(), \
|
|
3263
|
+
_ => \"object\".into() }})",
|
|
3278
3264
|
o
|
|
3279
3265
|
)
|
|
3280
3266
|
}
|
|
@@ -4606,6 +4592,7 @@ impl Codegen {
|
|
|
4606
4592
|
"setInterval",
|
|
4607
4593
|
"clearInterval",
|
|
4608
4594
|
"Promise",
|
|
4595
|
+
"Symbol",
|
|
4609
4596
|
"RegExp",
|
|
4610
4597
|
"Polars",
|
|
4611
4598
|
]
|
|
@@ -4679,6 +4666,7 @@ impl Codegen {
|
|
|
4679
4666
|
"setInterval",
|
|
4680
4667
|
"clearInterval",
|
|
4681
4668
|
"Promise",
|
|
4669
|
+
"Symbol",
|
|
4682
4670
|
"RegExp",
|
|
4683
4671
|
"Polars",
|
|
4684
4672
|
] {
|
|
@@ -4886,14 +4874,11 @@ impl Codegen {
|
|
|
4886
4874
|
// alias). Each property in source order is matched to a struct
|
|
4887
4875
|
// field; missing fields fall back to `default_value()` so the
|
|
4888
4876
|
// emit succeeds even on partial literals (rare, but harmless).
|
|
4889
|
-
if let (RustType::Named { name, fields }, Expr::Object { props, .. }) =
|
|
4890
|
-
(target_type, expr)
|
|
4877
|
+
if let (RustType::Named { name, fields }, Expr::Object { props, .. }) = (target_type, expr)
|
|
4891
4878
|
{
|
|
4892
4879
|
use std::collections::HashMap;
|
|
4893
|
-
let field_types: HashMap<&str, &RustType> =
|
|
4894
|
-
.iter()
|
|
4895
|
-
.map(|(k, t)| (k.as_ref(), t))
|
|
4896
|
-
.collect();
|
|
4880
|
+
let field_types: HashMap<&str, &RustType> =
|
|
4881
|
+
fields.iter().map(|(k, t)| (k.as_ref(), t)).collect();
|
|
4897
4882
|
let mut field_inits: HashMap<String, String> = HashMap::new();
|
|
4898
4883
|
let mut bail = false;
|
|
4899
4884
|
for prop in props {
|
|
@@ -17,9 +17,9 @@ pub use resolve::{
|
|
|
17
17
|
extract_native_import_features, format_rust_dependencies_toml, generate_native_wrapper_rs,
|
|
18
18
|
has_external_native_imports, has_native_imports, infer_native_module_exports,
|
|
19
19
|
is_builtin_native_spec, is_cargo_native_spec, is_native_import, merge_modules,
|
|
20
|
-
normalize_builtin_spec, read_project_tish_config,
|
|
21
|
-
|
|
22
|
-
|
|
20
|
+
normalize_builtin_spec, read_project_tish_config, resolve_bare_spec, resolve_native_modules,
|
|
21
|
+
resolve_project, resolve_project_from_stdin, MergedProgram, NativeBuildArtifacts,
|
|
22
|
+
NativeModuleInit, ResolvedNativeModule,
|
|
23
23
|
};
|
|
24
24
|
pub use types::{RustType, TypeContext};
|
|
25
25
|
|
|
@@ -106,6 +106,28 @@ fn factory() {
|
|
|
106
106
|
);
|
|
107
107
|
}
|
|
108
108
|
|
|
109
|
+
/// `value_call` must take `&Value` to a **local** (`let _callee = (<expr>).clone(); … &_callee`):
|
|
110
|
+
/// `&<temporary>` can dangle in release, and `let _callee = <ident>` would move globals like `Symbol`.
|
|
111
|
+
#[test]
|
|
112
|
+
fn native_emit_value_call_materializes_callee() {
|
|
113
|
+
use std::path::PathBuf;
|
|
114
|
+
let manifest = PathBuf::from(env!("CARGO_MANIFEST_DIR"));
|
|
115
|
+
let path = manifest.join("../../tests/core/symbol.tish").canonicalize().unwrap();
|
|
116
|
+
let (rust, _, _, _) = compile_project_full(&path, path.parent(), &[], true).unwrap();
|
|
117
|
+
assert!(
|
|
118
|
+
rust.contains("let _callee = (tishlang_runtime::get_index"),
|
|
119
|
+
"fixture should bracket-call via get_index with callee stored in a local"
|
|
120
|
+
);
|
|
121
|
+
assert!(
|
|
122
|
+
!rust.contains("let _callee = &tishlang_runtime::get_index"),
|
|
123
|
+
"expected callee materialization, found reference-to-temporary pattern"
|
|
124
|
+
);
|
|
125
|
+
assert!(
|
|
126
|
+
rust.contains("tishlang_runtime::value_call"),
|
|
127
|
+
"expected value_call via runtime re-export for nested Cargo builds"
|
|
128
|
+
);
|
|
129
|
+
}
|
|
130
|
+
|
|
109
131
|
#[test]
|
|
110
132
|
fn loop_var_decl_clone_via_project_full() {
|
|
111
133
|
// With the inference pass, `let outerVar = 42` is inferred as f64 (Copy) — no clone needed.
|
|
@@ -67,8 +67,10 @@ pub fn normalize_builtin_spec(spec: &str) -> Option<String> {
|
|
|
67
67
|
|
|
68
68
|
/// Built-in modules that come from tishlang_runtime, not from package.json.
|
|
69
69
|
pub fn is_builtin_native_spec(spec: &str) -> bool {
|
|
70
|
-
matches!(
|
|
71
|
-
|
|
70
|
+
matches!(
|
|
71
|
+
spec,
|
|
72
|
+
"tish:fs" | "tish:http" | "tish:timers" | "tish:process" | "tish:ws"
|
|
73
|
+
) || matches!(spec, "fs" | "http" | "timers" | "process" | "ws")
|
|
72
74
|
}
|
|
73
75
|
|
|
74
76
|
/// Resolve all native imports in a merged program via package.json lookup.
|
|
@@ -774,7 +776,8 @@ fn resolve_package_root_to_entry(pkg_root: &Path, spec: &str) -> Option<PathBuf>
|
|
|
774
776
|
pub fn resolve_bare_spec(spec: &str, from_dir: &Path, _project_root: &Path) -> Option<PathBuf> {
|
|
775
777
|
let mut search = from_dir.to_path_buf();
|
|
776
778
|
loop {
|
|
777
|
-
if let Some(p) =
|
|
779
|
+
if let Some(p) =
|
|
780
|
+
resolve_package_root_to_entry(&search.join("node_modules").join(spec), spec)
|
|
778
781
|
{
|
|
779
782
|
return Some(p);
|
|
780
783
|
}
|
|
@@ -83,9 +83,9 @@ impl RustType {
|
|
|
83
83
|
RustType::Value
|
|
84
84
|
}
|
|
85
85
|
},
|
|
86
|
-
TypeAnnotation::Array(elem) =>
|
|
87
|
-
Self::from_annotation_with_aliases(elem, aliases)
|
|
88
|
-
|
|
86
|
+
TypeAnnotation::Array(elem) => {
|
|
87
|
+
RustType::Vec(Box::new(Self::from_annotation_with_aliases(elem, aliases)))
|
|
88
|
+
}
|
|
89
89
|
TypeAnnotation::Object(fields) => {
|
|
90
90
|
let typed_fields: Vec<_> = fields
|
|
91
91
|
.iter()
|
|
@@ -115,9 +115,9 @@ impl RustType {
|
|
|
115
115
|
|t| !matches!(t, TypeAnnotation::Simple(s) if s.as_ref() == "null"),
|
|
116
116
|
);
|
|
117
117
|
if let Some(inner) = non_null {
|
|
118
|
-
return RustType::Option(Box::new(
|
|
119
|
-
|
|
120
|
-
));
|
|
118
|
+
return RustType::Option(Box::new(Self::from_annotation_with_aliases(
|
|
119
|
+
inner, aliases,
|
|
120
|
+
)));
|
|
121
121
|
}
|
|
122
122
|
}
|
|
123
123
|
}
|