diff --git a/docs/docs.yml b/docs/docs.yml index fac13ee95..c6cae7053 100644 --- a/docs/docs.yml +++ b/docs/docs.yml @@ -41,6 +41,8 @@ navigation: path: docs/get-started/debugging/vscode-playground.mdx - page: Enable Logging path: docs/get-started/debugging/enable-logging.mdx + - page: Exception Handling + path: docs/calling-baml/exceptions.mdx - section: Deploying BAML Projects contents: - page: Docker diff --git a/docs/docs/calling-baml/exceptions.mdx b/docs/docs/calling-baml/exceptions.mdx new file mode 100644 index 000000000..ae666abe9 --- /dev/null +++ b/docs/docs/calling-baml/exceptions.mdx @@ -0,0 +1,92 @@ +--- +title: "Exceptions" +--- + +When BAML raises an exception, it will be an instance of a subclass of `BamlError`. This allows you to catch all BAML-specific exceptions with a single `except` block. + +## Import path + +```python Python +from baml_py.errors import BamlError, BamlInvalidArgumentError, BamlClientError, BamlClientHttpError, BamlValidationError +``` + + +```typescript TypeScript +// Instead of classes, TypeScript raises a string that is prefixed with: +// "BamlError:" +// Subclasses are sequentially appended to the string. +// For example, BamlInvalidArgumentError is returned as: +// "BamlError: BamlInvalidArgumentError:" +// Or, BamlClientHttpError is returned as: +// "BamlError: BamlClientError: BamlClientHttpError:" +``` + +```ruby Ruby +Not available yet +``` + + + +## BamlError + +Base class for all BAML exceptions. + + + A human-readable error message. + + +### BamlInvalidArgumentError + +Subclass of `BamlError`. + +Raised when one or multiple arguments to a function are invalid. + +### BamlClientError + +Subclass of `BamlError`. + +Raised when a client fails to return a valid response. + + +In the case of aggregate clients like `fallback` or those with `retry_policy`, only the last client's error is raised. + + +#### BamlClientHttpError + +Subclass of `BamlClientError`. + +Raised when the HTTP request made by a client fails with a non-200 status code. + + + The status code of the response. + +Common status codes are: + +- 1: Other +- 2: Other +- 400: Bad Request +- 401: Unauthorized +- 403: Forbidden +- 404: Not Found +- 429: Too Many Requests +- 500: Internal Server Error + + +### BamlValidationError + +Subclass of `BamlError`. + +Raised when BAML fails to parse a string from the LLM into the specified object. + + + The raw text from the LLM that failed to parse into the expected return type of a function. + diff --git a/engine/Cargo.lock b/engine/Cargo.lock index afeeb3362..90913c851 100644 --- a/engine/Cargo.lock +++ b/engine/Cargo.lock @@ -143,7 +143,7 @@ dependencies = [ "proc-macro2", "quote", "serde", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -916,6 +916,7 @@ dependencies = [ name = "baml-typescript-ffi" version = "0.0.1" dependencies = [ + "anyhow", "baml-runtime", "baml-types", "env_logger", @@ -985,7 +986,7 @@ dependencies = [ "regex", "rustc-hash", "shlex", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -1167,7 +1168,7 @@ dependencies = [ "heck 0.5.0", "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -1326,7 +1327,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "edb49164822f3ee45b17acd4a208cfc1251410cf0cad9a833234c9890774dd9f" dependencies = [ "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -1350,7 +1351,7 @@ dependencies = [ "proc-macro2", "quote", "strsim 0.11.1", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -1361,7 +1362,7 @@ checksum = "d336a2a514f6ccccaa3e09b02d41d35330c07ddf03a62165fcec10bb561c7806" dependencies = [ "darling_core", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -1404,7 +1405,7 @@ dependencies = [ "darling", "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -1414,7 +1415,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "206868b8242f27cecce124c19fd88157fbd0dd334df2587f36417bafbc85097b" dependencies = [ "derive_builder_core", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -1427,7 +1428,7 @@ dependencies = [ "proc-macro2", "quote", "rustc_version", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -1502,7 +1503,7 @@ dependencies = [ "once_cell", "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -1522,7 +1523,7 @@ checksum = "de0d48a183585823424a4ce1aa132d174a6a81bd540895822eb4c8373a8e49e8" dependencies = [ "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -1750,7 +1751,7 @@ checksum = "87750cf4b7a4c0625b1529e4c543c2182106e4dedc60a2a6455e00d212c489ac" dependencies = [ "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -2642,7 +2643,7 @@ checksum = "5968c820e2960565f647819f5928a42d6e874551cab9d88d75e3e0660d7f71e3" dependencies = [ "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -2765,7 +2766,7 @@ dependencies = [ "napi-derive-backend", "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -2780,7 +2781,7 @@ dependencies = [ "quote", "regex", "semver", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -2917,7 +2918,7 @@ checksum = "a948666b637a0f465e8564c73e89d4dde00d72d4d473cc972f390fc3dcee7d9c" dependencies = [ "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -3042,7 +3043,7 @@ dependencies = [ "pest_meta", "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -3073,7 +3074,7 @@ checksum = "2f38a4412a78282e09a2cf38d195ea5420d15ba0602cb375210efbc877243965" dependencies = [ "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -3252,7 +3253,7 @@ dependencies = [ "proc-macro2", "pyo3-macros-backend", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -3265,7 +3266,7 @@ dependencies = [ "proc-macro2", "pyo3-build-config", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -3337,7 +3338,7 @@ dependencies = [ "quote", "regex", "shell-words", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -3793,9 +3794,9 @@ checksum = "a3f0bf26fd526d2a95683cd0f87bf103b8539e2ca1ef48ce002d67aad59aa0b4" [[package]] name = "serde" -version = "1.0.204" +version = "1.0.209" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bc76f558e0cbb2a839d37354c575f1dc3fdc6546b5be373ba43d95f231bf7c12" +checksum = "99fce0ffe7310761ca6bf9faf5115afbc19688edd00171d81b1bb1b116c63e09" dependencies = [ "serde_derive", ] @@ -3824,13 +3825,13 @@ dependencies = [ [[package]] name = "serde_derive" -version = "1.0.204" +version = "1.0.209" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e0cd7e117be63d3c3678776753929474f3b04a43a080c744d6b0ae2a8c28e222" +checksum = "a5831b979fd7b5439637af1752d535ff49f4860c0f341d1baeb6faf0f4242170" dependencies = [ "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -3863,7 +3864,7 @@ checksum = "6c64451ba24fc7a6a2d60fc75dd9c83c90903b19028d4eff35e88fc1e86564e9" dependencies = [ "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -4081,7 +4082,7 @@ dependencies = [ "proc-macro2", "quote", "rustversion", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -4109,9 +4110,9 @@ dependencies = [ [[package]] name = "syn" -version = "2.0.71" +version = "2.0.76" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b146dcf730474b4bcd16c311627b31ede9ab149045db4d6088b3becaea046462" +checksum = "578e081a14e0cefc3279b0472138c513f37b41a08d5a3cca9b6e4e8ceb6cd525" dependencies = [ "proc-macro2", "quote", @@ -4194,7 +4195,7 @@ checksum = "5999e24eaa32083191ba4e425deb75cdf25efefabe5aaccb7446dd0d4122a3f5" dependencies = [ "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -4234,7 +4235,7 @@ checksum = "d20468752b09f49e909e55a5d338caa8bedf615594e9d80bc4c565d30faf798c" dependencies = [ "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -4320,7 +4321,7 @@ checksum = "5f5ae998a069d4b5aba8ee9dad856af7d520c3699e6159b185c2acd48155d39a" dependencies = [ "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -4413,7 +4414,7 @@ checksum = "34704c8d6ebcbc939824180af020566b01a7c01f80641264eba0999f6c2b6be7" dependencies = [ "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] @@ -4683,7 +4684,7 @@ dependencies = [ "once_cell", "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", "wasm-bindgen-shared", ] @@ -4717,7 +4718,7 @@ checksum = "e94f17b526d0a461a191c78ea52bbce64071ed5c04c9ffe424dcb38f74171bb7" dependencies = [ "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", "wasm-bindgen-backend", "wasm-bindgen-shared", ] @@ -4750,7 +4751,7 @@ checksum = "b7f89739351a2e03cb94beb799d47fb2cac01759b40ec441f7de39b00cbf7ef0" dependencies = [ "proc-macro2", "quote", - "syn 2.0.71", + "syn 2.0.76", ] [[package]] diff --git a/engine/baml-lib/baml-core/src/ir/ir_helpers/mod.rs b/engine/baml-lib/baml-core/src/ir/ir_helpers/mod.rs index 31c169b6d..67e872061 100644 --- a/engine/baml-lib/baml-core/src/ir/ir_helpers/mod.rs +++ b/engine/baml-lib/baml-core/src/ir/ir_helpers/mod.rs @@ -1,10 +1,10 @@ mod error_utils; -mod scope_diagnostics; +pub mod scope_diagnostics; mod to_baml_arg; use self::scope_diagnostics::ScopeStack; use crate::{ - error_not_found, error_unsupported, + error_not_found, ir::{ repr::{IntermediateRepr, Walker}, Class, Client, Enum, EnumValue, Field, FunctionNode, RetryPolicy, TemplateString, TestCase, @@ -179,9 +179,9 @@ impl IRHelper for IntermediateRepr { } if scope.has_errors() { - anyhow::bail!(scope); + Err(anyhow::anyhow!(scope)) + } else { + Ok(BamlValue::Map(baml_arg_map)) } - - Ok(BamlValue::Map(baml_arg_map)) } } diff --git a/engine/baml-lib/baml-core/src/ir/mod.rs b/engine/baml-lib/baml-core/src/ir/mod.rs index 6a87a0f44..ff31e20d6 100644 --- a/engine/baml-lib/baml-core/src/ir/mod.rs +++ b/engine/baml-lib/baml-core/src/ir/mod.rs @@ -4,8 +4,8 @@ pub mod repr; mod walker; pub use ir_helpers::{ - ArgCoercer, ClassFieldWalker, ClassWalker, ClientWalker, EnumValueWalker, EnumWalker, - FunctionWalker, IRHelper, RetryPolicyWalker, TemplateStringWalker, TestCaseWalker, + scope_diagnostics, ArgCoercer, ClassFieldWalker, ClassWalker, ClientWalker, EnumValueWalker, + EnumWalker, FunctionWalker, IRHelper, RetryPolicyWalker, TemplateStringWalker, TestCaseWalker, }; pub(super) use repr::IntermediateRepr; diff --git a/engine/baml-runtime/src/errors.rs b/engine/baml-runtime/src/errors.rs new file mode 100644 index 000000000..a759f0f80 --- /dev/null +++ b/engine/baml-runtime/src/errors.rs @@ -0,0 +1,22 @@ +pub enum ExposedError { + /// Error in parsing post calling the LLM + ValidationError(String), +} + +impl std::error::Error for ExposedError {} + +impl std::fmt::Display for ExposedError { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + match self { + ExposedError::ValidationError(err) => { + write!(f, "Parsing error: {}", err) + } + } + } +} + +impl std::fmt::Debug for ExposedError { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + f.write_fmt(format_args!("{:?}", self)) + } +} diff --git a/engine/baml-runtime/src/internal/llm_client/mod.rs b/engine/baml-runtime/src/internal/llm_client/mod.rs index d1fdafc41..b8d046cec 100644 --- a/engine/baml-runtime/src/internal/llm_client/mod.rs +++ b/engine/baml-runtime/src/internal/llm_client/mod.rs @@ -176,6 +176,18 @@ impl ErrorCode { code => ErrorCode::Other(code), } } + + pub fn to_u16(&self) -> u16 { + match self { + ErrorCode::InvalidAuthentication => 401, + ErrorCode::NotSupported => 403, + ErrorCode::RateLimited => 429, + ErrorCode::ServerError => 500, + ErrorCode::ServiceUnavailable => 503, + ErrorCode::UnsupportedResponse(code) => *code, + ErrorCode::Other(code) => *code, + } + } } #[derive(Clone, Debug)] diff --git a/engine/baml-runtime/src/internal/llm_client/primitive/anthropic/anthropic_client.rs b/engine/baml-runtime/src/internal/llm_client/primitive/anthropic/anthropic_client.rs index 7f18cbb27..807f08b0f 100644 --- a/engine/baml-runtime/src/internal/llm_client/primitive/anthropic/anthropic_client.rs +++ b/engine/baml-runtime/src/internal/llm_client/primitive/anthropic/anthropic_client.rs @@ -86,8 +86,9 @@ fn resolve_properties( .or_else(|| ctx.env.get("ANTHROPIC_API_KEY").map(|s| s.to_string())); let allowed_metadata = match properties.remove("allowed_role_metadata") { - Some(allowed_metadata) => serde_json::from_value(allowed_metadata) - .context("allowed_role_metadata must be an array of keys. For example: ['key1', 'key2']")?, + Some(allowed_metadata) => serde_json::from_value(allowed_metadata).context( + "allowed_role_metadata must be an array of keys. For example: ['key1', 'key2']", + )?, None => AllowedMetadata::None, }; @@ -209,7 +210,7 @@ impl SseResponseTrait for AnthropicClient { start_time: system_start, latency: instant_start.elapsed(), message: format!("Failed to parse event: {:#?}", e), - code: ErrorCode::Other(2), + code: ErrorCode::UnsupportedResponse(2), }, ))); } diff --git a/engine/baml-runtime/src/internal/llm_client/primitive/google/googleai_client.rs b/engine/baml-runtime/src/internal/llm_client/primitive/google/googleai_client.rs index 007e2dc16..12c59081f 100644 --- a/engine/baml-runtime/src/internal/llm_client/primitive/google/googleai_client.rs +++ b/engine/baml-runtime/src/internal/llm_client/primitive/google/googleai_client.rs @@ -71,8 +71,9 @@ fn resolve_properties( .and_then(|v| v.as_str().map(|s| s.to_string())) .unwrap_or_else(|| "https://generativelanguage.googleapis.com/v1beta".to_string()); let allowed_metadata = match properties.remove("allowed_role_metadata") { - Some(allowed_metadata) => serde_json::from_value(allowed_metadata) - .context("allowed_role_metadata must be an array of keys. For example: ['key1', 'key2']")?, + Some(allowed_metadata) => serde_json::from_value(allowed_metadata).context( + "allowed_role_metadata must be an array of keys. For example: ['key1', 'key2']", + )?, None => AllowedMetadata::None, }; @@ -200,7 +201,7 @@ impl SseResponseTrait for GoogleAIClient { request_options: params.clone(), latency: instant_start.elapsed(), message: format!("Failed to parse event: {:#?}", e), - code: ErrorCode::Other(2), + code: ErrorCode::UnsupportedResponse(2), }, ))); } diff --git a/engine/baml-runtime/src/internal/llm_client/primitive/openai/openai_client.rs b/engine/baml-runtime/src/internal/llm_client/primitive/openai/openai_client.rs index 57c426ad5..1674f078d 100644 --- a/engine/baml-runtime/src/internal/llm_client/primitive/openai/openai_client.rs +++ b/engine/baml-runtime/src/internal/llm_client/primitive/openai/openai_client.rs @@ -358,7 +358,7 @@ impl SseResponseTrait for OpenAIClient { request_options: params.clone(), latency: instant_start.elapsed(), message: format!("Failed to parse event: {:#?}", e), - code: ErrorCode::Other(2), + code: ErrorCode::UnsupportedResponse(2), }, ))); } diff --git a/engine/baml-runtime/src/internal/llm_client/primitive/vertex/vertex_client.rs b/engine/baml-runtime/src/internal/llm_client/primitive/vertex/vertex_client.rs index 848b1c36a..9808e3e99 100644 --- a/engine/baml-runtime/src/internal/llm_client/primitive/vertex/vertex_client.rs +++ b/engine/baml-runtime/src/internal/llm_client/primitive/vertex/vertex_client.rs @@ -88,8 +88,9 @@ fn resolve_properties( .and_then(|v| v.as_str().map(|s| s.to_string())) .unwrap_or("".to_string()); let allowed_metadata = match properties.remove("allowed_role_metadata") { - Some(allowed_metadata) => serde_json::from_value(allowed_metadata) - .context("allowed_role_metadata must be an array of keys. For example: ['key1', 'key2']")?, + Some(allowed_metadata) => serde_json::from_value(allowed_metadata).context( + "allowed_role_metadata must be an array of keys. For example: ['key1', 'key2']", + )?, None => AllowedMetadata::None, }; let mut service_key: Option<(String, String)> = None; @@ -280,7 +281,7 @@ impl SseResponseTrait for VertexClient { request_options: params.clone(), latency: instant_start.elapsed(), message: format!("Failed to parse event: {:#?}", e), - code: ErrorCode::Other(2), + code: ErrorCode::UnsupportedResponse(2), }, ))); } diff --git a/engine/baml-runtime/src/lib.rs b/engine/baml-runtime/src/lib.rs index 7a0e7be40..0a2b808c7 100644 --- a/engine/baml-runtime/src/lib.rs +++ b/engine/baml-runtime/src/lib.rs @@ -14,8 +14,9 @@ pub(crate) mod internal; #[cfg(not(target_arch = "wasm32"))] mod cli; pub mod client_registry; +pub mod errors; mod macros; -mod request; +pub mod request; mod runtime; pub mod runtime_interface; pub mod tracing; @@ -236,7 +237,6 @@ impl BamlRuntime { ) -> (Result, Option) { log::trace!("Calling function: {}", function_name); let span = self.tracer.start_span(&function_name, ctx, ¶ms); - log::trace!("Span started"); let response = match ctx.create_ctx(tb, cb) { Ok(rctx) => { self.inner diff --git a/engine/baml-runtime/src/types/response.rs b/engine/baml-runtime/src/types/response.rs index b98459a93..9c625c4a2 100644 --- a/engine/baml-runtime/src/types/response.rs +++ b/engine/baml-runtime/src/types/response.rs @@ -1,5 +1,5 @@ -use crate::internal::llm_client::orchestrator::OrchestrationScope; pub use crate::internal::llm_client::LLMResponse; +use crate::{errors::ExposedError, internal::llm_client::orchestrator::OrchestrationScope}; use anyhow::Result; use colored::*; @@ -102,10 +102,12 @@ impl FunctionResult { if let Ok(val) = res { Ok(val) } else { - anyhow::bail!("{}", self) + Err(anyhow::anyhow!( + crate::errors::ExposedError::ValidationError(format!("{}", self)) + )) } }) - .unwrap_or_else(|| anyhow::bail!("{}", self)) + .unwrap_or_else(|| Err(anyhow::anyhow!(self.llm_response().clone()))) } } diff --git a/engine/language_client_python/python_src/baml_py/baml_py.pyi b/engine/language_client_python/python_src/baml_py/baml_py.pyi index 797bb9b94..6964a6166 100644 --- a/engine/language_client_python/python_src/baml_py/baml_py.pyi +++ b/engine/language_client_python/python_src/baml_py/baml_py.pyi @@ -1,4 +1,4 @@ -from typing import Any, Callable, Dict, List, Optional, Tuple +from typing import Any, Callable, Dict, Optional, Tuple class FunctionResult: """The result of a BAML function call. @@ -209,3 +209,24 @@ class ClassPropertyBuilder: def description(self, description: Optional[str]) -> ClassPropertyBuilder: ... def invoke_runtime_cli() -> None: ... + + +class BamlError(Exception): + """Base class for all BAML-related errors.""" + ... + +class BamlInvalidArgumentError(BamlError): + """Raised when an invalid argument is provided to a function.""" + ... + +class BamlClientError(BamlError): + """Raised for general client errors.""" + ... + +class BamlClientHttpError(BamlClientError): + """Raised for HTTP-related client errors.""" + ... + +class BamlValidationError(BamlError): + """Raised when validation fails.""" + ... diff --git a/engine/language_client_python/python_src/baml_py/errors.py b/engine/language_client_python/python_src/baml_py/errors.py new file mode 100644 index 000000000..363408000 --- /dev/null +++ b/engine/language_client_python/python_src/baml_py/errors.py @@ -0,0 +1,9 @@ +from .baml_py import BamlError, BamlClientError, BamlClientHttpError, BamlInvalidArgumentError, BamlValidationError + +__all__ = [ + "BamlError", + "BamlClientError", + "BamlClientHttpError", + "BamlInvalidArgumentError", + "BamlValidationError", +] diff --git a/engine/language_client_python/src/errors.rs b/engine/language_client_python/src/errors.rs new file mode 100644 index 000000000..1de6f2a9d --- /dev/null +++ b/engine/language_client_python/src/errors.rs @@ -0,0 +1,54 @@ +use baml_runtime::{ + errors::ExposedError, internal::llm_client::LLMResponse, + internal_core::ir::scope_diagnostics::ScopeStack, +}; +use pyo3::{create_exception, PyErr}; + +create_exception!(baml_py, BamlError, pyo3::exceptions::PyException); +create_exception!(baml_py, BamlInvalidArgumentError, BamlError); +create_exception!(baml_py, BamlClientError, BamlError); +create_exception!(baml_py, BamlClientHttpError, BamlClientError); +create_exception!(baml_py, BamlValidationError, BamlError); + +impl BamlError { + pub fn from_anyhow(err: anyhow::Error) -> PyErr { + if let Some(er) = err.downcast_ref::() { + match er { + ExposedError::ValidationError(_) => { + PyErr::new::(format!("{}", err)) + } + } + } else if let Some(er) = err.downcast_ref::() { + PyErr::new::(format!("Invalid argument: {}", er)) + } else if let Some(er) = err.downcast_ref::() { + match er { + LLMResponse::Success(_) => { + PyErr::new::(format!("Unexpected error from BAML: {}", err)) + } + LLMResponse::LLMFailure(failed) => match &failed.code { + baml_runtime::internal::llm_client::ErrorCode::Other(2) => { + PyErr::new::(format!( + "Something went wrong with the LLM client: {}", + err + )) + } + baml_runtime::internal::llm_client::ErrorCode::Other(_) + | baml_runtime::internal::llm_client::ErrorCode::InvalidAuthentication + | baml_runtime::internal::llm_client::ErrorCode::NotSupported + | baml_runtime::internal::llm_client::ErrorCode::RateLimited + | baml_runtime::internal::llm_client::ErrorCode::ServerError + | baml_runtime::internal::llm_client::ErrorCode::ServiceUnavailable + | baml_runtime::internal::llm_client::ErrorCode::UnsupportedResponse(_) => { + PyErr::new::(format!("{}", err)) + } + }, + LLMResponse::OtherFailure(_) => PyErr::new::(format!( + "Something went wrong with the LLM client: {}", + err + )), + } + } else { + PyErr::new::(format!("{:?}", err)) + } + } +} diff --git a/engine/language_client_python/src/lib.rs b/engine/language_client_python/src/lib.rs index ceecf9bae..42f5c6d28 100644 --- a/engine/language_client_python/src/lib.rs +++ b/engine/language_client_python/src/lib.rs @@ -1,17 +1,10 @@ +mod errors; mod parse_py_type; mod runtime; mod types; use pyo3::prelude::{pyfunction, pymodule, PyAnyMethods, PyModule, PyResult}; -use pyo3::{create_exception, wrap_pyfunction, Bound, PyErr, Python}; - -create_exception!(baml_py, BamlError, pyo3::exceptions::PyException); - -impl BamlError { - fn from_anyhow(err: anyhow::Error) -> PyErr { - PyErr::new::(format!("{:?}", err)) - } -} +use pyo3::{wrap_pyfunction, Bound, Python}; #[pyfunction] fn invoke_runtime_cli(py: Python) -> PyResult<()> { @@ -21,11 +14,11 @@ fn invoke_runtime_cli(py: Python) -> PyResult<()> { .extract::>()?, baml_runtime::CallerType::Python, ) - .map_err(BamlError::from_anyhow)?) + .map_err(errors::BamlError::from_anyhow)?) } #[pymodule] -fn baml_py(_: Python<'_>, m: Bound<'_, PyModule>) -> PyResult<()> { +fn baml_py(m: Bound<'_, PyModule>) -> PyResult<()> { if let Err(e) = env_logger::try_init_from_env( env_logger::Env::new() .filter("BAML_LOG") @@ -55,6 +48,23 @@ fn baml_py(_: Python<'_>, m: Bound<'_, PyModule>) -> PyResult<()> { m.add_class::()?; m.add_wrapped(wrap_pyfunction!(invoke_runtime_cli))?; + m.add("BamlError", m.py().get_type_bound::())?; + m.add( + "BamlInvalidArgumentError", + m.py().get_type_bound::(), + )?; + m.add( + "BamlClientError", + m.py().get_type_bound::(), + )?; + m.add( + "BamlClientHttpError", + m.py().get_type_bound::(), + )?; + m.add( + "BamlValidationError", + m.py().get_type_bound::(), + )?; Ok(()) } diff --git a/engine/language_client_python/src/runtime.rs b/engine/language_client_python/src/runtime.rs index 2b4f93d6e..7e82888d6 100644 --- a/engine/language_client_python/src/runtime.rs +++ b/engine/language_client_python/src/runtime.rs @@ -1,7 +1,7 @@ +use crate::errors::{BamlError, BamlInvalidArgumentError}; use crate::parse_py_type::parse_py_type; use crate::types::function_results::FunctionResult; use crate::types::trace_stats::TraceStats; -use crate::BamlError; use crate::types::function_result_stream::{FunctionResultStream, SyncFunctionResultStream}; use crate::types::runtime_ctx_manager::RuntimeContextManager; @@ -111,12 +111,14 @@ impl BamlRuntime { cb: Option<&ClientRegistry>, ) -> PyResult { let Some(args) = parse_py_type(args.into_bound(py).to_object(py), false)? else { - return Err(BamlError::new_err( + return Err(BamlInvalidArgumentError::new_err( "Failed to parse args, perhaps you used a non-serializable type?", )); }; let Some(args_map) = args.as_map_owned() else { - return Err(BamlError::new_err("Failed to parse args")); + return Err(BamlInvalidArgumentError::new_err( + "Failed to parse args. Expect kwargs", + )); }; log::debug!("pyo3 call_function parsed args into: {:#?}", args_map); @@ -127,12 +129,11 @@ impl BamlRuntime { pyo3_asyncio::tokio::future_into_py(py, async move { let ctx_mng = ctx_mng; - let result = baml_runtime + let (result, _) = baml_runtime .call_function(function_name, &args_map, &ctx_mng, tb.as_ref(), cb.as_ref()) .await; result - .0 .map(FunctionResult::from) .map_err(BamlError::from_anyhow) }) @@ -149,12 +150,14 @@ impl BamlRuntime { cb: Option<&ClientRegistry>, ) -> PyResult { let Some(args) = parse_py_type(args, false)? else { - return Err(BamlError::new_err( + return Err(BamlInvalidArgumentError::new_err( "Failed to parse args, perhaps you used a non-serializable type?", )); }; let Some(args_map) = args.as_map_owned() else { - return Err(BamlError::new_err("Failed to parse args")); + return Err(BamlInvalidArgumentError::new_err( + "Failed to parse args as a map", + )); }; log::debug!("pyo3 call_function_sync parsed args into: {:#?}", args_map); @@ -187,12 +190,12 @@ impl BamlRuntime { cb: Option<&ClientRegistry>, ) -> PyResult { let Some(args) = parse_py_type(args.into_bound(py).to_object(py), false)? else { - return Err(BamlError::new_err( + return Err(BamlInvalidArgumentError::new_err( "Failed to parse args, perhaps you used a non-serializable type?", )); }; let Some(args_map) = args.as_map() else { - return Err(BamlError::new_err("Failed to parse args")); + return Err(BamlInvalidArgumentError::new_err("Failed to parse args")); }; log::debug!("pyo3 stream_function parsed args into: {:#?}", args_map); @@ -228,12 +231,12 @@ impl BamlRuntime { cb: Option<&ClientRegistry>, ) -> PyResult { let Some(args) = parse_py_type(args.into_bound(py).to_object(py), false)? else { - return Err(BamlError::new_err( + return Err(BamlInvalidArgumentError::new_err( "Failed to parse args, perhaps you used a non-serializable type?", )); }; let Some(args_map) = args.as_map() else { - return Err(BamlError::new_err("Failed to parse args")); + return Err(BamlInvalidArgumentError::new_err("Failed to parse args")); }; log::debug!("pyo3 stream_function parsed args into: {:#?}", args_map); diff --git a/engine/language_client_python/src/types/audio.rs b/engine/language_client_python/src/types/audio.rs index 2c784bb83..bf25b02fb 100644 --- a/engine/language_client_python/src/types/audio.rs +++ b/engine/language_client_python/src/types/audio.rs @@ -2,6 +2,8 @@ use baml_types::BamlMediaContent; use pyo3::prelude::{pymethods, PyAnyMethods, PyModule, PyResult}; use pyo3::types::PyType; use pyo3::{Bound, Py, PyAny, PyObject, Python, ToPyObject}; + +use crate::errors::BamlError; crate::lang_wrapper!(BamlAudioPy, baml_types::BamlMedia); #[pymethods] @@ -31,7 +33,7 @@ impl BamlAudioPy { pub fn as_url(&self) -> PyResult { match &self.inner.content { BamlMediaContent::Url(url) => Ok(url.url.clone()), - _ => Err(crate::BamlError::new_err("Audio is not a URL")), + _ => Err(BamlError::new_err("Audio is not a URL")), } } @@ -41,7 +43,7 @@ impl BamlAudioPy { base64.base64.clone(), self.inner.mime_type.clone().unwrap_or("".to_string()), ]), - _ => Err(crate::BamlError::new_err("Audio is not base64")), + _ => Err(BamlError::new_err("Audio is not base64")), } } diff --git a/engine/language_client_python/src/types/client_registry.rs b/engine/language_client_python/src/types/client_registry.rs index 71f704279..ec611cfc7 100644 --- a/engine/language_client_python/src/types/client_registry.rs +++ b/engine/language_client_python/src/types/client_registry.rs @@ -2,8 +2,8 @@ use baml_runtime::client_registry; use pyo3::prelude::{pymethods, PyResult}; use pyo3::{PyObject, Python, ToPyObject}; +use crate::errors::BamlInvalidArgumentError; use crate::parse_py_type::parse_py_type; -use crate::BamlError; crate::lang_wrapper!(ClientRegistry, client_registry::ClientRegistry); @@ -26,12 +26,12 @@ impl ClientRegistry { retry_policy: Option, ) -> PyResult<()> { let Some(args) = parse_py_type(options.into_bound(py).to_object(py), false)? else { - return Err(BamlError::new_err( + return Err(BamlInvalidArgumentError::new_err( "Failed to parse args, perhaps you used a non-serializable type?", )); }; let Some(args_map) = args.as_map_owned() else { - return Err(BamlError::new_err( + return Err(BamlInvalidArgumentError::new_err( "Failed to parse args, perhaps you used a non-serializable type?", )); }; diff --git a/engine/language_client_python/src/types/function_result_stream.rs b/engine/language_client_python/src/types/function_result_stream.rs index f0be61b20..e9f254fe0 100644 --- a/engine/language_client_python/src/types/function_result_stream.rs +++ b/engine/language_client_python/src/types/function_result_stream.rs @@ -1,7 +1,7 @@ use pyo3::prelude::{pymethods, PyResult}; use pyo3::{PyObject, PyRefMut, Python}; -use crate::BamlError; +use crate::errors::BamlError; use super::function_results::FunctionResult; use super::runtime_ctx_manager::RuntimeContextManager; diff --git a/engine/language_client_python/src/types/function_results.rs b/engine/language_client_python/src/types/function_results.rs index 57d87bc65..427538360 100644 --- a/engine/language_client_python/src/types/function_results.rs +++ b/engine/language_client_python/src/types/function_results.rs @@ -3,6 +3,8 @@ use pyo3::prelude::{pymethods, PyResult}; use pyo3::{PyObject, Python}; use pythonize::pythonize; +use crate::errors::BamlError; + crate::lang_wrapper!(FunctionResult, baml_runtime::FunctionResult); #[pymethods] @@ -19,7 +21,7 @@ impl FunctionResult { let parsed = self .inner .parsed_content() - .map_err(crate::BamlError::from_anyhow)?; + .map_err(BamlError::from_anyhow)?; Ok(pythonize(py, &BamlValue::from(parsed))?) } diff --git a/engine/language_client_python/src/types/image.rs b/engine/language_client_python/src/types/image.rs index e8159604e..b98e5fe7a 100644 --- a/engine/language_client_python/src/types/image.rs +++ b/engine/language_client_python/src/types/image.rs @@ -1,6 +1,8 @@ use pyo3::prelude::{pymethods, PyAnyMethods, PyModule, PyResult}; use pyo3::types::PyType; use pyo3::{Bound, Py, PyAny, PyObject, Python, ToPyObject}; + +use crate::errors::BamlInvalidArgumentError; crate::lang_wrapper!(BamlImagePy, baml_types::BamlMedia); #[pymethods] @@ -30,7 +32,7 @@ impl BamlImagePy { pub fn as_url(&self) -> PyResult { match &self.inner.content { baml_types::BamlMediaContent::Url(url) => Ok(url.url.clone()), - _ => Err(crate::BamlError::new_err("Image is not a URL")), + _ => Err(BamlInvalidArgumentError::new_err("Image is not a URL")), } } @@ -40,7 +42,7 @@ impl BamlImagePy { base64.base64.clone(), self.inner.mime_type.clone().unwrap_or("".to_string()), ]), - _ => Err(crate::BamlError::new_err("Image is not base64")), + _ => Err(BamlInvalidArgumentError::new_err("Image is not base64")), } } diff --git a/engine/language_client_python/src/types/runtime_ctx_manager.rs b/engine/language_client_python/src/types/runtime_ctx_manager.rs index e68c3ccd9..29f5a0d0f 100644 --- a/engine/language_client_python/src/types/runtime_ctx_manager.rs +++ b/engine/language_client_python/src/types/runtime_ctx_manager.rs @@ -1,8 +1,8 @@ use pyo3::prelude::{pymethods, PyResult}; use pyo3::{PyObject, Python, ToPyObject}; +use crate::errors::BamlError; use crate::parse_py_type::parse_py_type; -use crate::BamlError; crate::lang_wrapper!(RuntimeContextManager, baml_runtime::RuntimeContextManager); diff --git a/engine/language_client_python/src/types/span.rs b/engine/language_client_python/src/types/span.rs index 17cd70c3d..131642798 100644 --- a/engine/language_client_python/src/types/span.rs +++ b/engine/language_client_python/src/types/span.rs @@ -3,8 +3,8 @@ use baml_types::BamlValue; use pyo3::prelude::{pymethods, PyResult}; use pyo3::{PyObject, Python, ToPyObject}; +use crate::errors::{BamlError, BamlInvalidArgumentError}; use crate::parse_py_type::parse_py_type; -use crate::BamlError; use super::runtime_ctx_manager::RuntimeContextManager; use crate::runtime::BamlRuntime; @@ -28,7 +28,7 @@ impl BamlSpan { let args = parse_py_type(args.into_bound(py).to_object(py), true)? .unwrap_or(BamlValue::Map(Default::default())); let Some(args_map) = args.as_map() else { - return Err(BamlError::new_err("Failed to parse args")); + return Err(BamlInvalidArgumentError::new_err("Failed to parse args")); }; let span = runtime diff --git a/engine/language_client_typescript/Cargo.toml b/engine/language_client_typescript/Cargo.toml index 63d00bcba..33b868635 100644 --- a/engine/language_client_typescript/Cargo.toml +++ b/engine/language_client_typescript/Cargo.toml @@ -21,6 +21,7 @@ napi = { version = "2", features = [ "napi5", "async", ] } +anyhow.workspace = true napi-derive = "2" serde.workspace = true serde_json.workspace = true diff --git a/engine/language_client_typescript/src/errors.rs b/engine/language_client_typescript/src/errors.rs new file mode 100644 index 000000000..7d191d042 --- /dev/null +++ b/engine/language_client_typescript/src/errors.rs @@ -0,0 +1,66 @@ +use baml_runtime::{ + errors::ExposedError, internal::llm_client::LLMResponse, + internal_core::ir::scope_diagnostics::ScopeStack, +}; + +// napi::Error::new(napi::Status::GenericFailure, e.to_string())) + +pub fn invalid_argument_error(message: &str) -> napi::Error { + napi::Error::new( + napi::Status::InvalidArg, + format!("BamlError: BamlInvalidArgumentError: {}", message), + ) +} + +pub fn from_anyhow_error(err: anyhow::Error) -> napi::Error { + if let Some(er) = err.downcast_ref::() { + match er { + ExposedError::ValidationError(_) => napi::Error::new( + napi::Status::GenericFailure, + format!("BamlError: BamlValidationError: {}", err), + ), + } + } else if let Some(er) = err.downcast_ref::() { + invalid_argument_error(&format!("{}", er)) + } else if let Some(er) = err.downcast_ref::() { + match er { + LLMResponse::Success(_) => napi::Error::new( + napi::Status::GenericFailure, + format!("BamlError: Unexpected error from BAML: {}", err), + ), + LLMResponse::LLMFailure(failed) => match &failed.code { + baml_runtime::internal::llm_client::ErrorCode::Other(2) => napi::Error::new( + napi::Status::GenericFailure, + format!( + "BamlError: BamlClientError: Something went wrong with the LLM client: {}", + err + ), + ), + baml_runtime::internal::llm_client::ErrorCode::Other(_) + | baml_runtime::internal::llm_client::ErrorCode::InvalidAuthentication + | baml_runtime::internal::llm_client::ErrorCode::NotSupported + | baml_runtime::internal::llm_client::ErrorCode::RateLimited + | baml_runtime::internal::llm_client::ErrorCode::ServerError + | baml_runtime::internal::llm_client::ErrorCode::ServiceUnavailable + | baml_runtime::internal::llm_client::ErrorCode::UnsupportedResponse(_) => { + napi::Error::new( + napi::Status::GenericFailure, + format!("BamlError: BamlClientError: BamlClientHttpError: {}", err), + ) + } + }, + LLMResponse::OtherFailure(_) => napi::Error::new( + napi::Status::GenericFailure, + format!( + "BamlError: BamlClientError: Something went wrong with the LLM client: {}", + err + ), + ), + } + } else { + napi::Error::new( + napi::Status::GenericFailure, + format!("BamlError: {:?}", err), + ) + } +} diff --git a/engine/language_client_typescript/src/lib.rs b/engine/language_client_typescript/src/lib.rs index f7217a0a6..4997079e6 100644 --- a/engine/language_client_typescript/src/lib.rs +++ b/engine/language_client_typescript/src/lib.rs @@ -1,6 +1,7 @@ use napi::{Env, JsUndefined}; use napi_derive::napi; +mod errors; mod parse_ts_types; mod runtime; mod types; diff --git a/engine/language_client_typescript/src/runtime.rs b/engine/language_client_typescript/src/runtime.rs index 1572e1a3b..a6029aadc 100644 --- a/engine/language_client_typescript/src/runtime.rs +++ b/engine/language_client_typescript/src/runtime.rs @@ -1,3 +1,4 @@ +use crate::errors::{from_anyhow_error, invalid_argument_error}; use crate::parse_ts_types; use crate::types::client_registry::ClientRegistry; use crate::types::function_result_stream::FunctionResultStream; @@ -54,7 +55,7 @@ impl BamlRuntime { ) -> napi::Result { let directory = PathBuf::from(directory); Ok(CoreRuntime::from_directory(&directory, env_vars) - .map_err(|e| napi::Error::new(napi::Status::GenericFailure, e.to_string()))? + .map_err(|e| from_anyhow_error(e))? .into()) } @@ -65,7 +66,7 @@ impl BamlRuntime { env_vars: HashMap, ) -> napi::Result { Ok(CoreRuntime::from_file_content(&root_path, &files, env_vars) - .map_err(|e| napi::Error::new(napi::Status::GenericFailure, e.to_string()))? + .map_err(|e| from_anyhow_error(e))? .into()) } @@ -89,13 +90,10 @@ impl BamlRuntime { let args = parse_ts_types::js_object_to_baml_value(env, args)?; if !args.is_map() { - return Err(napi::Error::new( - napi::Status::GenericFailure, - format!( - "Invalid args: Expected a map of arguments, got: {}", - args.r#type() - ), - )); + return Err(invalid_argument_error(&format!( + "Expected a map of arguments, got: {}", + args.r#type() + ))); } let args_map = args.as_map_owned().unwrap(); @@ -112,7 +110,7 @@ impl BamlRuntime { result .0 .map(FunctionResult::from) - .map_err(|e| napi::Error::new(napi::Status::GenericFailure, e.to_string())) + .map_err(|e| from_anyhow_error(e)) }; env.execute_tokio_future(fut, |&mut _, data| Ok(data)) @@ -131,13 +129,10 @@ impl BamlRuntime { let args = parse_ts_types::js_object_to_baml_value(env, args)?; if !args.is_map() { - return Err(napi::Error::new( - napi::Status::GenericFailure, - format!( - "Invalid args: Expected a map of arguments, got: {}", - args.r#type() - ), - )); + return Err(invalid_argument_error(&format!( + "Expected a map of arguments, got: {}", + args.r#type() + ))); } let args_map = args.as_map_owned().unwrap(); @@ -154,7 +149,7 @@ impl BamlRuntime { result .map(FunctionResult::from) - .map_err(|e| napi::Error::new(napi::Status::GenericFailure, e.to_string())) + .map_err(|e| from_anyhow_error(e)) } #[napi] @@ -170,13 +165,10 @@ impl BamlRuntime { ) -> napi::Result { let args: BamlValue = parse_ts_types::js_object_to_baml_value(env, args)?; if !args.is_map() { - return Err(napi::Error::new( - napi::Status::GenericFailure, - format!( - "Invalid args: Expected a map of arguments, got: {}", - args.r#type() - ), - )); + return Err(invalid_argument_error(&format!( + "Expected a map of arguments, got: {}", + args.r#type() + ))); } let args_map = args.as_map_owned().unwrap(); @@ -192,7 +184,7 @@ impl BamlRuntime { tb.as_ref(), client_registry.as_ref(), ) - .map_err(|e| napi::Error::new(napi::Status::GenericFailure, e.to_string()))?; + .map_err(|e| from_anyhow_error(e))?; let cb = match cb { Some(cb) => Some(env.create_reference(cb)?), @@ -215,13 +207,10 @@ impl BamlRuntime { ) -> napi::Result { let args: BamlValue = parse_ts_types::js_object_to_baml_value(env, args)?; if !args.is_map() { - return Err(napi::Error::new( - napi::Status::GenericFailure, - format!( - "Invalid args: Expected a map of arguments, got: {}", - args.r#type() - ), - )); + return Err(invalid_argument_error(&format!( + "Expected a map of arguments, got: {}", + args.r#type() + ))); } let args_map = args.as_map_owned().unwrap(); @@ -237,7 +226,7 @@ impl BamlRuntime { tb.as_ref(), client_registry.as_ref(), ) - .map_err(|e| napi::Error::new(napi::Status::GenericFailure, e.to_string()))?; + .map_err(|e| from_anyhow_error(e))?; let cb = match cb { Some(cb) => Some(env.create_reference(cb)?), @@ -301,7 +290,7 @@ impl BamlRuntime { let res = self .inner .set_log_event_callback(Some(cb)) - .map_err(|e| napi::Error::new(napi::Status::GenericFailure, e.to_string())); + .map_err(|e| from_anyhow_error(e)); let _ = tsfn.unref(&env); match res { @@ -316,7 +305,7 @@ impl BamlRuntime { let res = self .inner .set_log_event_callback(None) - .map_err(|e| napi::Error::new(napi::Status::GenericFailure, e.to_string())); + .map_err(|e| from_anyhow_error(e)); match res { Ok(_) => Ok(()), @@ -341,9 +330,7 @@ impl BamlRuntime { #[napi] pub fn flush(&mut self, env: Env) -> napi::Result<()> { - self.inner - .flush() - .map_err(|e| napi::Error::new(napi::Status::GenericFailure, e.to_string())) + self.inner.flush().map_err(|e| from_anyhow_error(e)) } #[napi] diff --git a/engine/language_client_typescript/src/types/audio.rs b/engine/language_client_typescript/src/types/audio.rs index 7ea25476f..d3a7cdc96 100644 --- a/engine/language_client_typescript/src/types/audio.rs +++ b/engine/language_client_typescript/src/types/audio.rs @@ -2,6 +2,8 @@ use napi::bindgen_prelude::External; use napi_derive::napi; use serde_json::json; +use crate::errors::invalid_argument_error; + crate::lang_wrapper!(BamlAudio, baml_types::BamlMedia); #[napi] @@ -35,10 +37,7 @@ impl BamlAudio { pub fn as_url(&self) -> napi::Result { match &self.inner.content { baml_types::BamlMediaContent::Url(url) => Ok(url.url.clone()), - _ => Err(napi::Error::new( - napi::Status::GenericFailure, - "Audio is not a URL".to_string(), - )), + _ => Err(invalid_argument_error("Audio is not a URL")), } } @@ -49,10 +48,7 @@ impl BamlAudio { base64.base64.clone(), self.inner.mime_type.clone().unwrap_or("".to_string()), ]), - _ => Err(napi::Error::new( - napi::Status::GenericFailure, - "Audio is not base64".to_string(), - )), + _ => Err(invalid_argument_error("Audio is not base64")), } } diff --git a/engine/language_client_typescript/src/types/client_registry.rs b/engine/language_client_typescript/src/types/client_registry.rs index 502bab8a6..ef088d96d 100644 --- a/engine/language_client_typescript/src/types/client_registry.rs +++ b/engine/language_client_typescript/src/types/client_registry.rs @@ -3,6 +3,7 @@ use napi::Env; use napi::JsObject; use napi_derive::napi; +use crate::errors::invalid_argument_error; use crate::parse_ts_types; crate::lang_wrapper!(ClientRegistry, client_registry::ClientRegistry); @@ -27,13 +28,10 @@ impl ClientRegistry { ) -> napi::Result<()> { let args = parse_ts_types::js_object_to_baml_value(env, options)?; if !args.is_map() { - return Err(napi::Error::new( - napi::Status::GenericFailure, - format!( - "Invalid options: Expected a map of arguments, got: {}", - args.r#type() - ), - )); + return Err(invalid_argument_error(&format!( + "Invalid options: Expected a map of arguments, got: {}", + args.r#type() + ))); } let args_map = args.as_map_owned().unwrap(); diff --git a/engine/language_client_typescript/src/types/function_result_stream.rs b/engine/language_client_typescript/src/types/function_result_stream.rs index 4bade2dae..c48a76b44 100644 --- a/engine/language_client_typescript/src/types/function_result_stream.rs +++ b/engine/language_client_typescript/src/types/function_result_stream.rs @@ -4,6 +4,8 @@ use napi::Env; use napi::{JsFunction, JsObject, JsUndefined}; use napi_derive::napi; +use crate::errors::from_anyhow_error; + use super::function_results::FunctionResult; use super::runtime_ctx_manager::RuntimeContextManager; @@ -89,7 +91,7 @@ impl FunctionResultStream { .await; res.0 .map(FunctionResult::from) - .map_err(|e| napi::Error::new(napi::Status::GenericFailure, format!("{:?}", e))) + .map_err(|e| from_anyhow_error(e)) }; env.execute_tokio_future(fut, |&mut _, data| Ok(data)) diff --git a/engine/language_client_typescript/src/types/function_results.rs b/engine/language_client_typescript/src/types/function_results.rs index fa1d527ea..866819af8 100644 --- a/engine/language_client_typescript/src/types/function_results.rs +++ b/engine/language_client_typescript/src/types/function_results.rs @@ -1,6 +1,8 @@ use baml_types::BamlValue; use napi_derive::napi; +use crate::errors::from_anyhow_error; + crate::lang_wrapper!(FunctionResult, baml_runtime::FunctionResult); #[napi] @@ -19,7 +21,7 @@ impl FunctionResult { let parsed = self .inner .parsed_content() - .map_err(|e| napi::Error::new(napi::Status::GenericFailure, format!("{:?}", e)))?; + .map_err(|e| from_anyhow_error(e))?; Ok(serde_json::json!(BamlValue::from(parsed))) } diff --git a/engine/language_client_typescript/src/types/image.rs b/engine/language_client_typescript/src/types/image.rs index 78489da31..0214f4f31 100644 --- a/engine/language_client_typescript/src/types/image.rs +++ b/engine/language_client_typescript/src/types/image.rs @@ -1,6 +1,8 @@ use napi::bindgen_prelude::External; use napi_derive::napi; use serde_json::json; + +use crate::errors::invalid_argument_error; crate::lang_wrapper!(BamlImage, baml_types::BamlMedia); #[napi] @@ -34,10 +36,7 @@ impl BamlImage { pub fn as_url(&self) -> napi::Result { match &self.inner.content { baml_types::BamlMediaContent::Url(url) => Ok(url.url.clone()), - _ => Err(napi::Error::new( - napi::Status::GenericFailure, - "Image is not a URL".to_string(), - )), + _ => Err(invalid_argument_error("Image is not a URL")), } } @@ -48,10 +47,7 @@ impl BamlImage { base64.base64.clone(), self.inner.mime_type.clone().unwrap_or("".to_string()), ]), - _ => Err(napi::Error::new( - napi::Status::GenericFailure, - "Image is not base64".to_string(), - )), + _ => Err(invalid_argument_error("Image is not base64")), } } diff --git a/engine/language_client_typescript/src/types/runtime_ctx_manager.rs b/engine/language_client_typescript/src/types/runtime_ctx_manager.rs index 8fd4257de..0f09fdd83 100644 --- a/engine/language_client_typescript/src/types/runtime_ctx_manager.rs +++ b/engine/language_client_typescript/src/types/runtime_ctx_manager.rs @@ -1,6 +1,8 @@ use baml_types::BamlValue; use napi_derive::napi; +use crate::errors::invalid_argument_error; + crate::lang_wrapper!(RuntimeContextManager, baml_runtime::RuntimeContextManager); #[napi] @@ -10,17 +12,11 @@ impl RuntimeContextManager { let tags: Result = serde_json::from_value(tags); let Ok(tags) = tags else { - return Err(napi::Error::new( - napi::Status::GenericFailure, - "Invalid tags", - )); + return Err(invalid_argument_error("Invalid tags")); }; let Some(tags) = tags.as_map_owned() else { - return Err(napi::Error::new( - napi::Status::GenericFailure, - "Invalid tags", - )); + return Err(invalid_argument_error("Invalid tags")); }; self.inner.upsert_tags(tags.into_iter().collect()); diff --git a/engine/language_client_typescript/src/types/span.rs b/engine/language_client_typescript/src/types/span.rs index 10397c14e..a9e4759ff 100644 --- a/engine/language_client_typescript/src/types/span.rs +++ b/engine/language_client_typescript/src/types/span.rs @@ -3,7 +3,7 @@ use baml_types::BamlValue; use napi_derive::napi; use super::runtime_ctx_manager::RuntimeContextManager; -use crate::BamlRuntime; +use crate::{errors::invalid_argument_error, BamlRuntime}; crate::lang_wrapper!(BamlSpan, Option>, @@ -23,10 +23,7 @@ impl BamlSpan { let args: BamlValue = serde_json::from_value(args) .map_err(|e| napi::Error::new(napi::Status::GenericFailure, format!("{:?}", e)))?; let Some(args_map) = args.as_map() else { - return Err(napi::Error::new( - napi::Status::GenericFailure, - "Invalid span args", - )); + return Err(invalid_argument_error("Invalid span args")); }; let span = runtime diff --git a/integ-tests/python/tests/test_functions.py b/integ-tests/python/tests/test_functions.py index 02f7ae5a5..bd6e04914 100644 --- a/integ-tests/python/tests/test_functions.py +++ b/integ-tests/python/tests/test_functions.py @@ -7,6 +7,7 @@ load_dotenv() import baml_py +from baml_py import errors from ..baml_client import b from ..baml_client.sync_client import b as sync_b from ..baml_client.globals import ( @@ -993,3 +994,30 @@ async def test_caching(): print("Duration with caching: ", duration2) assert duration2 < duration, "Expected second call to be faster than first by a large margin." + +@pytest.mark.asyncio +async def test_arg_exceptions(): + with pytest.raises(errors.BamlInvalidArgumentError): + _ = await b.TestCaching(111) # intentionally passing an int instead of a string + + + with pytest.raises(errors.BamlClientError): + cr = baml_py.ClientRegistry() + cr.add_llm_client("MyClient", "openai", {"model": "gpt-4o-mini", "api_key": "INVALID_KEY"}) + cr.set_primary("MyClient") + await b.MyFunc( + input="My name is Harrison. My hair is black and I'm 6 feet tall.", + baml_options={"client_registry": cr}, + ) + + with pytest.raises(errors.BamlClientHttpError): + cr = baml_py.ClientRegistry() + cr.add_llm_client("MyClient", "openai", {"model": "gpt-4o-mini", "api_key": "INVALID_KEY"}) + cr.set_primary("MyClient") + await b.MyFunc( + input="My name is Harrison. My hair is black and I'm 6 feet tall.", + baml_options={"client_registry": cr}, + ) + + with pytest.raises(errors.BamlValidationError): + await b.DummyOutputFunction("dummy input") \ No newline at end of file diff --git a/integ-tests/typescript/test-report.html b/integ-tests/typescript/test-report.html index 231143164..dc233f5d6 100644 --- a/integ-tests/typescript/test-report.html +++ b/integ-tests/typescript/test-report.html @@ -257,1780 +257,4 @@ font-size: 1rem; padding: 0 0.5rem; } -

Test Report

Started: 2024-08-14 18:03:14
Suites (1)
0 passed
1 failed
0 pending
Tests (39)
37 passed
2 failed
0 pending
Integ tests > should work for all inputs
single bool
failed
0.004s
Error: LLM call failed: LLMErrorResponse { client: "Vertex", model: None, prompt: Chat([RenderedChatMessage { role: "user", parts: [Text("Return this value back to me: true")] }]), request_options: {}, start_time: SystemTime { tv_sec: 1723683794, tv_nsec: 704138000 }, latency: 140.083µs, message: "Error {\n    context: \"Failed to build request\",\n    source: \"Service account not found\",\n}", code: Other(2) }
-
-    at BamlAsyncClient.parsed [as TestFnNamedArgsSingleBool] (/Users/vbv/repos/gloo-lang/integ-tests/typescript/baml_client/async_client.ts:842:16)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:28:19)
Integ tests > should work for all inputs
single string list
passed
0.531s
Integ tests > should work for all inputs
single class
passed
0.381s
Integ tests > should work for all inputs
multiple classes
passed
0.44s
Integ tests > should work for all inputs
single enum list
passed
0.525s
Integ tests > should work for all inputs
single float
passed
0.375s
Integ tests > should work for all inputs
single int
passed
0.351s
Integ tests > should work for all inputs
single optional string
passed
0.321s
Integ tests > should work for all inputs
single map string to string
passed
0.528s
Integ tests > should work for all inputs
single map string to class
passed
0.616s
Integ tests > should work for all inputs
single map string to map
passed
0.554s
Integ tests
should work for all outputs
passed
3.147s
Integ tests
works with retries1
passed
0.925s
Integ tests
works with retries2
passed
1.908s
Integ tests
works with fallbacks
passed
1.76s
Integ tests
should work with image from url
passed
2.094s
Integ tests
should work with image from base 64
passed
1.365s
Integ tests
should work with audio base 64
passed
1.3s
Integ tests
should work with audio from url
passed
1.038s
Integ tests
should support streaming in OpenAI
passed
2.837s
Integ tests
should support streaming in Gemini
passed
7.172s
Integ tests
should support AWS
passed
2.159s
Integ tests
should support streaming in AWS
passed
2.122s
Integ tests
should support streaming without iterating
passed
2.773s
Integ tests
should support streaming in Claude
passed
0.81s
Integ tests
should support vertex
failed
0s
Error: LLM call failed: LLMErrorResponse { client: "Vertex", model: None, prompt: Chat([RenderedChatMessage { role: "user", parts: [Text("Write a nice short story about Donkey Kong")] }]), request_options: {}, start_time: SystemTime { tv_sec: 1723683830, tv_nsec: 765387000 }, latency: 15.25µs, message: "Error {\n    context: \"Failed to build request\",\n    source: \"Service account not found\",\n}", code: Other(2) }
-
-    at BamlAsyncClient.parsed [as TestVertex] (/Users/vbv/repos/gloo-lang/integ-tests/typescript/baml_client/async_client.ts:1162:16)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:262:17)
Integ tests
supports tracing sync
passed
0.002s
Integ tests
supports tracing async
passed
3.682s
Integ tests
should work with dynamic types single
passed
1.077s
Integ tests
should work with dynamic types enum
passed
0.946s
Integ tests
should work with dynamic types class
passed
1.076s
Integ tests
should work with dynamic inputs class
passed
0.544s
Integ tests
should work with dynamic inputs list
passed
0.614s
Integ tests
should work with dynamic output map
passed
0.889s
Integ tests
should work with dynamic output union
passed
2.128s
Integ tests
should work with nested classes
passed
4.147s
Integ tests
should work with dynamic client
passed
0.537s
Integ tests
should work with 'onLogEvent'
passed
1.926s
Integ tests
should work with a sync client
passed
0.699s
Console Log
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:40:15)
-    at Promise.then.completed (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:298:28)
-    at new Promise (<anonymous>)
-    at callAsyncCircusFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:231:10)
-    at _callCircusTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:316:40)
-    at _runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:252:3)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:126:9)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:121:9)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:121:9)
-    at run (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:71:3)
-    at runAndTransformResultsToJestFormat (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapterInit.js:122:21)
-    at jestAdapter (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapter.js:79:19)
-    at runTestInternal (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:367:16)
-    at runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:444:34)
calling with class
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:46:15)
got response key
-true
-52
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:132:15)
Expected error Error: (3 other previous tries)
-LLM call failed: LLMErrorResponse { client: "RetryClientConstant", model: None, prompt: Chat([RenderedChatMessage { role: "system", parts: [Text("Say a haiku")] }]), request_options: {"model": String("gpt-3.5-turbo")}, start_time: SystemTime { tv_sec: 1723683803, tv_nsec: 307847000 }, latency: 114.770958ms, message: "Request failed: {\n    \"error\": {\n        \"message\": \"Incorrect API key provided: blah. You can find your API key at https://platform.openai.com/account/api-keys.\",\n        \"type\": \"invalid_request_error\",\n        \"param\": null,\n        \"code\": \"invalid_api_key\"\n    }\n}\n", code: InvalidAuthentication }
-
-    at BamlAsyncClient.parsed [as TestRetryConstant] (/Users/vbv/repos/gloo-lang/integ-tests/typescript/baml_client/async_client.ts:1130:16)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:129:7) {
-  code: 'GenericFailure'
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:141:15)
Expected error Error: (3 other previous tries)
-LLM call failed: LLMErrorResponse { client: "RetryClientExponential", model: None, prompt: Chat([RenderedChatMessage { role: "system", parts: [Text("Say a haiku")] }]), request_options: {"model": String("gpt-3.5-turbo")}, start_time: SystemTime { tv_sec: 1723683805, tv_nsec: 244561000 }, latency: 87.42575ms, message: "Request failed: {\n    \"error\": {\n        \"message\": \"Incorrect API key provided: blahh. You can find your API key at https://platform.openai.com/account/api-keys.\",\n        \"type\": \"invalid_request_error\",\n        \"param\": null,\n        \"code\": \"invalid_api_key\"\n    }\n}\n", code: InvalidAuthentication }
-
-    at BamlAsyncClient.parsed [as TestRetryExponential] (/Users/vbv/repos/gloo-lang/integ-tests/typescript/baml_client/async_client.ts:1146:16)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:138:7) {
-  code: 'GenericFailure'
-}
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:274:15)
-    at func (/Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:69:38)
-    at AsyncLocalStorage.run (node:async_hooks:338:14)
-    at run (/Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:67:22)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:283:5)
-    at Promise.then.completed (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:298:28)
-    at new Promise (<anonymous>)
-    at callAsyncCircusFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:231:10)
-    at _callCircusTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:316:40)
-    at _runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:252:3)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:126:9)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:121:9)
-    at run (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:71:3)
-    at runAndTransformResultsToJestFormat (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapterInit.js:122:21)
-    at jestAdapter (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapter.js:79:19)
-    at runTestInternal (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:367:16)
-    at runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:444:34)
hello world
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:277:15)
-    at func (/Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:69:38)
-    at AsyncLocalStorage.run (node:async_hooks:338:14)
-    at run (/Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:67:22)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:283:5)
-    at Promise.then.completed (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:298:28)
-    at new Promise (<anonymous>)
-    at callAsyncCircusFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:231:10)
-    at _callCircusTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:316:40)
-    at _runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:252:3)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:126:9)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:121:9)
-    at run (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:71:3)
-    at runAndTransformResultsToJestFormat (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapterInit.js:122:21)
-    at jestAdapter (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapter.js:79:19)
-    at runTestInternal (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:367:16)
-    at runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:444:34)
dummyFunc returned
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:280:15)
-    at func (/Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:69:38)
-    at AsyncLocalStorage.run (node:async_hooks:338:14)
-    at run (/Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:67:22)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:283:5)
-    at Promise.then.completed (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:298:28)
-    at new Promise (<anonymous>)
-    at callAsyncCircusFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:231:10)
-    at _callCircusTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:316:40)
-    at _runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:252:3)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:126:9)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:121:9)
-    at run (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:71:3)
-    at runAndTransformResultsToJestFormat (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapterInit.js:122:21)
-    at jestAdapter (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapter.js:79:19)
-    at runTestInternal (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:367:16)
-    at runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:444:34)
dummyFunc2 returned
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 0)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 0)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:313:5)
samDummyNested nested1
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 1)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 0)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:313:5)
samDummyNested nested2
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 2)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 0)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:313:5)
samDummyNested nested3
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:306:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 0)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:313:5)
dummy hi1
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 0)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 1)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:313:5)
samDummyNested nested1
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 1)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 1)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:313:5)
samDummyNested nested2
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 2)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 1)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:313:5)
samDummyNested nested3
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:306:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 1)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:313:5)
dummy hi2
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 0)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 2)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:313:5)
samDummyNested nested1
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 1)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 2)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:313:5)
samDummyNested nested2
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 2)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 2)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:313:5)
samDummyNested nested3
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:306:15)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 2)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:313:5)
dummy hi3
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:320:15)
-    at func (/Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:44)
-    at AsyncLocalStorage.run (node:async_hooks:338:14)
-    at run (/Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:28)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:336:5)
hello world
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 0)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
samDummyNested nested1
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 1)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
samDummyNested nested2
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 2)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
samDummyNested nested3
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:306:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
dummy firstDummyFuncArg
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 0)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at /Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:325:20
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:319:17)
samDummyNested nested1
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 1)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at /Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:325:20
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:319:17)
samDummyNested nested2
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 2)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at /Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:325:20
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:319:17)
samDummyNested nested3
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:306:15)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at /Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:325:20
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:319:17)
dummy secondDummyFuncArg
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 0)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at /Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:333:20
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:319:17)
samDummyNested nested1
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 1)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at /Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:333:20
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:319:17)
samDummyNested nested2
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:295:15)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at async Promise.all (index 2)
-    at dummyFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:301:22)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at /Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:333:20
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:319:17)
samDummyNested nested3
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:306:15)
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at /Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:333:20
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:38
-    at /Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:13
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:319:17)
dummy thirdDummyFuncArg
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:339:15)
-    at func (/Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:90:44)
-    at AsyncLocalStorage.run (node:async_hooks:338:14)
-    at run (/Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:88:28)
-    at Object.<anonymous> (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:345:5)
hello world
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:349:13)
stats {"failed":0,"started":30,"finalized":30,"submitted":30,"sent":30,"done":30}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:373:13)
[
-  {
-    name: 'Harrison',
-    hair_color: 'BLACK',
-    last_name: null,
-    height: 1.83,
-    hobbies: [ 'SPORTS' ]
-  }
-]
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:430:13)
-    at Promise.then.completed (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:298:28)
-    at new Promise (<anonymous>)
-    at callAsyncCircusFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:231:10)
-    at _callCircusTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:316:40)
-    at _runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:252:3)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:126:9)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:121:9)
-    at run (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:71:3)
-    at runAndTransformResultsToJestFormat (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapterInit.js:122:21)
-    at jestAdapter (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapter.js:79:19)
-    at runTestInternal (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:367:16)
-    at runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:444:34)
[
-  [
-    'hair_color',
-    ClassPropertyBuilder { bldr: ClassPropertyBuilder {} }
-  ],
-  [
-    'attributes',
-    ClassPropertyBuilder { bldr: ClassPropertyBuilder {} }
-  ]
-]
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:432:15)
-    at Promise.then.completed (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:298:28)
-    at new Promise (<anonymous>)
-    at callAsyncCircusFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:231:10)
-    at _callCircusTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:316:40)
-    at _runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:252:3)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:126:9)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:121:9)
-    at run (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:71:3)
-    at runAndTransformResultsToJestFormat (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapterInit.js:122:21)
-    at jestAdapter (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapter.js:79:19)
-    at runTestInternal (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:367:16)
-    at runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:444:34)
Property: hair_color
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:432:15)
-    at Promise.then.completed (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:298:28)
-    at new Promise (<anonymous>)
-    at callAsyncCircusFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:231:10)
-    at _callCircusTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:316:40)
-    at _runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:252:3)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:126:9)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:121:9)
-    at run (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:71:3)
-    at runAndTransformResultsToJestFormat (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapterInit.js:122:21)
-    at jestAdapter (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapter.js:79:19)
-    at runTestInternal (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:367:16)
-    at runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:444:34)
Property: attributes
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:440:13)
final  {
-  hair_color: 'black',
-  attributes: { eye_color: 'blue', height: '6 feet', facial_hair: 'beard' }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:464:13)
-    at Promise.then.completed (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:298:28)
-    at new Promise (<anonymous>)
-    at callAsyncCircusFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:231:10)
-    at _callCircusTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:316:40)
-    at _runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:252:3)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:126:9)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:121:9)
-    at run (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:71:3)
-    at runAndTransformResultsToJestFormat (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapterInit.js:122:21)
-    at jestAdapter (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapter.js:79:19)
-    at runTestInternal (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:367:16)
-    at runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:444:34)
[
-  [
-    'hair_color',
-    ClassPropertyBuilder { bldr: ClassPropertyBuilder {} }
-  ],
-  [
-    'attributes',
-    ClassPropertyBuilder { bldr: ClassPropertyBuilder {} }
-  ],
-  [ 'height', ClassPropertyBuilder { bldr: ClassPropertyBuilder {} } ]
-]
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:466:15)
-    at Promise.then.completed (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:298:28)
-    at new Promise (<anonymous>)
-    at callAsyncCircusFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:231:10)
-    at _callCircusTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:316:40)
-    at _runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:252:3)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:126:9)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:121:9)
-    at run (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:71:3)
-    at runAndTransformResultsToJestFormat (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapterInit.js:122:21)
-    at jestAdapter (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapter.js:79:19)
-    at runTestInternal (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:367:16)
-    at runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:444:34)
Property: hair_color
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:466:15)
-    at Promise.then.completed (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:298:28)
-    at new Promise (<anonymous>)
-    at callAsyncCircusFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:231:10)
-    at _callCircusTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:316:40)
-    at _runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:252:3)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:126:9)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:121:9)
-    at run (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:71:3)
-    at runAndTransformResultsToJestFormat (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapterInit.js:122:21)
-    at jestAdapter (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapter.js:79:19)
-    at runTestInternal (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:367:16)
-    at runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:444:34)
Property: attributes
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:466:15)
-    at Promise.then.completed (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:298:28)
-    at new Promise (<anonymous>)
-    at callAsyncCircusFn (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/utils.js:231:10)
-    at _callCircusTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:316:40)
-    at _runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:252:3)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:126:9)
-    at _runTestsForDescribeBlock (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:121:9)
-    at run (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/run.js:71:3)
-    at runAndTransformResultsToJestFormat (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapterInit.js:122:21)
-    at jestAdapter (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-circus@29.7.0/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapter.js:79:19)
-    at runTestInternal (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:367:16)
-    at runTest (/Users/vbv/repos/gloo-lang/integ-tests/typescript/node_modules/.pnpm/jest-runner@29.7.0/node_modules/jest-runner/build/runTest.js:444:34)
Property: height
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:474:13)
final  {
-  hair_color: 'black',
-  attributes: { eye_color: 'blue', facial_hair: 'beard', age: '30 years old' },
-  height: { feet: 6, inches: null }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:485:13)
final  {
-  hair_color: 'black',
-  attributes: { eye_color: 'blue', facial_hair: 'beard', age: '30 years old' },
-  height: { meters: 1.8 }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: null, prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: '', prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: null }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: null, prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: null, prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: null, prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: null, prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: null, prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: null, prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: null, prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: '', prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: 'World', prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: 'World', prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: 'World', prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: 'World', prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: 'World', prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: 'World', prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: 'World', prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: 'World', prop2: null, inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg { prop1: 'Hello', prop2: { prop1: 'World', prop2: '', inner: null } }
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: { prop1: 'World', prop2: 'JSON', inner: null }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: { prop1: 'World', prop2: 'JSON is', inner: null }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: { prop1: 'World', prop2: 'JSON is cool', inner: null }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: { prop1: 'World', prop2: 'JSON is cool', inner: null }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: { prop1: 'World', prop2: 'JSON is cool', inner: null }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: { prop1: 'World', prop2: 'JSON is cool', inner: null }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: { prop1: 'World', prop2: 'JSON is cool', inner: null }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: { prop1: 'World', prop2: 'JSON is cool', inner: null }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: { prop1: 'World', prop2: 'JSON is cool', inner: null }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: null, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: null, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: null, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: null, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: null, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: null, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: null, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: null, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 4, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: null }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.1 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
-    at runNextTicks (node:internal/process/task_queues:60:5)
-    at listOnTimeout (node:internal/timers:538:9)
-    at processTimers (node:internal/timers:512:7)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at Object.log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:498:15)
msg {
-  prop1: 'Hello',
-  prop2: {
-    prop1: 'World',
-    prop2: 'JSON is cool',
-    inner: { prop2: 42, prop3: 3.14 }
-  }
-}
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:523:15)
-    at callback (/Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:56:17)
onLogEvent {
-  metadata: {
-    eventId: 'bc3e3903-74f4-47b4-b9cf-ad812a2dae65',
-    rootEventId: 'bc3e3903-74f4-47b4-b9cf-ad812a2dae65'
-  },
-  prompt: '[\n' +
-    '  {\n' +
-    '    "role": "system",\n' +
-    '    "content": [\n' +
-    '      {\n' +
-    '        "text": "Return this value back to me: [\\"a\\", \\"b\\", \\"c\\"]"\n' +
-    '      }\n' +
-    '    ]\n' +
-    '  }\n' +
-    ']',
-  rawOutput: 'Sure, here is the value: ["a", "b", "c"]',
-  parsedOutput: 'Sure, here is the value: ["a", "b", "c"]',
-  startTime: '2024-08-15T01:04:06.830Z'
-}
    at log (/Users/vbv/repos/gloo-lang/integ-tests/typescript/tests/integ-tests.test.ts:523:15)
-    at callback (/Users/vbv/repos/gloo-lang/engine/language_client_typescript/async_context_vars.js:56:17)
onLogEvent {
-  metadata: {
-    eventId: 'b7fe20c9-b2b9-4de6-bc6d-fd1a6cdf1177',
-    rootEventId: 'b7fe20c9-b2b9-4de6-bc6d-fd1a6cdf1177'
-  },
-  prompt: '[\n' +
-    '  {\n' +
-    '    "role": "system",\n' +
-    '    "content": [\n' +
-    '      {\n' +
-    '        "text": "Return this value back to me: [\\"d\\", \\"e\\", \\"f\\"]"\n' +
-    '      }\n' +
-    '    ]\n' +
-    '  }\n' +
-    ']',
-  rawOutput: '["d", "e", "f"]',
-  parsedOutput: '["d", "e", "f"]',
-  startTime: '2024-08-15T01:04:07.525Z'
-}
\ No newline at end of file +

Test Report

Started: 2024-08-27 00:31:58
Suites (1)
1 passed
0 failed
0 pending
Tests (44)
1 passed
0 failed
43 pending
Integ tests > should work for all inputs
single bool
pending
0s
Integ tests > should work for all inputs
single string list
pending
0s
Integ tests > should work for all inputs
single class
pending
0s
Integ tests > should work for all inputs
multiple classes
pending
0s
Integ tests > should work for all inputs
single enum list
pending
0s
Integ tests > should work for all inputs
single float
pending
0s
Integ tests > should work for all inputs
single int
pending
0s
Integ tests > should work for all inputs
single optional string
pending
0s
Integ tests > should work for all inputs
single map string to string
pending
0s
Integ tests > should work for all inputs
single map string to class
pending
0s
Integ tests > should work for all inputs
single map string to map
pending
0s
Integ tests
should work for all outputs
pending
0s
Integ tests
works with retries1
pending
0s
Integ tests
works with retries2
pending
0s
Integ tests
works with fallbacks
pending
0s
Integ tests
should work with image from url
pending
0s
Integ tests
should work with image from base 64
pending
0s
Integ tests
should work with audio base 64
pending
0s
Integ tests
should work with audio from url
pending
0s
Integ tests
should support streaming in OpenAI
pending
0s
Integ tests
should support streaming in Gemini
pending
0s
Integ tests
should support AWS
pending
0s
Integ tests
should support streaming in AWS
pending
0s
Integ tests
should support OpenAI shorthand
pending
0s
Integ tests
should support OpenAI shorthand streaming
pending
0s
Integ tests
should support anthropic shorthand
pending
0s
Integ tests
should support anthropic shorthand streaming
pending
0s
Integ tests
should support streaming without iterating
pending
0s
Integ tests
should support streaming in Claude
pending
0s
Integ tests
should support vertex
pending
0s
Integ tests
supports tracing sync
pending
0s
Integ tests
supports tracing async
pending
0s
Integ tests
should work with dynamic types single
pending
0s
Integ tests
should work with dynamic types enum
pending
0s
Integ tests
should work with dynamic types class
pending
0s
Integ tests
should work with dynamic inputs class
pending
0s
Integ tests
should work with dynamic inputs list
pending
0s
Integ tests
should work with dynamic output map
pending
0s
Integ tests
should work with dynamic output union
pending
0s
Integ tests
should work with nested classes
pending
0s
Integ tests
should work with dynamic client
pending
0s
Integ tests
should work with 'onLogEvent'
pending
0s
Integ tests
should work with a sync client
pending
0s
Integ tests
should raise an error when appropriate
passed
1.145s
\ No newline at end of file diff --git a/integ-tests/typescript/tests/integ-tests.test.ts b/integ-tests/typescript/tests/integ-tests.test.ts index 6e8485ff5..9b0dfa3a3 100644 --- a/integ-tests/typescript/tests/integ-tests.test.ts +++ b/integ-tests/typescript/tests/integ-tests.test.ts @@ -554,6 +554,30 @@ describe('Integ tests', () => { const res = b_sync.TestFnNamedArgsSingleStringList(['a', 'b', 'c']) expect(res).toContain('a') }) + + it('should raise an error when appropriate', async () => { + await expect(async () => { + await b.TestCaching(111 as unknown as string) // intentionally passing an int instead of a string + }).rejects.toThrow('BamlInvalidArgumentError') + + await expect(async () => { + const cr = new ClientRegistry() + cr.addLlmClient('MyClient', 'openai', { model: 'gpt-4o-mini', api_key: 'INVALID_KEY' }) + cr.setPrimary('MyClient') + await b.MyFunc("My name is Harrison. My hair is black and I'm 6 feet tall.", { clientRegistry: cr }) + }).rejects.toThrow('BamlClientError') + + await expect(async () => { + const cr = new ClientRegistry() + cr.addLlmClient('MyClient', 'openai', { model: 'gpt-4o-mini', api_key: 'INVALID_KEY' }) + cr.setPrimary('MyClient') + await b.MyFunc("My name is Harrison. My hair is black and I'm 6 feet tall.", { clientRegistry: cr }) + }).rejects.toThrow('BamlClientHttpError') + + await expect(async () => { + await b.DummyOutputFunction('dummy input') + }).rejects.toThrow('BamlValidationError') + }) }) interface MyInterface {