From 9b64b122c4c41f5b47446c30763cb88c40931a40 Mon Sep 17 00:00:00 2001 From: Pileks Date: Wed, 12 Apr 2023 19:47:27 +0200 Subject: [PATCH 01/19] import newer logger in typescript template --- .../templates/app/typescript/schema.graphql | 2 +- .../templates/app/typescript/src/index.ts | 53 +++++++++++++------ 2 files changed, 37 insertions(+), 18 deletions(-) diff --git a/packages/templates/app/typescript/schema.graphql b/packages/templates/app/typescript/schema.graphql index b6fc4770f6..95d5ea5cee 100644 --- a/packages/templates/app/typescript/schema.graphql +++ b/packages/templates/app/typescript/schema.graphql @@ -1,2 +1,2 @@ -#import * into HelloWorld from "ens/helloworld.polytest.eth" +#import * into Logger from "ens/wraps.eth:logger@1.0.0" #import * into Ethereum from "ens/wraps.eth:ethereum@1.0.0" diff --git a/packages/templates/app/typescript/src/index.ts b/packages/templates/app/typescript/src/index.ts index 021d465362..5ed2345ab7 100644 --- a/packages/templates/app/typescript/src/index.ts +++ b/packages/templates/app/typescript/src/index.ts @@ -1,4 +1,8 @@ -import { HelloWorld_Module, Ethereum_Module } from "./wrap"; +import { + Logger_Module, + Ethereum_Module, + Logger_Logger_LogLevelEnum, +} from "./wrap"; import { PolywrapClient } from "@polywrap/client-js"; @@ -7,22 +11,37 @@ const client = new PolywrapClient(); async function main() { console.log("Invoking: logMessage"); - await HelloWorld_Module.logMessage({ - message: "Hello there" - }, client); - - await HelloWorld_Module.logMessage({ - message: "Hello again" - }, client); - - await HelloWorld_Module.logMessage({ - message: "One last time..." - }, client); - - const result = await Ethereum_Module.encodeParams({ - types: ["address", "uint256"], - values: ["0xB1B7586656116D546033e3bAFF69BFcD6592225E", "500"] - }, client); + await Logger_Module.log( + { + message: "Hello there", + level: Logger_Logger_LogLevelEnum.INFO, + }, + client + ); + + await Logger_Module.log( + { + message: "Hello again", + level: Logger_Logger_LogLevelEnum.INFO, + }, + client + ); + + await Logger_Module.log( + { + message: "One last time...", + level: Logger_Logger_LogLevelEnum.INFO, + }, + client + ); + + const result = await Ethereum_Module.encodeParams( + { + types: ["address", "uint256"], + values: ["0xB1B7586656116D546033e3bAFF69BFcD6592225E", "500"], + }, + client + ); if (result.ok) { console.log(`Ethereum_Module.encodeParams:\n${result.value}`); From 104e68686fe2fb04f5c0f10344769a97e1dae1f3 Mon Sep 17 00:00:00 2001 From: dOrgJelli Date: Wed, 12 Apr 2023 17:26:36 -0500 Subject: [PATCH 02/19] chore: use logging wrap --- .../templates/app/typescript/schema.graphql | 2 +- .../templates/app/typescript/src/index.ts | 41 +++++++------------ 2 files changed, 16 insertions(+), 27 deletions(-) diff --git a/packages/templates/app/typescript/schema.graphql b/packages/templates/app/typescript/schema.graphql index 95d5ea5cee..2b89a5497f 100644 --- a/packages/templates/app/typescript/schema.graphql +++ b/packages/templates/app/typescript/schema.graphql @@ -1,2 +1,2 @@ -#import * into Logger from "ens/wraps.eth:logger@1.0.0" +#import * into Logging from "ens/wraps.eth:logging@1.0.0" #import * into Ethereum from "ens/wraps.eth:ethereum@1.0.0" diff --git a/packages/templates/app/typescript/src/index.ts b/packages/templates/app/typescript/src/index.ts index 5ed2345ab7..f97a17cd1c 100644 --- a/packages/templates/app/typescript/src/index.ts +++ b/packages/templates/app/typescript/src/index.ts @@ -1,7 +1,6 @@ import { - Logger_Module, + Logging_Module, Ethereum_Module, - Logger_Logger_LogLevelEnum, } from "./wrap"; import { PolywrapClient } from "@polywrap/client-js"; @@ -9,31 +8,21 @@ import { PolywrapClient } from "@polywrap/client-js"; const client = new PolywrapClient(); async function main() { - console.log("Invoking: logMessage"); + console.log("Invoking: Logging.info(...)"); - await Logger_Module.log( - { - message: "Hello there", - level: Logger_Logger_LogLevelEnum.INFO, - }, - client - ); + await Logging_Module.info({ + message: "Hello there", + }, client); - await Logger_Module.log( - { - message: "Hello again", - level: Logger_Logger_LogLevelEnum.INFO, - }, - client - ); + await Logging_Module.info({ + message: "Hello again", + }, client); - await Logger_Module.log( - { - message: "One last time...", - level: Logger_Logger_LogLevelEnum.INFO, - }, - client - ); + await Logging_Module.info({ + message: "One last time...", + }, client); + + console.log("Invoking: Ethereum.encodeParams(...)"); const result = await Ethereum_Module.encodeParams( { @@ -44,9 +33,9 @@ async function main() { ); if (result.ok) { - console.log(`Ethereum_Module.encodeParams:\n${result.value}`); + console.log(`Ethereum.encodeParams:\n${result.value}`); } else { - console.log(`Error - Ethereum_Module.encodeParams:\n${result.error}`); + console.log(`Error - Ethereum.encodeParams:\n${result.error}`); } } From 74848f4882e4b185367f34cb1a99e0407286dc9e Mon Sep 17 00:00:00 2001 From: krisbitney Date: Fri, 14 Apr 2023 09:36:35 +0000 Subject: [PATCH 03/19] removed top-level docker property during build manifest migration --- .../src/formats/polywrap.build/migrators/0.1.0_to_0.2.0.ts | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/packages/js/manifests/polywrap/src/formats/polywrap.build/migrators/0.1.0_to_0.2.0.ts b/packages/js/manifests/polywrap/src/formats/polywrap.build/migrators/0.1.0_to_0.2.0.ts index f076051a3d..070eb39853 100644 --- a/packages/js/manifests/polywrap/src/formats/polywrap.build/migrators/0.1.0_to_0.2.0.ts +++ b/packages/js/manifests/polywrap/src/formats/polywrap.build/migrators/0.1.0_to_0.2.0.ts @@ -5,7 +5,8 @@ import { BuildManifest as NewManifest } from "../0.2.0"; export function migrate(old: OldManifest): NewManifest { return { - ...old, + config: old.config, + linked_packages: old.linked_packages, __type: "BuildManifest", format: "0.2.0", strategies: { From 49390a273f0db7cfea7f5a56a9773080ae477b88 Mon Sep 17 00:00:00 2001 From: krisbitney Date: Sat, 15 Apr 2023 11:19:18 +0000 Subject: [PATCH 04/19] removed possibility of empty object assigned to extension property in project manifest migrator 0.2.0_to_0.3.0.ts --- .../src/formats/polywrap/migrators/0.2.0_to_0.3.0.ts | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/packages/js/manifests/polywrap/src/formats/polywrap/migrators/0.2.0_to_0.3.0.ts b/packages/js/manifests/polywrap/src/formats/polywrap/migrators/0.2.0_to_0.3.0.ts index 5c9398f8b5..f3f862628e 100644 --- a/packages/js/manifests/polywrap/src/formats/polywrap/migrators/0.2.0_to_0.3.0.ts +++ b/packages/js/manifests/polywrap/src/formats/polywrap/migrators/0.2.0_to_0.3.0.ts @@ -1,7 +1,8 @@ -import { ILogger } from "@polywrap/logging-js"; import { PolywrapManifest as OldManifest } from "../0.2.0"; import { PolywrapManifest as NewManifest } from "../0.3.0"; +import { ILogger } from "@polywrap/logging-js"; + export function migrate(migrate: OldManifest, logger?: ILogger): NewManifest { if (migrate.extensions?.meta) { logger?.warn( @@ -21,8 +22,11 @@ export function migrate(migrate: OldManifest, logger?: ILogger): NewManifest { ); delete migrate.extensions.infra; } + const hasExtensions = + migrate.extensions && Object.keys(migrate.extensions).length > 0; return { ...migrate, format: "0.3.0", + extensions: hasExtensions ? migrate.extensions : undefined, }; } From c7c06fa911d9eafebda642763aeed35f105646eb Mon Sep 17 00:00:00 2001 From: namesty Date: Mon, 17 Apr 2023 19:49:55 +0200 Subject: [PATCH 05/19] (feat): added env argument --- .../bindings/rust/plugin/templates/module-rs.mustache | 9 ++------- 1 file changed, 2 insertions(+), 7 deletions(-) diff --git a/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache b/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache index 4713defb93..ae80d2d635 100644 --- a/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache +++ b/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache @@ -2,12 +2,11 @@ /// All modifications will be overwritten. use std::sync::Arc; -use polywrap_core::invoke::Invoker; +use polywrap_core::{invoke::Invoker, env::Env}; use polywrap_plugin::error::PluginError; use polywrap_plugin::module::PluginModule; use serde::{Serialize, Deserialize}; use super::types::*; -use async_trait::async_trait; {{#moduleType}} {{#methods}} @@ -20,14 +19,10 @@ pub struct Args{{#toUpper}}{{name}}{{/toUpper}} { {{/methods}} {{/moduleType}} -#[async_trait] pub trait Module: PluginModule { {{#moduleType}} {{#methods}} - async fn {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}(&mut self, args: &Args{{#toUpper}}{{name}}{{/toUpper}}, invoker: Arc) -> Result<{{#return}}{{#toWasm}}{{toGraphQLType}}{{/toWasm}}{{/return}}, PluginError>; - {{^last}} - - {{/last}} + fn {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}(&mut self, args: &Args{{#toUpper}}{{name}}{{/toUpper}}, invoker: Arc{{#env}}, env: {{^required}}Option<{{/required}}Env{{^required}}>{{/required}}) -> Result<{{#return}}{{#toWasm}}{{toGraphQLType}}{{/toWasm}}{{/return}}, PluginError>; {{/methods}} {{/moduleType}} } From 059dca3a7a69fa4b1a87a5f582b748d69b5e9198 Mon Sep 17 00:00:00 2001 From: namesty Date: Tue, 18 Apr 2023 00:45:11 +0200 Subject: [PATCH 06/19] (chore): removed async. Added proper Env signature --- .../src/bindings/rust/plugin/templates/module-rs.mustache | 4 ++-- .../src/bindings/rust/plugin/templates/types-rs.mustache | 6 ++---- 2 files changed, 4 insertions(+), 6 deletions(-) diff --git a/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache b/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache index ae80d2d635..8953dbf80c 100644 --- a/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache +++ b/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache @@ -2,7 +2,7 @@ /// All modifications will be overwritten. use std::sync::Arc; -use polywrap_core::{invoke::Invoker, env::Env}; +use polywrap_core::{invoke::Invoker}; use polywrap_plugin::error::PluginError; use polywrap_plugin::module::PluginModule; use serde::{Serialize, Deserialize}; @@ -22,7 +22,7 @@ pub struct Args{{#toUpper}}{{name}}{{/toUpper}} { pub trait Module: PluginModule { {{#moduleType}} {{#methods}} - fn {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}(&mut self, args: &Args{{#toUpper}}{{name}}{{/toUpper}}, invoker: Arc{{#env}}, env: {{^required}}Option<{{/required}}Env{{^required}}>{{/required}}) -> Result<{{#return}}{{#toWasm}}{{toGraphQLType}}{{/toWasm}}{{/return}}, PluginError>; + fn {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}(&mut self, args: &Args{{#toUpper}}{{name}}{{/toUpper}}, invoker: Arc{{#env}}, env: {{^required}}Option<{{/required}}Env{{^required}}>{{/required}}{{/env}}) -> Result<{{#return}}{{#toWasm}}{{toGraphQLType}}{{/toWasm}}{{/return}}, PluginError>; {{/methods}} {{/moduleType}} } diff --git a/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache b/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache index 3b2f22a95b..67ca04c707 100644 --- a/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache +++ b/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache @@ -114,7 +114,7 @@ impl {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { } {{#methods}} - pub async fn {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}(args: &{{#toUpper}}{{parent.type}}{{/toUpper}}Args{{#toUpper}}{{name}}{{/toUpper}}, invoker: Arc) -> Result<{{#return}}{{#toWasm}}{{toGraphQLType}}{{/toWasm}}{{/return}}, PluginError> { + pub fn {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}(args: &{{#toUpper}}{{parent.type}}{{/toUpper}}Args{{#toUpper}}{{name}}{{/toUpper}}, invoker: Arc) -> Result<{{#return}}{{#toWasm}}{{toGraphQLType}}{{/toWasm}}{{/return}}, PluginError> { let uri = {{#parent}}{{#toUpper}}{{type}}{{/toUpper}}{{/parent}}::URI; let serialized_args = serialize(args.clone()).unwrap(); let opt_args = Some(serialized_args.as_slice()); @@ -126,7 +126,6 @@ impl {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { None, None ) - .await .map_err(|e| PluginError::SubinvocationError { uri: uri.to_string(), method: "{{name}}".to_string(), @@ -156,7 +155,7 @@ impl<'a> {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}}<'a } {{#methods}} - pub async fn {{#toLower}}{{name}}{{/toLower}}(&self, args: &{{#toUpper}}{{parent.type}}{{/toUpper}}Args{{#toUpper}}{{name}}{{/toUpper}}) -> Result<{{#return}}{{#toWasm}}{{toGraphQLType}}{{/toWasm}}{{/return}}, PluginError> { + pub fn {{#toLower}}{{name}}{{/toLower}}(&self, args: &{{#toUpper}}{{parent.type}}{{/toUpper}}Args{{#toUpper}}{{name}}{{/toUpper}}) -> Result<{{#return}}{{#toWasm}}{{toGraphQLType}}{{/toWasm}}{{/return}}, PluginError> { let uri = self.uri; let serialized_args = serialize(args.clone()).unwrap(); let result = invoker.invoke_raw( @@ -165,7 +164,6 @@ impl<'a> {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}}<'a serialized_args, None, None - .await .map_err(|e| PluginError::SubinvocationError { uri: uri.to_string(), method: "{{name}}".to_string(), From 1f4332987134fcfc6e3a2cfa3da2cac67de6846b Mon Sep 17 00:00:00 2001 From: namesty Date: Tue, 18 Apr 2023 00:45:24 +0200 Subject: [PATCH 07/19] (chore): use GenericMap extension in bindings --- .../bind/src/bindings/rust/plugin/templates/types-rs.mustache | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache b/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache index 67ca04c707..9f1936ab23 100644 --- a/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache +++ b/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache @@ -7,7 +7,7 @@ use serde::{Serialize, Deserialize}; use num_bigint::BigInt; use bigdecimal::BigDecimal as BigNumber; use serde_json as JSON; -use std::collections::BTreeMap as Map; +use polywrap_msgpack::extensions::generic_map::GenericMap as Map; {{#importedModuleTypes}} use std::sync::Arc; use polywrap_msgpack::{decode, serialize}; From a978ff4c0b20de16c20d52ce43f1719274326c00 Mon Sep 17 00:00:00 2001 From: dOrgJelli Date: Mon, 17 Apr 2023 18:10:30 -0500 Subject: [PATCH 08/19] chore: remove dependencies folder --- dependencies/package.json | 8 -------- package.json | 5 ++--- 2 files changed, 2 insertions(+), 11 deletions(-) delete mode 100644 dependencies/package.json diff --git a/dependencies/package.json b/dependencies/package.json deleted file mode 100644 index 731cfbb5f0..0000000000 --- a/dependencies/package.json +++ /dev/null @@ -1,8 +0,0 @@ -{ - "dependencies": { - "polywrap": "~0.10.0-pre" - }, - "resolutions": { - "colors": "1.4.0" - } -} \ No newline at end of file diff --git a/package.json b/package.json index b04866d46a..007709910f 100644 --- a/package.json +++ b/package.json @@ -1,11 +1,11 @@ { "name": "root", - "description": "Polywrap Monorepo", + "description": "Polywrap Toolchain", "license": "MIT", "private": true, "repository": { "type": "git", - "url": "https://github.com/polywrap/monorepo.git" + "url": "https://github.com/polywrap/toolchain.git" }, "workspaces": { "packages": [ @@ -15,7 +15,6 @@ "./packages/schema/**", "./packages/templates/**", "./packages/test-cases", - "./packages/test-env/**", "./packages/wasm/**" ] }, From b7202b97568f21728ad4c25936d06bcd15abe9de Mon Sep 17 00:00:00 2001 From: dOrgJelli Date: Mon, 17 Apr 2023 21:07:54 -0500 Subject: [PATCH 09/19] chore: fix rust plugin bindings & tests --- .../rust/plugin/templates/module-rs.mustache | 3 ++ .../rust/plugin/templates/types-rs.mustache | 1 + .../bind/sanity/output/plugin-rs/module.rs | 12 +++-- .../bind/sanity/output/plugin-rs/types.rs | 14 +++--- yarn.lock | 45 +++++++++++-------- 5 files changed, 42 insertions(+), 33 deletions(-) diff --git a/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache b/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache index 8953dbf80c..1ecca04168 100644 --- a/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache +++ b/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache @@ -23,6 +23,9 @@ pub trait Module: PluginModule { {{#moduleType}} {{#methods}} fn {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}(&mut self, args: &Args{{#toUpper}}{{name}}{{/toUpper}}, invoker: Arc{{#env}}, env: {{^required}}Option<{{/required}}Env{{^required}}>{{/required}}{{/env}}) -> Result<{{#return}}{{#toWasm}}{{toGraphQLType}}{{/toWasm}}{{/return}}, PluginError>; + {{^last}} + + {{/last}} {{/methods}} {{/moduleType}} } diff --git a/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache b/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache index 9f1936ab23..50c1d9de5d 100644 --- a/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache +++ b/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache @@ -164,6 +164,7 @@ impl<'a> {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}}<'a serialized_args, None, None + ) .map_err(|e| PluginError::SubinvocationError { uri: uri.to_string(), method: "{{name}}".to_string(), diff --git a/packages/test-cases/cases/bind/sanity/output/plugin-rs/module.rs b/packages/test-cases/cases/bind/sanity/output/plugin-rs/module.rs index 38c60ab6c9..13a34bfe19 100644 --- a/packages/test-cases/cases/bind/sanity/output/plugin-rs/module.rs +++ b/packages/test-cases/cases/bind/sanity/output/plugin-rs/module.rs @@ -2,12 +2,11 @@ /// All modifications will be overwritten. use std::sync::Arc; -use polywrap_core::invoke::Invoker; +use polywrap_core::{invoke::Invoker}; use polywrap_plugin::error::PluginError; use polywrap_plugin::module::PluginModule; use serde::{Serialize, Deserialize}; use super::types::*; -use async_trait::async_trait; #[derive(Clone, Debug, Deserialize, Serialize)] pub struct ArgsModuleMethod { @@ -46,13 +45,12 @@ pub struct ArgsIf { pub _if: Else, } -#[async_trait] pub trait Module: PluginModule { - async fn module_method(&mut self, args: &ArgsModuleMethod, invoker: Arc) -> Result; + fn module_method(&mut self, args: &ArgsModuleMethod, invoker: Arc) -> Result; - async fn object_method(&mut self, args: &ArgsObjectMethod, invoker: Arc) -> Result, PluginError>; + fn object_method(&mut self, args: &ArgsObjectMethod, invoker: Arc, env: Env) -> Result, PluginError>; - async fn optional_env_method(&mut self, args: &ArgsOptionalEnvMethod, invoker: Arc) -> Result, PluginError>; + fn optional_env_method(&mut self, args: &ArgsOptionalEnvMethod, invoker: Arc, env: Option) -> Result, PluginError>; - async fn _if(&mut self, args: &ArgsIf, invoker: Arc) -> Result; + fn _if(&mut self, args: &ArgsIf, invoker: Arc) -> Result; } diff --git a/packages/test-cases/cases/bind/sanity/output/plugin-rs/types.rs b/packages/test-cases/cases/bind/sanity/output/plugin-rs/types.rs index 37087d9458..67e2f1be85 100644 --- a/packages/test-cases/cases/bind/sanity/output/plugin-rs/types.rs +++ b/packages/test-cases/cases/bind/sanity/output/plugin-rs/types.rs @@ -7,7 +7,7 @@ use serde::{Serialize, Deserialize}; use num_bigint::BigInt; use bigdecimal::BigDecimal as BigNumber; use serde_json as JSON; -use std::collections::BTreeMap as Map; +use polywrap_msgpack::extensions::generic_map::GenericMap as Map; use std::sync::Arc; use polywrap_msgpack::{decode, serialize}; use polywrap_core::{invoke::{Invoker}, uri::Uri}; @@ -187,7 +187,7 @@ impl<'a> TestImportModule<'a> { TestImportModule { uri: uri } } - pub async fn imported_method(&self, args: &TestImportModuleArgsImportedMethod) -> Result, PluginError> { + pub fn imported_method(&self, args: &TestImportModuleArgsImportedMethod) -> Result, PluginError> { let uri = self.uri; let serialized_args = serialize(args.clone()).unwrap(); let result = invoker.invoke_raw( @@ -196,7 +196,7 @@ impl<'a> TestImportModule<'a> { serialized_args, None, None - .await + ) .map_err(|e| PluginError::SubinvocationError { uri: uri.to_string(), method: "importedMethod".to_string(), @@ -207,7 +207,7 @@ impl<'a> TestImportModule<'a> { Ok(Some(decode(result.as_slice())?)) } - pub async fn another_method(&self, args: &TestImportModuleArgsAnotherMethod) -> Result { + pub fn another_method(&self, args: &TestImportModuleArgsAnotherMethod) -> Result { let uri = self.uri; let serialized_args = serialize(args.clone()).unwrap(); let result = invoker.invoke_raw( @@ -216,7 +216,7 @@ impl<'a> TestImportModule<'a> { serialized_args, None, None - .await + ) .map_err(|e| PluginError::SubinvocationError { uri: uri.to_string(), method: "anotherMethod".to_string(), @@ -227,7 +227,7 @@ impl<'a> TestImportModule<'a> { Ok(decode(result.as_slice())?) } - pub async fn returns_array_of_enums(&self, args: &TestImportModuleArgsReturnsArrayOfEnums) -> Result>, PluginError> { + pub fn returns_array_of_enums(&self, args: &TestImportModuleArgsReturnsArrayOfEnums) -> Result>, PluginError> { let uri = self.uri; let serialized_args = serialize(args.clone()).unwrap(); let result = invoker.invoke_raw( @@ -236,7 +236,7 @@ impl<'a> TestImportModule<'a> { serialized_args, None, None - .await + ) .map_err(|e| PluginError::SubinvocationError { uri: uri.to_string(), method: "returnsArrayOfEnums".to_string(), diff --git a/yarn.lock b/yarn.lock index be8b9082a6..5abecd74b9 100644 --- a/yarn.lock +++ b/yarn.lock @@ -2516,9 +2516,9 @@ integrity sha512-0d5Wd09ItQWH1qFbEyQ7oTQ3GZrMfth5JkbN3EvTKLXcHLRDSXeLnlvlOn0wvxVIwK5o2M8JzP/OWz7T3NRsbw== "@types/lodash@^4.14.182": - version "4.14.192" - resolved "https://registry.yarnpkg.com/@types/lodash/-/lodash-4.14.192.tgz#5790406361a2852d332d41635d927f1600811285" - integrity sha512-km+Vyn3BYm5ytMO13k9KTp27O75rbQ0NFw+U//g+PX7VZyjCioXaRFisqSIJRECljcTv73G3i6BpglNGHgUQ5A== + version "4.14.194" + resolved "https://registry.yarnpkg.com/@types/lodash/-/lodash-4.14.194.tgz#b71eb6f7a0ff11bff59fc987134a093029258a76" + integrity sha512-r22s9tAS7imvBt2lyHC9B8AGwWnXaYb1tY09oyLkXDs4vArpYJzw09nj8MLx5VfciBPGIb+ZwG0ssYnEPJxn/g== "@types/minimatch@*", "@types/minimatch@^5.1.2": version "5.1.2" @@ -3536,9 +3536,9 @@ camelcase@^6.0.0: integrity sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA== caniuse-lite@^1.0.30001449: - version "1.0.30001478" - resolved "https://registry.yarnpkg.com/caniuse-lite/-/caniuse-lite-1.0.30001478.tgz#0ef8a1cf8b16be47a0f9fc4ecfc952232724b32a" - integrity sha512-gMhDyXGItTHipJj2ApIvR+iVB5hd0KP3svMWWXDvZOmjzJJassGLMfxRkQCSYgGd2gtdL/ReeiyvMSFD1Ss6Mw== + version "1.0.30001480" + resolved "https://registry.yarnpkg.com/caniuse-lite/-/caniuse-lite-1.0.30001480.tgz#9bbd35ee44c2480a1e3a3b9f4496f5066817164a" + integrity sha512-q7cpoPPvZYgtyC4VaBSN0Bt+PJ4c4EYRf0DrduInOz2SkFpHD5p3LnvEpqBp7UnJn+8x1Ogl1s38saUxe+ihQQ== capture-exit@^2.0.0: version "2.0.0" @@ -4357,9 +4357,9 @@ electron-fetch@^1.7.2: encoding "^0.1.13" electron-to-chromium@^1.4.284: - version "1.4.362" - resolved "https://registry.yarnpkg.com/electron-to-chromium/-/electron-to-chromium-1.4.362.tgz#1dfd7a076fc4785a16941f06410d0668e1a7a1aa" - integrity sha512-PYzAoScDfUcAwZfJQvr6hK2xXzLsMocj/Wuz6LpW6TZQNVv9TflBSB+UoEPuFujc478BgAxCoCFarcVPmjzsog== + version "1.4.366" + resolved "https://registry.yarnpkg.com/electron-to-chromium/-/electron-to-chromium-1.4.366.tgz#48d400f9c4af8e80f7bbad0d18730c165d43155e" + integrity sha512-XjC4pyf1no8kJe24nUfyexpWwiGRbZWXU/KbprSEvXcTXUlr3Zr5vK3lQt2to0ttpMhAc3iENccwPSKbnEW2Fg== elliptic@6.5.4: version "6.5.4" @@ -4606,9 +4606,9 @@ eslint-import-resolver-node@^0.3.4: resolve "^1.22.1" eslint-module-utils@^2.6.0: - version "2.7.4" - resolved "https://registry.yarnpkg.com/eslint-module-utils/-/eslint-module-utils-2.7.4.tgz#4f3e41116aaf13a20792261e61d3a2e7e0583974" - integrity sha512-j4GT+rqzCoRKHwURX7pddtIPGySnX9Si/cgMI5ztrcqOPtk5dDEeZ34CQVPphnqkJytlc97Vuk05Um2mJ3gEQA== + version "2.8.0" + resolved "https://registry.yarnpkg.com/eslint-module-utils/-/eslint-module-utils-2.8.0.tgz#e439fee65fc33f6bba630ff621efc38ec0375c49" + integrity sha512-aWajIYfsqCKRDgUfjEXNN/JlrzauMuSEy5sbd7WXbtW3EH6A6MpwEh42c7qD+MqQo9QMJ6fWLAeIJynx0g6OAw== dependencies: debug "^3.2.7" @@ -7286,9 +7286,9 @@ long@^4.0.0: integrity sha512-XsP+KhQif4bjX1kbuSiySJFNAehNxgLb6hPRGJ9QsUr8ajHkuXGdrHmFUTUUXhDwVX2R5bY4JNZEwbUiMhV+MA== long@^5.2.0: - version "5.2.1" - resolved "https://registry.yarnpkg.com/long/-/long-5.2.1.tgz#e27595d0083d103d2fa2c20c7699f8e0c92b897f" - integrity sha512-GKSNGeNAtw8IryjjkhZxuKB3JzlcLTwjtiQCHKvqQet81I93kXslhDQruGI/QsddO83mcDToBVy7GqGS/zYf/A== + version "5.2.3" + resolved "https://registry.yarnpkg.com/long/-/long-5.2.3.tgz#a3ba97f3877cf1d778eccbcb048525ebb77499e1" + integrity sha512-lcHwpNoggQTObv5apGNCTdJrO69eHOZMi4BNC+rTLER8iHAqGrUVeLh/irVIM7zTw2bOXA8T6uNPeujwOLg/2Q== lru-cache@^5.1.1: version "5.1.1" @@ -9315,13 +9315,20 @@ semver@7.3.8: dependencies: lru-cache "^6.0.0" -semver@7.4.0, semver@7.x, semver@^7.1.1, semver@^7.1.3, semver@^7.2.1, semver@^7.3.2, semver@^7.3.4, semver@^7.3.5: +semver@7.4.0: version "7.4.0" resolved "https://registry.yarnpkg.com/semver/-/semver-7.4.0.tgz#8481c92feffc531ab1e012a8ffc15bdd3a0f4318" integrity sha512-RgOxM8Mw+7Zus0+zcLEUn8+JfoLpj/huFTItQy2hsM4khuC1HYRDp0cU482Ewn/Fcy6bCjufD8vAj7voC66KQw== dependencies: lru-cache "^6.0.0" +semver@7.x, semver@^7.1.1, semver@^7.1.3, semver@^7.2.1, semver@^7.3.2, semver@^7.3.4, semver@^7.3.5: + version "7.5.0" + resolved "https://registry.yarnpkg.com/semver/-/semver-7.5.0.tgz#ed8c5dc8efb6c629c88b23d41dc9bf40c1d96cd0" + integrity sha512-+XC0AD/R7Q2mPSRuy2Id0+CGTZ98+8f+KvwirxOKIEyid+XSx6HbC63p+O4IndTHuX5Z+JxQ0TghCkO5Cg/2HA== + dependencies: + lru-cache "^6.0.0" + semver@^6.0.0, semver@^6.3.0: version "6.3.0" resolved "https://registry.yarnpkg.com/semver/-/semver-6.3.0.tgz#ee0a64c8af5e8ceea67687b133761e1becbd1d3d" @@ -10343,9 +10350,9 @@ upath@^2.0.1: integrity sha512-1uEe95xksV1O0CYKXo8vQvN1JEbtJp7lb7C5U9HMsIp6IVwntkH/oNUzyVNQSd4S1sYk2FpSSW44FqMc8qee5w== update-browserslist-db@^1.0.10: - version "1.0.10" - resolved "https://registry.yarnpkg.com/update-browserslist-db/-/update-browserslist-db-1.0.10.tgz#0f54b876545726f17d00cd9a2561e6dade943ff3" - integrity sha512-OztqDenkfFkbSG+tRxBeAnCVPckDBcvibKd35yDONx6OU8N7sqgwc7rCbkJ/WcYtVRZ4ba68d6byhC21GFh7sQ== + version "1.0.11" + resolved "https://registry.yarnpkg.com/update-browserslist-db/-/update-browserslist-db-1.0.11.tgz#9a2a641ad2907ae7b3616506f4b977851db5b940" + integrity sha512-dCwEFf0/oT85M1fHBg4F0jtLwJrutGoHSQXCh7u4o2t1drG+c0a9Flnqww6XUKSfQMPpJBRjU8d4RXB09qtvaA== dependencies: escalade "^3.1.1" picocolors "^1.0.0" From c3dbf05a1f3e7abb5d9dc7b7e0a336f39a499d50 Mon Sep 17 00:00:00 2001 From: dOrgJelli Date: Mon, 17 Apr 2023 22:18:32 -0500 Subject: [PATCH 10/19] chore: fix semver package versions --- packages/js/manifests/polywrap/package.json | 4 ++-- packages/js/manifests/wrap/package.json | 4 ++-- yarn.lock | 23 +++++++-------------- 3 files changed, 12 insertions(+), 19 deletions(-) diff --git a/packages/js/manifests/polywrap/package.json b/packages/js/manifests/polywrap/package.json index 38fafed212..cef22218a4 100644 --- a/packages/js/manifests/polywrap/package.json +++ b/packages/js/manifests/polywrap/package.json @@ -18,7 +18,7 @@ "@polywrap/logging-js": "0.10.0", "@polywrap/polywrap-manifest-schemas": "0.10.0", "jsonschema": "1.4.0", - "semver": "7.4.0", + "semver": "7.5.0", "yaml": "2.1.3" }, "devDependencies": { @@ -26,7 +26,7 @@ "@types/jest": "26.0.8", "@types/mustache": "4.0.1", "@types/prettier": "2.6.0", - "@types/semver": "7.3.8", + "@types/semver": "7.3.11", "jest": "26.6.3", "json-schema-to-typescript": "11.0.2", "mustache": "4.0.1", diff --git a/packages/js/manifests/wrap/package.json b/packages/js/manifests/wrap/package.json index f276845390..bcb50ce796 100644 --- a/packages/js/manifests/wrap/package.json +++ b/packages/js/manifests/wrap/package.json @@ -17,7 +17,7 @@ "dependencies": { "@apidevtools/json-schema-ref-parser": "9.0.9", "jsonschema": "1.4.0", - "semver": "7.4.0" + "semver": "7.5.0" }, "devDependencies": { "@polywrap/msgpack-js": "0.10.0", @@ -26,7 +26,7 @@ "@types/jest": "26.0.8", "@types/mustache": "4.0.1", "@types/prettier": "2.6.0", - "@types/semver": "7.3.8", + "@types/semver": "7.3.11", "jest": "26.6.3", "json-schema-to-typescript": "11.0.2", "mustache": "4.0.1", diff --git a/yarn.lock b/yarn.lock index 5abecd74b9..1591f2db65 100644 --- a/yarn.lock +++ b/yarn.lock @@ -2593,10 +2593,10 @@ "@types/glob" "*" "@types/node" "*" -"@types/semver@7.3.8": - version "7.3.8" - resolved "https://registry.yarnpkg.com/@types/semver/-/semver-7.3.8.tgz#508a27995498d7586dcecd77c25e289bfaf90c59" - integrity sha512-D/2EJvAlCEtYFEYmmlGwbGXuK886HzyCc3nZX/tkFTQdEU8jZDAgiv08P162yB17y4ZXZoq7yFAnW4GDBb9Now== +"@types/semver@7.3.11": + version "7.3.11" + resolved "https://registry.yarnpkg.com/@types/semver/-/semver-7.3.11.tgz#7a84d3228f34e68d14955fc406f8e66fdbe9e65e" + integrity sha512-R9HhjC4aKx3jL0FLwU7x6qMTysTvLh7jesRslXmxgCOXZwyh5dsnmrPQQToMyess8D4U+8G9x9mBFZoC/1o/Tw== "@types/shelljs@0.8.9": version "0.8.9" @@ -4357,9 +4357,9 @@ electron-fetch@^1.7.2: encoding "^0.1.13" electron-to-chromium@^1.4.284: - version "1.4.366" - resolved "https://registry.yarnpkg.com/electron-to-chromium/-/electron-to-chromium-1.4.366.tgz#48d400f9c4af8e80f7bbad0d18730c165d43155e" - integrity sha512-XjC4pyf1no8kJe24nUfyexpWwiGRbZWXU/KbprSEvXcTXUlr3Zr5vK3lQt2to0ttpMhAc3iENccwPSKbnEW2Fg== + version "1.4.367" + resolved "https://registry.yarnpkg.com/electron-to-chromium/-/electron-to-chromium-1.4.367.tgz#d9ddc529ba2315fc852b722c359e4a40e86aa742" + integrity sha512-mNuDxb+HpLhPGUKrg0hSxbTjHWw8EziwkwlJNkFUj3W60ypigLDRVz04vU+VRsJPi8Gub+FDhYUpuTm9xiEwRQ== elliptic@6.5.4: version "6.5.4" @@ -9315,14 +9315,7 @@ semver@7.3.8: dependencies: lru-cache "^6.0.0" -semver@7.4.0: - version "7.4.0" - resolved "https://registry.yarnpkg.com/semver/-/semver-7.4.0.tgz#8481c92feffc531ab1e012a8ffc15bdd3a0f4318" - integrity sha512-RgOxM8Mw+7Zus0+zcLEUn8+JfoLpj/huFTItQy2hsM4khuC1HYRDp0cU482Ewn/Fcy6bCjufD8vAj7voC66KQw== - dependencies: - lru-cache "^6.0.0" - -semver@7.x, semver@^7.1.1, semver@^7.1.3, semver@^7.2.1, semver@^7.3.2, semver@^7.3.4, semver@^7.3.5: +semver@7.5.0, semver@7.x, semver@^7.1.1, semver@^7.1.3, semver@^7.2.1, semver@^7.3.2, semver@^7.3.4, semver@^7.3.5: version "7.5.0" resolved "https://registry.yarnpkg.com/semver/-/semver-7.5.0.tgz#ed8c5dc8efb6c629c88b23d41dc9bf40c1d96cd0" integrity sha512-+XC0AD/R7Q2mPSRuy2Id0+CGTZ98+8f+KvwirxOKIEyid+XSx6HbC63p+O4IndTHuX5Z+JxQ0TghCkO5Cg/2HA== From 499ec92ffd6708b2035c6bdd40689b68c2a7dcaa Mon Sep 17 00:00:00 2001 From: namesty Date: Tue, 18 Apr 2023 23:08:27 +0200 Subject: [PATCH 11/19] (feat): serde rename for snake cased properties in types --- .../bind/src/bindings/rust/functions.ts | 20 +++++++++++++++++++ .../rust/plugin/templates/module-rs.mustache | 2 +- .../rust/plugin/templates/types-rs.mustache | 14 ++++++------- 3 files changed, 28 insertions(+), 8 deletions(-) diff --git a/packages/schema/bind/src/bindings/rust/functions.ts b/packages/schema/bind/src/bindings/rust/functions.ts index 7c8d50fa8b..69e14cd0bb 100644 --- a/packages/schema/bind/src/bindings/rust/functions.ts +++ b/packages/schema/bind/src/bindings/rust/functions.ts @@ -314,6 +314,26 @@ export const serdeKeyword: MustacheFn = () => { }; }; +export const serdeRenameIfSnakeCase: MustacheFn = () => { + return (value: string, render: (template: string) => string): string => { + let type = render(value); + + if (isSnakeCase(type)) { + return `#[serde(rename = "${snakeCaseToCamelCase(type)}")]\n `; + } + + if (isKeyword(type)) { + return `#[serde(rename = "${type}")]\n `; + } + return ""; + }; +} + +const isSnakeCase = (value: string): boolean => /[a-z0-9]+(?:_[a-z0-9]+)*/.test(value) && value.includes("_") +const snakeCaseToCamelCase = (value: string): string => value.toLowerCase().replace( + /[-_][a-z]/g, (group) => group.slice(-1).toUpperCase() +) + const toWasmArray = (type: string, optional: boolean): string => { const result = type.match(/(\[)([[\]A-Za-z1-9_.!]+)(\])/); diff --git a/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache b/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache index 1ecca04168..2d566b3358 100644 --- a/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache +++ b/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache @@ -13,7 +13,7 @@ use super::types::*; #[derive(Clone, Debug, Deserialize, Serialize)] pub struct Args{{#toUpper}}{{name}}{{/toUpper}} { {{#arguments}} - {{#serdeKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/serdeKeyword}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, + {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, {{/arguments}} } diff --git a/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache b/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache index 50c1d9de5d..deb45cf6a2 100644 --- a/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache +++ b/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache @@ -21,7 +21,7 @@ use polywrap_plugin::error::PluginError; #[derive(Clone, Debug, Deserialize, Serialize)] pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { {{#properties}} - {{#serdeKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/serdeKeyword}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, + {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, {{/properties}} } {{/envType}} @@ -33,7 +33,7 @@ pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} #[derive(Clone, Debug, Deserialize, Serialize)] pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { {{#properties}} - {{#serdeKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/serdeKeyword}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, + {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, {{/properties}} } {{/objectTypes}} @@ -45,7 +45,7 @@ pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} #[derive(Clone, Copy, Debug, Deserialize, Serialize)] pub enum {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { {{#constants}} - {{#serdeKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/serdeKeyword}}{{#detectKeyword}}{{.}}{{/detectKeyword}}, + {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}{{#detectKeyword}}{{.}}{{/detectKeyword}}, {{/constants}} _MAX_ } @@ -58,7 +58,7 @@ pub enum {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { #[derive(Clone, Debug, Deserialize, Serialize)] pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { {{#properties}} - {{#serdeKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/serdeKeyword}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, + {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, {{/properties}} } {{/importedObjectTypes}} @@ -70,7 +70,7 @@ pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} #[derive(Clone, Debug, Deserialize, Serialize)] pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { {{#properties}} - {{#serdeKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/serdeKeyword}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, + {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, {{/properties}} } {{/importedEnvType}} @@ -82,7 +82,7 @@ pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} #[derive(Clone, Copy, Debug, Deserialize, Serialize)] pub enum {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { {{#constants}} - {{#serdeKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/serdeKeyword}}{{#detectKeyword}}{{.}}{{/detectKeyword}}, + {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}{{#detectKeyword}}{{.}}{{/detectKeyword}}, {{/constants}} _MAX_ } @@ -97,7 +97,7 @@ pub enum {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { #[derive(Clone, Debug, Deserialize, Serialize)] pub struct {{#toUpper}}{{parent.type}}{{/toUpper}}Args{{#toUpper}}{{name}}{{/toUpper}} { {{#arguments}} - {{#serdeKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/serdeKeyword}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, + {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, {{/arguments}} } From 7f9aba8c94262316f451465c008596ae0b1b76d0 Mon Sep 17 00:00:00 2001 From: namesty Date: Tue, 18 Apr 2023 23:32:12 +0200 Subject: [PATCH 12/19] (fix): bind sanity tests updated with serde renames --- .../bind/sanity/output/plugin-rs/module.rs | 14 +++++++ .../bind/sanity/output/plugin-rs/types.rs | 42 +++++++++++++++++++ 2 files changed, 56 insertions(+) diff --git a/packages/test-cases/cases/bind/sanity/output/plugin-rs/module.rs b/packages/test-cases/cases/bind/sanity/output/plugin-rs/module.rs index 13a34bfe19..c2cef1d87d 100644 --- a/packages/test-cases/cases/bind/sanity/output/plugin-rs/module.rs +++ b/packages/test-cases/cases/bind/sanity/output/plugin-rs/module.rs @@ -11,31 +11,45 @@ use super::types::*; #[derive(Clone, Debug, Deserialize, Serialize)] pub struct ArgsModuleMethod { pub str: String, + #[serde(rename = "optStr")] pub opt_str: Option, pub en: CustomEnum, + #[serde(rename = "optEnum")] pub opt_enum: Option, + #[serde(rename = "enumArray")] pub enum_array: Vec, + #[serde(rename = "optEnumArray")] pub opt_enum_array: Option>>, pub map: Map, + #[serde(rename = "mapOfArr")] pub map_of_arr: Map>, + #[serde(rename = "mapOfMap")] pub map_of_map: Map>, + #[serde(rename = "mapOfObj")] pub map_of_obj: Map, + #[serde(rename = "mapOfArrOfObj")] pub map_of_arr_of_obj: Map>, } #[derive(Clone, Debug, Deserialize, Serialize)] pub struct ArgsObjectMethod { pub object: AnotherType, + #[serde(rename = "optObject")] pub opt_object: Option, + #[serde(rename = "objectArray")] pub object_array: Vec, + #[serde(rename = "optObjectArray")] pub opt_object_array: Option>>, } #[derive(Clone, Debug, Deserialize, Serialize)] pub struct ArgsOptionalEnvMethod { pub object: AnotherType, + #[serde(rename = "optObject")] pub opt_object: Option, + #[serde(rename = "objectArray")] pub object_array: Vec, + #[serde(rename = "optObjectArray")] pub opt_object_array: Option>>, } diff --git a/packages/test-cases/cases/bind/sanity/output/plugin-rs/types.rs b/packages/test-cases/cases/bind/sanity/output/plugin-rs/types.rs index 67e2f1be85..ca26e879f4 100644 --- a/packages/test-cases/cases/bind/sanity/output/plugin-rs/types.rs +++ b/packages/test-cases/cases/bind/sanity/output/plugin-rs/types.rs @@ -18,7 +18,9 @@ use polywrap_plugin::error::PluginError; #[derive(Clone, Debug, Deserialize, Serialize)] pub struct Env { pub prop: String, + #[serde(rename = "optProp")] pub opt_prop: Option, + #[serde(rename = "optMap")] pub opt_map: Option>>, } // Env END // @@ -28,8 +30,10 @@ pub struct Env { #[derive(Clone, Debug, Deserialize, Serialize)] pub struct CustomType { pub str: String, + #[serde(rename = "optStr")] pub opt_str: Option, pub u: u32, + #[serde(rename = "optU")] pub opt_u: Option, pub u8: u8, pub u16: u16, @@ -39,35 +43,58 @@ pub struct CustomType { pub i16: i16, pub i32: i32, pub bigint: BigInt, + #[serde(rename = "optBigint")] pub opt_bigint: Option, pub bignumber: BigNumber, + #[serde(rename = "optBignumber")] pub opt_bignumber: Option, pub json: JSON::Value, + #[serde(rename = "optJson")] pub opt_json: Option, pub bytes: Vec, + #[serde(rename = "optBytes")] pub opt_bytes: Option>, pub boolean: bool, + #[serde(rename = "optBoolean")] pub opt_boolean: Option, + #[serde(rename = "uArray")] pub u_array: Vec, + #[serde(rename = "uOptArray")] pub u_opt_array: Option>, + #[serde(rename = "optUOptArray")] pub opt_u_opt_array: Option>>, + #[serde(rename = "optStrOptArray")] pub opt_str_opt_array: Option>>, + #[serde(rename = "uArrayArray")] pub u_array_array: Vec>, + #[serde(rename = "uOptArrayOptArray")] pub u_opt_array_opt_array: Vec>>>, + #[serde(rename = "uArrayOptArrayArray")] pub u_array_opt_array_array: Vec>>>, + #[serde(rename = "crazyArray")] pub crazy_array: Option>>>>>>, pub object: AnotherType, + #[serde(rename = "optObject")] pub opt_object: Option, + #[serde(rename = "objectArray")] pub object_array: Vec, + #[serde(rename = "optObjectArray")] pub opt_object_array: Option>>, pub en: CustomEnum, + #[serde(rename = "optEnum")] pub opt_enum: Option, + #[serde(rename = "enumArray")] pub enum_array: Vec, + #[serde(rename = "optEnumArray")] pub opt_enum_array: Option>>, pub map: Map, + #[serde(rename = "mapOfArr")] pub map_of_arr: Map>, + #[serde(rename = "mapOfObj")] pub map_of_obj: Map, + #[serde(rename = "mapOfArrOfObj")] pub map_of_arr_of_obj: Map>, + #[serde(rename = "mapCustomValue")] pub map_custom_value: Map>, } #[derive(Clone, Debug, Deserialize, Serialize)] @@ -109,12 +136,18 @@ pub enum While { #[derive(Clone, Debug, Deserialize, Serialize)] pub struct TestImportObject { pub object: TestImportAnotherObject, + #[serde(rename = "optObject")] pub opt_object: Option, + #[serde(rename = "objectArray")] pub object_array: Vec, + #[serde(rename = "optObjectArray")] pub opt_object_array: Option>>, pub en: TestImportEnum, + #[serde(rename = "optEnum")] pub opt_enum: Option, + #[serde(rename = "enumArray")] pub enum_array: Vec, + #[serde(rename = "optEnumArray")] pub opt_enum_array: Option>>, } #[derive(Clone, Debug, Deserialize, Serialize)] @@ -149,17 +182,26 @@ pub enum TestImportEnumReturn { #[derive(Clone, Debug, Deserialize, Serialize)] pub struct TestImportModuleArgsImportedMethod { pub str: String, + #[serde(rename = "optStr")] pub opt_str: Option, pub u: u32, + #[serde(rename = "optU")] pub opt_u: Option, + #[serde(rename = "uArrayArray")] pub u_array_array: Vec>>>, pub object: TestImportObject, + #[serde(rename = "optObject")] pub opt_object: Option, + #[serde(rename = "objectArray")] pub object_array: Vec, + #[serde(rename = "optObjectArray")] pub opt_object_array: Option>>, pub en: TestImportEnum, + #[serde(rename = "optEnum")] pub opt_enum: Option, + #[serde(rename = "enumArray")] pub enum_array: Vec, + #[serde(rename = "optEnumArray")] pub opt_enum_array: Option>>, } From 9f3d30923673948173b8c706036e4e6daa877b3c Mon Sep 17 00:00:00 2001 From: namesty Date: Tue, 18 Apr 2023 23:33:12 +0200 Subject: [PATCH 13/19] (lint): lint fixes --- .../schema/bind/src/bindings/rust/functions.ts | 16 +++++++++------- 1 file changed, 9 insertions(+), 7 deletions(-) diff --git a/packages/schema/bind/src/bindings/rust/functions.ts b/packages/schema/bind/src/bindings/rust/functions.ts index 69e14cd0bb..bec1533640 100644 --- a/packages/schema/bind/src/bindings/rust/functions.ts +++ b/packages/schema/bind/src/bindings/rust/functions.ts @@ -316,7 +316,7 @@ export const serdeKeyword: MustacheFn = () => { export const serdeRenameIfSnakeCase: MustacheFn = () => { return (value: string, render: (template: string) => string): string => { - let type = render(value); + const type = render(value); if (isSnakeCase(type)) { return `#[serde(rename = "${snakeCaseToCamelCase(type)}")]\n `; @@ -326,13 +326,15 @@ export const serdeRenameIfSnakeCase: MustacheFn = () => { return `#[serde(rename = "${type}")]\n `; } return ""; - }; -} + }; +}; -const isSnakeCase = (value: string): boolean => /[a-z0-9]+(?:_[a-z0-9]+)*/.test(value) && value.includes("_") -const snakeCaseToCamelCase = (value: string): string => value.toLowerCase().replace( - /[-_][a-z]/g, (group) => group.slice(-1).toUpperCase() -) +const isSnakeCase = (value: string): boolean => + /[a-z0-9]+(?:_[a-z0-9]+)*/.test(value) && value.includes("_"); +const snakeCaseToCamelCase = (value: string): string => + value + .toLowerCase() + .replace(/[-_][a-z]/g, (group) => group.slice(-1).toUpperCase()); const toWasmArray = (type: string, optional: boolean): string => { const result = type.match(/(\[)([[\]A-Za-z1-9_.!]+)(\])/); From 406264a8f82152fe5aa95e8c66d50ef1a7e1f11b Mon Sep 17 00:00:00 2001 From: namesty Date: Wed, 19 Apr 2023 00:57:09 +0200 Subject: [PATCH 14/19] (chore): rename if case mismatch (dont assume snake). Changed test cases --- .../bind/src/bindings/rust/functions.ts | 15 ++---- .../rust/plugin/templates/module-rs.mustache | 2 +- .../rust/plugin/templates/types-rs.mustache | 14 +++--- .../cases/bind/sanity/input/schema.graphql | 6 +-- .../cases/bind/sanity/output/app-ts/types.ts | 6 +-- .../bind/sanity/output/plugin-py/types.py | 6 +-- .../bind/sanity/output/plugin-py/wrap_info.py | 2 +- .../bind/sanity/output/plugin-rs/types.rs | 7 ++- .../bind/sanity/output/plugin-rs/wrap.info.rs | 24 ++++----- .../bind/sanity/output/plugin-ts/types.ts | 6 +-- .../bind/sanity/output/plugin-ts/wrap.info.ts | 24 ++++----- .../sanity/output/wasm-as/CustomType/index.ts | 6 +-- .../wasm-as/CustomType/serialization.ts | 50 +++++++++---------- .../sanity/output/wasm-rs/custom_type/mod.rs | 4 +- .../wasm-rs/custom_type/serialization.rs | 28 +++++------ 15 files changed, 95 insertions(+), 105 deletions(-) diff --git a/packages/schema/bind/src/bindings/rust/functions.ts b/packages/schema/bind/src/bindings/rust/functions.ts index bec1533640..e346469954 100644 --- a/packages/schema/bind/src/bindings/rust/functions.ts +++ b/packages/schema/bind/src/bindings/rust/functions.ts @@ -314,27 +314,18 @@ export const serdeKeyword: MustacheFn = () => { }; }; -export const serdeRenameIfSnakeCase: MustacheFn = () => { +export const serdeRenameIfCaseMismatch: MustacheFn = () => { return (value: string, render: (template: string) => string): string => { const type = render(value); - if (isSnakeCase(type)) { - return `#[serde(rename = "${snakeCaseToCamelCase(type)}")]\n `; - } - - if (isKeyword(type)) { + if (hasUppercase(type) || isKeyword(type)) { return `#[serde(rename = "${type}")]\n `; } return ""; }; }; -const isSnakeCase = (value: string): boolean => - /[a-z0-9]+(?:_[a-z0-9]+)*/.test(value) && value.includes("_"); -const snakeCaseToCamelCase = (value: string): string => - value - .toLowerCase() - .replace(/[-_][a-z]/g, (group) => group.slice(-1).toUpperCase()); +const hasUppercase = (value: string): boolean => value !== value.toLowerCase(); const toWasmArray = (type: string, optional: boolean): string => { const result = type.match(/(\[)([[\]A-Za-z1-9_.!]+)(\])/); diff --git a/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache b/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache index 2d566b3358..d0f2e7f644 100644 --- a/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache +++ b/packages/schema/bind/src/bindings/rust/plugin/templates/module-rs.mustache @@ -13,7 +13,7 @@ use super::types::*; #[derive(Clone, Debug, Deserialize, Serialize)] pub struct Args{{#toUpper}}{{name}}{{/toUpper}} { {{#arguments}} - {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, + {{#serdeRenameIfCaseMismatch}}{{name}}{{/serdeRenameIfCaseMismatch}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, {{/arguments}} } diff --git a/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache b/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache index deb45cf6a2..d22021b794 100644 --- a/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache +++ b/packages/schema/bind/src/bindings/rust/plugin/templates/types-rs.mustache @@ -21,7 +21,7 @@ use polywrap_plugin::error::PluginError; #[derive(Clone, Debug, Deserialize, Serialize)] pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { {{#properties}} - {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, + {{#serdeRenameIfCaseMismatch}}{{name}}{{/serdeRenameIfCaseMismatch}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, {{/properties}} } {{/envType}} @@ -33,7 +33,7 @@ pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} #[derive(Clone, Debug, Deserialize, Serialize)] pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { {{#properties}} - {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, + {{#serdeRenameIfCaseMismatch}}{{name}}{{/serdeRenameIfCaseMismatch}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, {{/properties}} } {{/objectTypes}} @@ -45,7 +45,7 @@ pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} #[derive(Clone, Copy, Debug, Deserialize, Serialize)] pub enum {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { {{#constants}} - {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}{{#detectKeyword}}{{.}}{{/detectKeyword}}, + {{#serdeRenameIfCaseMismatch}}{{name}}{{/serdeRenameIfCaseMismatch}}{{#detectKeyword}}{{.}}{{/detectKeyword}}, {{/constants}} _MAX_ } @@ -58,7 +58,7 @@ pub enum {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { #[derive(Clone, Debug, Deserialize, Serialize)] pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { {{#properties}} - {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, + {{#serdeRenameIfCaseMismatch}}{{name}}{{/serdeRenameIfCaseMismatch}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, {{/properties}} } {{/importedObjectTypes}} @@ -70,7 +70,7 @@ pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} #[derive(Clone, Debug, Deserialize, Serialize)] pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { {{#properties}} - {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, + {{#serdeRenameIfCaseMismatch}}{{name}}{{/serdeRenameIfCaseMismatch}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, {{/properties}} } {{/importedEnvType}} @@ -82,7 +82,7 @@ pub struct {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} #[derive(Clone, Copy, Debug, Deserialize, Serialize)] pub enum {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { {{#constants}} - {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}{{#detectKeyword}}{{.}}{{/detectKeyword}}, + {{#serdeRenameIfCaseMismatch}}{{name}}{{/serdeRenameIfCaseMismatch}}{{#detectKeyword}}{{.}}{{/detectKeyword}}, {{/constants}} _MAX_ } @@ -97,7 +97,7 @@ pub enum {{#detectKeyword}}{{#toUpper}}{{type}}{{/toUpper}}{{/detectKeyword}} { #[derive(Clone, Debug, Deserialize, Serialize)] pub struct {{#toUpper}}{{parent.type}}{{/toUpper}}Args{{#toUpper}}{{name}}{{/toUpper}} { {{#arguments}} - {{#serdeRenameIfSnakeCase}}{{#toLower}}{{name}}{{/toLower}}{{/serdeRenameIfSnakeCase}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, + {{#serdeRenameIfCaseMismatch}}{{name}}{{/serdeRenameIfCaseMismatch}}pub {{#detectKeyword}}{{#toLower}}{{name}}{{/toLower}}{{/detectKeyword}}: {{#toWasm}}{{toGraphQLType}}{{/toWasm}}, {{/arguments}} } diff --git a/packages/test-cases/cases/bind/sanity/input/schema.graphql b/packages/test-cases/cases/bind/sanity/input/schema.graphql index dc5d3c0d48..d9407d0f8a 100644 --- a/packages/test-cases/cases/bind/sanity/input/schema.graphql +++ b/packages/test-cases/cases/bind/sanity/input/schema.graphql @@ -109,9 +109,9 @@ type CustomType { optBytes: Bytes boolean: Boolean! optBoolean: Boolean - uArray: [UInt!]! - uOptArray: [UInt!] - optUOptArray: [UInt] + u_array: [UInt!]! + uOpt_array: [UInt!] + _opt_uOptArray: [UInt] optStrOptArray: [String] uArrayArray: [[UInt!]!]! uOptArrayOptArray: [[UInt32]]! diff --git a/packages/test-cases/cases/bind/sanity/output/app-ts/types.ts b/packages/test-cases/cases/bind/sanity/output/app-ts/types.ts index 79b06c4d96..63cbd9c017 100644 --- a/packages/test-cases/cases/bind/sanity/output/app-ts/types.ts +++ b/packages/test-cases/cases/bind/sanity/output/app-ts/types.ts @@ -45,9 +45,9 @@ export interface CustomType { optBytes?: Types.Bytes | null; boolean: Types.Boolean; optBoolean?: Types.Boolean | null; - uArray: Array; - uOptArray?: Array | null; - optUOptArray?: Array | null; + u_array: Array; + uOpt_array?: Array | null; + _opt_uOptArray?: Array | null; optStrOptArray?: Array | null; uArrayArray: Array>; uOptArrayOptArray: Array | null>; diff --git a/packages/test-cases/cases/bind/sanity/output/plugin-py/types.py b/packages/test-cases/cases/bind/sanity/output/plugin-py/types.py index e5d45f5403..a52aa5ad4b 100644 --- a/packages/test-cases/cases/bind/sanity/output/plugin-py/types.py +++ b/packages/test-cases/cases/bind/sanity/output/plugin-py/types.py @@ -43,9 +43,9 @@ "optBytes": Optional[bytes], "boolean": bool, "optBoolean": Optional[bool], - "uArray": list[int], - "uOptArray": Optional[list[int]], - "optUOptArray": Optional[list[Optional[int]]], + "u_array": list[int], + "uOpt_array": Optional[list[int]], + "_opt_uOptArray": Optional[list[Optional[int]]], "optStrOptArray": Optional[list[Optional[str]]], "uArrayArray": list[list[int]], "uOptArrayOptArray": list[Optional[list[Optional[int]]]], diff --git a/packages/test-cases/cases/bind/sanity/output/plugin-py/wrap_info.py b/packages/test-cases/cases/bind/sanity/output/plugin-py/wrap_info.py index b86538fd75..c7f563a264 100644 --- a/packages/test-cases/cases/bind/sanity/output/plugin-py/wrap_info.py +++ b/packages/test-cases/cases/bind/sanity/output/plugin-py/wrap_info.py @@ -7,7 +7,7 @@ from polywrap_manifest import WrapManifest -abi = json.loads(b64decode("eyJlbnVtVHlwZXMiOlt7ImNvbnN0YW50cyI6WyJTVFJJTkciLCJCWVRFUyJdLCJraW5kIjo4LCJ0eXBlIjoiQ3VzdG9tRW51bSJ9LHsiY29uc3RhbnRzIjpbImZvciIsImluIl0sImtpbmQiOjgsInR5cGUiOiJ3aGlsZSJ9XSwiZW52VHlwZSI6eyJraW5kIjo2NTUzNiwicHJvcGVydGllcyI6W3sia2luZCI6MzQsIm5hbWUiOiJwcm9wIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoicHJvcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sInR5cGUiOiJTdHJpbmcifSx7ImtpbmQiOjM0LCJuYW1lIjoib3B0UHJvcCIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoib3B0UHJvcCIsInR5cGUiOiJTdHJpbmcifSwidHlwZSI6IlN0cmluZyJ9LHsia2luZCI6MzQsIm1hcCI6eyJrZXkiOnsia2luZCI6NCwibmFtZSI6Im9wdE1hcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sImtpbmQiOjI2MjE0NiwibmFtZSI6Im9wdE1hcCIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoib3B0TWFwIiwidHlwZSI6IkludCJ9LCJ0eXBlIjoiTWFwPFN0cmluZywgSW50PiIsInZhbHVlIjp7ImtpbmQiOjQsIm5hbWUiOiJvcHRNYXAiLCJ0eXBlIjoiSW50In19LCJuYW1lIjoib3B0TWFwIiwidHlwZSI6Ik1hcDxTdHJpbmcsIEludD4ifV0sInR5cGUiOiJFbnYifSwiaW1wb3J0ZWRFbnVtVHlwZXMiOlt7ImNvbnN0YW50cyI6WyJTVFJJTkciLCJCWVRFUyJdLCJraW5kIjo1MjAsIm5hbWVzcGFjZSI6IlRlc3RJbXBvcnQiLCJuYXRpdmVUeXBlIjoiRW51bSIsInR5cGUiOiJUZXN0SW1wb3J0X0VudW0iLCJ1cmkiOiJ0ZXN0aW1wb3J0LnVyaS5ldGgifSx7ImNvbnN0YW50cyI6WyJTVFJJTkciLCJCWVRFUyJdLCJraW5kIjo1MjAsIm5hbWVzcGFjZSI6IlRlc3RJbXBvcnQiLCJuYXRpdmVUeXBlIjoiRW51bSIsInR5cGUiOiJUZXN0SW1wb3J0X0VudW1fUmV0dXJuIiwidXJpIjoidGVzdGltcG9ydC51cmkuZXRoIn1dLCJpbXBvcnRlZEVudlR5cGVzIjpbeyJraW5kIjo1MjQyODgsIm5hbWVzcGFjZSI6IlRlc3RJbXBvcnQiLCJuYXRpdmVUeXBlIjoiRW52IiwicHJvcGVydGllcyI6W3sia2luZCI6MzQsIm5hbWUiOiJlbnZpcm9Qcm9wIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiZW52aXJvUHJvcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sInR5cGUiOiJTdHJpbmcifV0sInR5cGUiOiJUZXN0SW1wb3J0X0VudiIsInVyaSI6InRlc3RpbXBvcnQudXJpLmV0aCJ9XSwiaW1wb3J0ZWRNb2R1bGVUeXBlcyI6W3siaXNJbnRlcmZhY2UiOnRydWUsImtpbmQiOjI1NiwibWV0aG9kcyI6W3siYXJndW1lbnRzIjpbeyJraW5kIjozNCwibmFtZSI6InN0ciIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InN0ciIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sInR5cGUiOiJTdHJpbmcifSx7ImtpbmQiOjM0LCJuYW1lIjoib3B0U3RyIiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJvcHRTdHIiLCJ0eXBlIjoiU3RyaW5nIn0sInR5cGUiOiJTdHJpbmcifSx7ImtpbmQiOjM0LCJuYW1lIjoidSIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InUiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQifSwidHlwZSI6IlVJbnQifSx7ImtpbmQiOjM0LCJuYW1lIjoib3B0VSIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoib3B0VSIsInR5cGUiOiJVSW50In0sInR5cGUiOiJVSW50In0seyJhcnJheSI6eyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJ1QXJyYXlBcnJheSIsInR5cGUiOiJVSW50In0sImtpbmQiOjE4LCJuYW1lIjoidUFycmF5QXJyYXkiLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InVBcnJheUFycmF5IiwidHlwZSI6IlVJbnQifSwidHlwZSI6IltVSW50XSJ9LCJpdGVtIjp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6InVBcnJheUFycmF5IiwidHlwZSI6IlVJbnQifSwia2luZCI6MTgsIm5hbWUiOiJ1QXJyYXlBcnJheSIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoidUFycmF5QXJyYXkiLCJ0eXBlIjoiVUludCJ9LCJ0eXBlIjoiW1VJbnRdIn0sImtpbmQiOjE4LCJuYW1lIjoidUFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltbVUludF1dIn0sImtpbmQiOjM0LCJuYW1lIjoidUFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltbVUludF1dIn0seyJraW5kIjozNCwibmFtZSI6Im9iamVjdCIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib2JqZWN0IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X09iamVjdCJ9LCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlRlc3RJbXBvcnRfT2JqZWN0In0seyJraW5kIjozNCwibmFtZSI6Im9wdE9iamVjdCIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib3B0T2JqZWN0IiwidHlwZSI6IlRlc3RJbXBvcnRfT2JqZWN0In0sInR5cGUiOiJUZXN0SW1wb3J0X09iamVjdCJ9LHsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo4MTkyLCJuYW1lIjoib2JqZWN0QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlRlc3RJbXBvcnRfT2JqZWN0In0sImtpbmQiOjE4LCJuYW1lIjoib2JqZWN0QXJyYXkiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9iamVjdEFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X09iamVjdCJ9LCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltUZXN0SW1wb3J0X09iamVjdF0ifSwia2luZCI6MzQsIm5hbWUiOiJvYmplY3RBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW1Rlc3RJbXBvcnRfT2JqZWN0XSJ9LHsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo4MTkyLCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJ0eXBlIjoiVGVzdEltcG9ydF9PYmplY3QifSwia2luZCI6MTgsIm5hbWUiOiJvcHRPYmplY3RBcnJheSIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJ0eXBlIjoiVGVzdEltcG9ydF9PYmplY3QifSwidHlwZSI6IltUZXN0SW1wb3J0X09iamVjdF0ifSwia2luZCI6MzQsIm5hbWUiOiJvcHRPYmplY3RBcnJheSIsInR5cGUiOiJbVGVzdEltcG9ydF9PYmplY3RdIn0seyJlbnVtIjp7ImtpbmQiOjE2Mzg0LCJuYW1lIjoiZW4iLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlRlc3RJbXBvcnRfRW51bSJ9LCJraW5kIjozNCwibmFtZSI6ImVuIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X0VudW0ifSx7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtIiwidHlwZSI6IlRlc3RJbXBvcnRfRW51bSJ9LCJraW5kIjozNCwibmFtZSI6Im9wdEVudW0iLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0seyJhcnJheSI6eyJlbnVtIjp7ImtpbmQiOjE2Mzg0LCJuYW1lIjoiZW51bUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X0VudW0ifSwiaXRlbSI6eyJraW5kIjoxNjM4NCwibmFtZSI6ImVudW1BcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0sImtpbmQiOjE4LCJuYW1lIjoiZW51bUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbVGVzdEltcG9ydF9FbnVtXSJ9LCJraW5kIjozNCwibmFtZSI6ImVudW1BcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW1Rlc3RJbXBvcnRfRW51bV0ifSx7ImFycmF5Ijp7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtQXJyYXkiLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0sIml0ZW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtQXJyYXkiLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0sImtpbmQiOjE4LCJuYW1lIjoib3B0RW51bUFycmF5IiwidHlwZSI6IltUZXN0SW1wb3J0X0VudW1dIn0sImtpbmQiOjM0LCJuYW1lIjoib3B0RW51bUFycmF5IiwidHlwZSI6IltUZXN0SW1wb3J0X0VudW1dIn1dLCJlbnYiOnsicmVxdWlyZWQiOnRydWV9LCJraW5kIjo2NCwibmFtZSI6ImltcG9ydGVkTWV0aG9kIiwicmVxdWlyZWQiOnRydWUsInJldHVybiI6eyJraW5kIjozNCwibmFtZSI6ImltcG9ydGVkTWV0aG9kIiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJpbXBvcnRlZE1ldGhvZCIsInR5cGUiOiJUZXN0SW1wb3J0X09iamVjdCJ9LCJ0eXBlIjoiVGVzdEltcG9ydF9PYmplY3QifSwidHlwZSI6Ik1ldGhvZCJ9LHsiYXJndW1lbnRzIjpbeyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJhcmciLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJraW5kIjoxOCwibmFtZSI6ImFyZyIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6ImFyZyIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sInR5cGUiOiJbU3RyaW5nXSJ9LCJraW5kIjozNCwibmFtZSI6ImFyZyIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW1N0cmluZ10ifV0sImtpbmQiOjY0LCJuYW1lIjoiYW5vdGhlck1ldGhvZCIsInJlcXVpcmVkIjp0cnVlLCJyZXR1cm4iOnsia2luZCI6MzQsIm5hbWUiOiJhbm90aGVyTWV0aG9kIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiYW5vdGhlck1ldGhvZCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50MzIifSwidHlwZSI6IkludDMyIn0sInR5cGUiOiJNZXRob2QifSx7ImFyZ3VtZW50cyI6W3sia2luZCI6MzQsIm5hbWUiOiJhcmciLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJhcmciLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJ0eXBlIjoiU3RyaW5nIn1dLCJraW5kIjo2NCwibmFtZSI6InJldHVybnNBcnJheU9mRW51bXMiLCJyZXF1aXJlZCI6dHJ1ZSwicmV0dXJuIjp7ImFycmF5Ijp7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJyZXR1cm5zQXJyYXlPZkVudW1zIiwidHlwZSI6IlRlc3RJbXBvcnRfRW51bV9SZXR1cm4ifSwiaXRlbSI6eyJraW5kIjoxNjM4NCwibmFtZSI6InJldHVybnNBcnJheU9mRW51bXMiLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtX1JldHVybiJ9LCJraW5kIjoxOCwibmFtZSI6InJldHVybnNBcnJheU9mRW51bXMiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltUZXN0SW1wb3J0X0VudW1fUmV0dXJuXSJ9LCJraW5kIjozNCwibmFtZSI6InJldHVybnNBcnJheU9mRW51bXMiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltUZXN0SW1wb3J0X0VudW1fUmV0dXJuXSJ9LCJ0eXBlIjoiTWV0aG9kIn1dLCJuYW1lc3BhY2UiOiJUZXN0SW1wb3J0IiwibmF0aXZlVHlwZSI6Ik1vZHVsZSIsInR5cGUiOiJUZXN0SW1wb3J0X01vZHVsZSIsInVyaSI6InRlc3RpbXBvcnQudXJpLmV0aCJ9XSwiaW1wb3J0ZWRPYmplY3RUeXBlcyI6W3sia2luZCI6MTAyNSwibmFtZXNwYWNlIjoiVGVzdEltcG9ydCIsIm5hdGl2ZVR5cGUiOiJPYmplY3QiLCJwcm9wZXJ0aWVzIjpbeyJraW5kIjozNCwibmFtZSI6Im9iamVjdCIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib2JqZWN0IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3QifSwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3QifSx7ImtpbmQiOjM0LCJuYW1lIjoib3B0T2JqZWN0Iiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJvcHRPYmplY3QiLCJ0eXBlIjoiVGVzdEltcG9ydF9Bbm90aGVyT2JqZWN0In0sInR5cGUiOiJUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3QifSx7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6ODE5MiwibmFtZSI6Im9iamVjdEFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3QifSwia2luZCI6MTgsIm5hbWUiOiJvYmplY3RBcnJheSIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib2JqZWN0QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlRlc3RJbXBvcnRfQW5vdGhlck9iamVjdCJ9LCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3RdIn0sImtpbmQiOjM0LCJuYW1lIjoib2JqZWN0QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3RdIn0seyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjgxOTIsIm5hbWUiOiJvcHRPYmplY3RBcnJheSIsInR5cGUiOiJUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3QifSwia2luZCI6MTgsIm5hbWUiOiJvcHRPYmplY3RBcnJheSIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJ0eXBlIjoiVGVzdEltcG9ydF9Bbm90aGVyT2JqZWN0In0sInR5cGUiOiJbVGVzdEltcG9ydF9Bbm90aGVyT2JqZWN0XSJ9LCJraW5kIjozNCwibmFtZSI6Im9wdE9iamVjdEFycmF5IiwidHlwZSI6IltUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3RdIn0seyJlbnVtIjp7ImtpbmQiOjE2Mzg0LCJuYW1lIjoiZW4iLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlRlc3RJbXBvcnRfRW51bSJ9LCJraW5kIjozNCwibmFtZSI6ImVuIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X0VudW0ifSx7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtIiwidHlwZSI6IlRlc3RJbXBvcnRfRW51bSJ9LCJraW5kIjozNCwibmFtZSI6Im9wdEVudW0iLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0seyJhcnJheSI6eyJlbnVtIjp7ImtpbmQiOjE2Mzg0LCJuYW1lIjoiZW51bUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X0VudW0ifSwiaXRlbSI6eyJraW5kIjoxNjM4NCwibmFtZSI6ImVudW1BcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0sImtpbmQiOjE4LCJuYW1lIjoiZW51bUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbVGVzdEltcG9ydF9FbnVtXSJ9LCJraW5kIjozNCwibmFtZSI6ImVudW1BcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW1Rlc3RJbXBvcnRfRW51bV0ifSx7ImFycmF5Ijp7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtQXJyYXkiLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0sIml0ZW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtQXJyYXkiLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0sImtpbmQiOjE4LCJuYW1lIjoib3B0RW51bUFycmF5IiwidHlwZSI6IltUZXN0SW1wb3J0X0VudW1dIn0sImtpbmQiOjM0LCJuYW1lIjoib3B0RW51bUFycmF5IiwidHlwZSI6IltUZXN0SW1wb3J0X0VudW1dIn1dLCJ0eXBlIjoiVGVzdEltcG9ydF9PYmplY3QiLCJ1cmkiOiJ0ZXN0aW1wb3J0LnVyaS5ldGgifSx7ImtpbmQiOjEwMjUsIm5hbWVzcGFjZSI6IlRlc3RJbXBvcnQiLCJuYXRpdmVUeXBlIjoiQW5vdGhlck9iamVjdCIsInByb3BlcnRpZXMiOlt7ImtpbmQiOjM0LCJuYW1lIjoicHJvcCIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InByb3AiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJ0eXBlIjoiU3RyaW5nIn1dLCJ0eXBlIjoiVGVzdEltcG9ydF9Bbm90aGVyT2JqZWN0IiwidXJpIjoidGVzdGltcG9ydC51cmkuZXRoIn1dLCJpbnRlcmZhY2VUeXBlcyI6W3siY2FwYWJpbGl0aWVzIjp7ImdldEltcGxlbWVudGF0aW9ucyI6eyJlbmFibGVkIjp0cnVlfX0sImtpbmQiOjMyNzY4LCJuYW1lc3BhY2UiOiJUZXN0SW1wb3J0IiwibmF0aXZlVHlwZSI6IkludGVyZmFjZSIsInR5cGUiOiJUZXN0SW1wb3J0IiwidXJpIjoidGVzdGltcG9ydC51cmkuZXRoIn1dLCJtb2R1bGVUeXBlIjp7ImltcG9ydHMiOlt7InR5cGUiOiJUZXN0SW1wb3J0X01vZHVsZSJ9LHsidHlwZSI6IlRlc3RJbXBvcnRfT2JqZWN0In0seyJ0eXBlIjoiVGVzdEltcG9ydF9Bbm90aGVyT2JqZWN0In0seyJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0seyJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtX1JldHVybiJ9XSwia2luZCI6MTI4LCJtZXRob2RzIjpbeyJhcmd1bWVudHMiOlt7ImtpbmQiOjM0LCJuYW1lIjoic3RyIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoic3RyIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwidHlwZSI6IlN0cmluZyJ9LHsia2luZCI6MzQsIm5hbWUiOiJvcHRTdHIiLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6Im9wdFN0ciIsInR5cGUiOiJTdHJpbmcifSwidHlwZSI6IlN0cmluZyJ9LHsiZW51bSI6eyJraW5kIjoxNjM4NCwibmFtZSI6ImVuIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJDdXN0b21FbnVtIn0sImtpbmQiOjM0LCJuYW1lIjoiZW4iLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkN1c3RvbUVudW0ifSx7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtIiwidHlwZSI6IkN1c3RvbUVudW0ifSwia2luZCI6MzQsIm5hbWUiOiJvcHRFbnVtIiwidHlwZSI6IkN1c3RvbUVudW0ifSx7ImFycmF5Ijp7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJlbnVtQXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkN1c3RvbUVudW0ifSwiaXRlbSI6eyJraW5kIjoxNjM4NCwibmFtZSI6ImVudW1BcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQ3VzdG9tRW51bSJ9LCJraW5kIjoxOCwibmFtZSI6ImVudW1BcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW0N1c3RvbUVudW1dIn0sImtpbmQiOjM0LCJuYW1lIjoiZW51bUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbQ3VzdG9tRW51bV0ifSx7ImFycmF5Ijp7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtQXJyYXkiLCJ0eXBlIjoiQ3VzdG9tRW51bSJ9LCJpdGVtIjp7ImtpbmQiOjE2Mzg0LCJuYW1lIjoib3B0RW51bUFycmF5IiwidHlwZSI6IkN1c3RvbUVudW0ifSwia2luZCI6MTgsIm5hbWUiOiJvcHRFbnVtQXJyYXkiLCJ0eXBlIjoiW0N1c3RvbUVudW1dIn0sImtpbmQiOjM0LCJuYW1lIjoib3B0RW51bUFycmF5IiwidHlwZSI6IltDdXN0b21FbnVtXSJ9LHsia2luZCI6MzQsIm1hcCI6eyJrZXkiOnsia2luZCI6NCwibmFtZSI6Im1hcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sImtpbmQiOjI2MjE0NiwibmFtZSI6Im1hcCIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6Im1hcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50In0sInR5cGUiOiJNYXA8U3RyaW5nLCBJbnQ+IiwidmFsdWUiOnsia2luZCI6NCwibmFtZSI6Im1hcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50In19LCJuYW1lIjoibWFwIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJNYXA8U3RyaW5nLCBJbnQ+In0seyJraW5kIjozNCwibWFwIjp7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6Im1hcE9mQXJyIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJJbnQifSwia2luZCI6MTgsIm5hbWUiOiJtYXBPZkFyciIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6Im1hcE9mQXJyIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJJbnQifSwidHlwZSI6IltJbnRdIn0sImtleSI6eyJraW5kIjo0LCJuYW1lIjoibWFwT2ZBcnIiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJraW5kIjoyNjIxNDYsIm5hbWUiOiJtYXBPZkFyciIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiTWFwPFN0cmluZywgW0ludF0+IiwidmFsdWUiOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoibWFwT2ZBcnIiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkludCJ9LCJraW5kIjoxOCwibmFtZSI6Im1hcE9mQXJyIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoibWFwT2ZBcnIiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkludCJ9LCJ0eXBlIjoiW0ludF0ifX0sIm5hbWUiOiJtYXBPZkFyciIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiTWFwPFN0cmluZywgW0ludF0+In0seyJraW5kIjozNCwibWFwIjp7ImtleSI6eyJraW5kIjo0LCJuYW1lIjoibWFwT2ZNYXAiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJraW5kIjoyNjIxNDYsIm1hcCI6eyJrZXkiOnsia2luZCI6NCwibmFtZSI6Im1hcE9mTWFwIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwia2luZCI6MjYyMTQ2LCJuYW1lIjoibWFwT2ZNYXAiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJtYXBPZk1hcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50In0sInR5cGUiOiJNYXA8U3RyaW5nLCBJbnQ+IiwidmFsdWUiOnsia2luZCI6NCwibmFtZSI6Im1hcE9mTWFwIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJJbnQifX0sIm5hbWUiOiJtYXBPZk1hcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiTWFwPFN0cmluZywgTWFwPFN0cmluZywgSW50Pj4iLCJ2YWx1ZSI6eyJrZXkiOnsia2luZCI6NCwibmFtZSI6Im1hcE9mTWFwIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwia2luZCI6MjYyMTQ2LCJuYW1lIjoibWFwT2ZNYXAiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJtYXBPZk1hcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50In0sInR5cGUiOiJNYXA8U3RyaW5nLCBJbnQ+IiwidmFsdWUiOnsia2luZCI6NCwibmFtZSI6Im1hcE9mTWFwIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJJbnQifX19LCJuYW1lIjoibWFwT2ZNYXAiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6Ik1hcDxTdHJpbmcsIE1hcDxTdHJpbmcsIEludD4+In0seyJraW5kIjozNCwibWFwIjp7ImtleSI6eyJraW5kIjo0LCJuYW1lIjoibWFwT2ZPYmoiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJraW5kIjoyNjIxNDYsIm5hbWUiOiJtYXBPZk9iaiIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoibWFwT2ZPYmoiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkFub3RoZXJUeXBlIn0sInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiTWFwPFN0cmluZywgQW5vdGhlclR5cGU+IiwidmFsdWUiOnsia2luZCI6ODE5MiwibmFtZSI6Im1hcE9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9fSwibmFtZSI6Im1hcE9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJNYXA8U3RyaW5nLCBBbm90aGVyVHlwZT4ifSx7ImtpbmQiOjM0LCJtYXAiOnsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo4MTkyLCJuYW1lIjoibWFwT2ZBcnJPZk9iaiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwia2luZCI6MTgsIm5hbWUiOiJtYXBPZkFyck9mT2JqIiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJtYXBPZkFyck9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltBbm90aGVyVHlwZV0ifSwia2V5Ijp7ImtpbmQiOjQsIm5hbWUiOiJtYXBPZkFyck9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwia2luZCI6MjYyMTQ2LCJuYW1lIjoibWFwT2ZBcnJPZk9iaiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiTWFwPFN0cmluZywgW0Fub3RoZXJUeXBlXT4iLCJ2YWx1ZSI6eyJpdGVtIjp7ImtpbmQiOjgxOTIsIm5hbWUiOiJtYXBPZkFyck9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJraW5kIjoxOCwibmFtZSI6Im1hcE9mQXJyT2ZPYmoiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im1hcE9mQXJyT2ZPYmoiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkFub3RoZXJUeXBlIn0sInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW0Fub3RoZXJUeXBlXSJ9fSwibmFtZSI6Im1hcE9mQXJyT2ZPYmoiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6Ik1hcDxTdHJpbmcsIFtBbm90aGVyVHlwZV0+In1dLCJraW5kIjo2NCwibmFtZSI6Im1vZHVsZU1ldGhvZCIsInJlcXVpcmVkIjp0cnVlLCJyZXR1cm4iOnsia2luZCI6MzQsIm5hbWUiOiJtb2R1bGVNZXRob2QiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJtb2R1bGVNZXRob2QiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkludCJ9LCJ0eXBlIjoiSW50In0sInR5cGUiOiJNZXRob2QifSx7ImFyZ3VtZW50cyI6W3sia2luZCI6MzQsIm5hbWUiOiJvYmplY3QiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9iamVjdCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LHsia2luZCI6MzQsIm5hbWUiOiJvcHRPYmplY3QiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9wdE9iamVjdCIsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJ0eXBlIjoiQW5vdGhlclR5cGUifSx7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6ODE5MiwibmFtZSI6Im9iamVjdEFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJraW5kIjoxOCwibmFtZSI6Im9iamVjdEFycmF5Iiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJvYmplY3RBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbQW5vdGhlclR5cGVdIn0sImtpbmQiOjM0LCJuYW1lIjoib2JqZWN0QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltBbm90aGVyVHlwZV0ifSx7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6ODE5MiwibmFtZSI6Im9wdE9iamVjdEFycmF5IiwidHlwZSI6IkFub3RoZXJUeXBlIn0sImtpbmQiOjE4LCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9wdE9iamVjdEFycmF5IiwidHlwZSI6IkFub3RoZXJUeXBlIn0sInR5cGUiOiJbQW5vdGhlclR5cGVdIn0sImtpbmQiOjM0LCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJ0eXBlIjoiW0Fub3RoZXJUeXBlXSJ9XSwiZW52Ijp7InJlcXVpcmVkIjp0cnVlfSwia2luZCI6NjQsIm5hbWUiOiJvYmplY3RNZXRob2QiLCJyZXF1aXJlZCI6dHJ1ZSwicmV0dXJuIjp7ImtpbmQiOjM0LCJuYW1lIjoib2JqZWN0TWV0aG9kIiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJvYmplY3RNZXRob2QiLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwidHlwZSI6IkFub3RoZXJUeXBlIn0sInR5cGUiOiJNZXRob2QifSx7ImFyZ3VtZW50cyI6W3sia2luZCI6MzQsIm5hbWUiOiJvYmplY3QiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9iamVjdCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LHsia2luZCI6MzQsIm5hbWUiOiJvcHRPYmplY3QiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9wdE9iamVjdCIsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJ0eXBlIjoiQW5vdGhlclR5cGUifSx7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6ODE5MiwibmFtZSI6Im9iamVjdEFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJraW5kIjoxOCwibmFtZSI6Im9iamVjdEFycmF5Iiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJvYmplY3RBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbQW5vdGhlclR5cGVdIn0sImtpbmQiOjM0LCJuYW1lIjoib2JqZWN0QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltBbm90aGVyVHlwZV0ifSx7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6ODE5MiwibmFtZSI6Im9wdE9iamVjdEFycmF5IiwidHlwZSI6IkFub3RoZXJUeXBlIn0sImtpbmQiOjE4LCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9wdE9iamVjdEFycmF5IiwidHlwZSI6IkFub3RoZXJUeXBlIn0sInR5cGUiOiJbQW5vdGhlclR5cGVdIn0sImtpbmQiOjM0LCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJ0eXBlIjoiW0Fub3RoZXJUeXBlXSJ9XSwiZW52Ijp7InJlcXVpcmVkIjpmYWxzZX0sImtpbmQiOjY0LCJuYW1lIjoib3B0aW9uYWxFbnZNZXRob2QiLCJyZXF1aXJlZCI6dHJ1ZSwicmV0dXJuIjp7ImtpbmQiOjM0LCJuYW1lIjoib3B0aW9uYWxFbnZNZXRob2QiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9wdGlvbmFsRW52TWV0aG9kIiwidHlwZSI6IkFub3RoZXJUeXBlIn0sInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJ0eXBlIjoiTWV0aG9kIn0seyJhcmd1bWVudHMiOlt7ImtpbmQiOjM0LCJuYW1lIjoiaWYiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6ImlmIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJlbHNlIn0sInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiZWxzZSJ9XSwia2luZCI6NjQsIm5hbWUiOiJpZiIsInJlcXVpcmVkIjp0cnVlLCJyZXR1cm4iOnsia2luZCI6MzQsIm5hbWUiOiJpZiIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoiaWYiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6ImVsc2UifSwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJlbHNlIn0sInR5cGUiOiJNZXRob2QifV0sInR5cGUiOiJNb2R1bGUifSwib2JqZWN0VHlwZXMiOlt7ImtpbmQiOjEsInByb3BlcnRpZXMiOlt7ImtpbmQiOjM0LCJuYW1lIjoic3RyIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoic3RyIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwidHlwZSI6IlN0cmluZyJ9LHsia2luZCI6MzQsIm5hbWUiOiJvcHRTdHIiLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6Im9wdFN0ciIsInR5cGUiOiJTdHJpbmcifSwidHlwZSI6IlN0cmluZyJ9LHsia2luZCI6MzQsIm5hbWUiOiJ1IiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoidSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludCJ9LCJ0eXBlIjoiVUludCJ9LHsia2luZCI6MzQsIm5hbWUiOiJvcHRVIiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJvcHRVIiwidHlwZSI6IlVJbnQifSwidHlwZSI6IlVJbnQifSx7ImtpbmQiOjM0LCJuYW1lIjoidTgiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJ1OCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDgifSwidHlwZSI6IlVJbnQ4In0seyJraW5kIjozNCwibmFtZSI6InUxNiIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InUxNiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDE2In0sInR5cGUiOiJVSW50MTYifSx7ImtpbmQiOjM0LCJuYW1lIjoidTMyIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoidTMyIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwidHlwZSI6IlVJbnQzMiJ9LHsia2luZCI6MzQsIm5hbWUiOiJpIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiaSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50In0sInR5cGUiOiJJbnQifSx7ImtpbmQiOjM0LCJuYW1lIjoiaTgiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJpOCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50OCJ9LCJ0eXBlIjoiSW50OCJ9LHsia2luZCI6MzQsIm5hbWUiOiJpMTYiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJpMTYiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkludDE2In0sInR5cGUiOiJJbnQxNiJ9LHsia2luZCI6MzQsIm5hbWUiOiJpMzIiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJpMzIiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkludDMyIn0sInR5cGUiOiJJbnQzMiJ9LHsia2luZCI6MzQsIm5hbWUiOiJiaWdpbnQiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJiaWdpbnQiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkJpZ0ludCJ9LCJ0eXBlIjoiQmlnSW50In0seyJraW5kIjozNCwibmFtZSI6Im9wdEJpZ2ludCIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoib3B0QmlnaW50IiwidHlwZSI6IkJpZ0ludCJ9LCJ0eXBlIjoiQmlnSW50In0seyJraW5kIjozNCwibmFtZSI6ImJpZ251bWJlciIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6ImJpZ251bWJlciIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQmlnTnVtYmVyIn0sInR5cGUiOiJCaWdOdW1iZXIifSx7ImtpbmQiOjM0LCJuYW1lIjoib3B0QmlnbnVtYmVyIiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJvcHRCaWdudW1iZXIiLCJ0eXBlIjoiQmlnTnVtYmVyIn0sInR5cGUiOiJCaWdOdW1iZXIifSx7ImtpbmQiOjM0LCJuYW1lIjoianNvbiIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6Impzb24iLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkpTT04ifSwidHlwZSI6IkpTT04ifSx7ImtpbmQiOjM0LCJuYW1lIjoib3B0SnNvbiIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoib3B0SnNvbiIsInR5cGUiOiJKU09OIn0sInR5cGUiOiJKU09OIn0seyJraW5kIjozNCwibmFtZSI6ImJ5dGVzIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiYnl0ZXMiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkJ5dGVzIn0sInR5cGUiOiJCeXRlcyJ9LHsia2luZCI6MzQsIm5hbWUiOiJvcHRCeXRlcyIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoib3B0Qnl0ZXMiLCJ0eXBlIjoiQnl0ZXMifSwidHlwZSI6IkJ5dGVzIn0seyJraW5kIjozNCwibmFtZSI6ImJvb2xlYW4iLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJib29sZWFuIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJCb29sZWFuIn0sInR5cGUiOiJCb29sZWFuIn0seyJraW5kIjozNCwibmFtZSI6Im9wdEJvb2xlYW4iLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6Im9wdEJvb2xlYW4iLCJ0eXBlIjoiQm9vbGVhbiJ9LCJ0eXBlIjoiQm9vbGVhbiJ9LHsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoidUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50In0sImtpbmQiOjE4LCJuYW1lIjoidUFycmF5IiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoidUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50In0sInR5cGUiOiJbVUludF0ifSwia2luZCI6MzQsIm5hbWUiOiJ1QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltVSW50XSJ9LHsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoidU9wdEFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50In0sImtpbmQiOjE4LCJuYW1lIjoidU9wdEFycmF5Iiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJ1T3B0QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQifSwidHlwZSI6IltVSW50XSJ9LCJraW5kIjozNCwibmFtZSI6InVPcHRBcnJheSIsInR5cGUiOiJbVUludF0ifSx7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6Im9wdFVPcHRBcnJheSIsInR5cGUiOiJVSW50In0sImtpbmQiOjE4LCJuYW1lIjoib3B0VU9wdEFycmF5Iiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJvcHRVT3B0QXJyYXkiLCJ0eXBlIjoiVUludCJ9LCJ0eXBlIjoiW1VJbnRdIn0sImtpbmQiOjM0LCJuYW1lIjoib3B0VU9wdEFycmF5IiwidHlwZSI6IltVSW50XSJ9LHsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoib3B0U3RyT3B0QXJyYXkiLCJ0eXBlIjoiU3RyaW5nIn0sImtpbmQiOjE4LCJuYW1lIjoib3B0U3RyT3B0QXJyYXkiLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6Im9wdFN0ck9wdEFycmF5IiwidHlwZSI6IlN0cmluZyJ9LCJ0eXBlIjoiW1N0cmluZ10ifSwia2luZCI6MzQsIm5hbWUiOiJvcHRTdHJPcHRBcnJheSIsInR5cGUiOiJbU3RyaW5nXSJ9LHsiYXJyYXkiOnsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoidUFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQifSwia2luZCI6MTgsIm5hbWUiOiJ1QXJyYXlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InVBcnJheUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50In0sInR5cGUiOiJbVUludF0ifSwiaXRlbSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJ1QXJyYXlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludCJ9LCJraW5kIjoxOCwibmFtZSI6InVBcnJheUFycmF5IiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoidUFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQifSwidHlwZSI6IltVSW50XSJ9LCJraW5kIjoxOCwibmFtZSI6InVBcnJheUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbW1VJbnRdXSJ9LCJraW5kIjozNCwibmFtZSI6InVBcnJheUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbW1VJbnRdXSJ9LHsiYXJyYXkiOnsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoidU9wdEFycmF5T3B0QXJyYXkiLCJ0eXBlIjoiVUludDMyIn0sImtpbmQiOjE4LCJuYW1lIjoidU9wdEFycmF5T3B0QXJyYXkiLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InVPcHRBcnJheU9wdEFycmF5IiwidHlwZSI6IlVJbnQzMiJ9LCJ0eXBlIjoiW1VJbnQzMl0ifSwiaXRlbSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJ1T3B0QXJyYXlPcHRBcnJheSIsInR5cGUiOiJVSW50MzIifSwia2luZCI6MTgsIm5hbWUiOiJ1T3B0QXJyYXlPcHRBcnJheSIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoidU9wdEFycmF5T3B0QXJyYXkiLCJ0eXBlIjoiVUludDMyIn0sInR5cGUiOiJbVUludDMyXSJ9LCJraW5kIjoxOCwibmFtZSI6InVPcHRBcnJheU9wdEFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbW1VJbnQzMl1dIn0sImtpbmQiOjM0LCJuYW1lIjoidU9wdEFycmF5T3B0QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltbVUludDMyXV0ifSx7ImFycmF5Ijp7ImFycmF5Ijp7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6InVBcnJheU9wdEFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQzMiJ9LCJraW5kIjoxOCwibmFtZSI6InVBcnJheU9wdEFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJ1QXJyYXlPcHRBcnJheUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwidHlwZSI6IltVSW50MzJdIn0sIml0ZW0iOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoidUFycmF5T3B0QXJyYXlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sImtpbmQiOjE4LCJuYW1lIjoidUFycmF5T3B0QXJyYXlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InVBcnJheU9wdEFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQzMiJ9LCJ0eXBlIjoiW1VJbnQzMl0ifSwia2luZCI6MTgsIm5hbWUiOiJ1QXJyYXlPcHRBcnJheUFycmF5IiwidHlwZSI6IltbVUludDMyXV0ifSwiaXRlbSI6eyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJ1QXJyYXlPcHRBcnJheUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwia2luZCI6MTgsIm5hbWUiOiJ1QXJyYXlPcHRBcnJheUFycmF5IiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoidUFycmF5T3B0QXJyYXlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sInR5cGUiOiJbVUludDMyXSJ9LCJpdGVtIjp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6InVBcnJheU9wdEFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQzMiJ9LCJraW5kIjoxOCwibmFtZSI6InVBcnJheU9wdEFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJ1QXJyYXlPcHRBcnJheUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwidHlwZSI6IltVSW50MzJdIn0sImtpbmQiOjE4LCJuYW1lIjoidUFycmF5T3B0QXJyYXlBcnJheSIsInR5cGUiOiJbW1VJbnQzMl1dIn0sImtpbmQiOjE4LCJuYW1lIjoidUFycmF5T3B0QXJyYXlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW1tbVUludDMyXV1dIn0sImtpbmQiOjM0LCJuYW1lIjoidUFycmF5T3B0QXJyYXlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW1tbVUludDMyXV1dIn0seyJhcnJheSI6eyJhcnJheSI6eyJhcnJheSI6eyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJjcmF6eUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwia2luZCI6MTgsIm5hbWUiOiJjcmF6eUFycmF5Iiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJjcmF6eUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwidHlwZSI6IltVSW50MzJdIn0sIml0ZW0iOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoiY3JhenlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sImtpbmQiOjE4LCJuYW1lIjoiY3JhenlBcnJheSIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiY3JhenlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sInR5cGUiOiJbVUludDMyXSJ9LCJraW5kIjoxOCwibmFtZSI6ImNyYXp5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltbVUludDMyXV0ifSwiaXRlbSI6eyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJjcmF6eUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwia2luZCI6MTgsIm5hbWUiOiJjcmF6eUFycmF5Iiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJjcmF6eUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwidHlwZSI6IltVSW50MzJdIn0sIml0ZW0iOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoiY3JhenlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sImtpbmQiOjE4LCJuYW1lIjoiY3JhenlBcnJheSIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiY3JhenlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sInR5cGUiOiJbVUludDMyXSJ9LCJraW5kIjoxOCwibmFtZSI6ImNyYXp5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltbVUludDMyXV0ifSwia2luZCI6MTgsIm5hbWUiOiJjcmF6eUFycmF5IiwidHlwZSI6IltbW1VJbnQzMl1dXSJ9LCJpdGVtIjp7ImFycmF5Ijp7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6ImNyYXp5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQzMiJ9LCJraW5kIjoxOCwibmFtZSI6ImNyYXp5QXJyYXkiLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6ImNyYXp5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQzMiJ9LCJ0eXBlIjoiW1VJbnQzMl0ifSwiaXRlbSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJjcmF6eUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwia2luZCI6MTgsIm5hbWUiOiJjcmF6eUFycmF5Iiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJjcmF6eUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwidHlwZSI6IltVSW50MzJdIn0sImtpbmQiOjE4LCJuYW1lIjoiY3JhenlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW1tVSW50MzJdXSJ9LCJpdGVtIjp7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6ImNyYXp5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQzMiJ9LCJraW5kIjoxOCwibmFtZSI6ImNyYXp5QXJyYXkiLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6ImNyYXp5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQzMiJ9LCJ0eXBlIjoiW1VJbnQzMl0ifSwiaXRlbSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJjcmF6eUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwia2luZCI6MTgsIm5hbWUiOiJjcmF6eUFycmF5Iiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJjcmF6eUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwidHlwZSI6IltVSW50MzJdIn0sImtpbmQiOjE4LCJuYW1lIjoiY3JhenlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW1tVSW50MzJdXSJ9LCJraW5kIjoxOCwibmFtZSI6ImNyYXp5QXJyYXkiLCJ0eXBlIjoiW1tbVUludDMyXV1dIn0sImtpbmQiOjE4LCJuYW1lIjoiY3JhenlBcnJheSIsInR5cGUiOiJbW1tbVUludDMyXV1dXSJ9LCJraW5kIjozNCwibmFtZSI6ImNyYXp5QXJyYXkiLCJ0eXBlIjoiW1tbW1VJbnQzMl1dXV0ifSx7ImtpbmQiOjM0LCJuYW1lIjoib2JqZWN0Iiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJvYmplY3QiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkFub3RoZXJUeXBlIn0sInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSx7ImtpbmQiOjM0LCJuYW1lIjoib3B0T2JqZWN0Iiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJvcHRPYmplY3QiLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwidHlwZSI6IkFub3RoZXJUeXBlIn0seyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjgxOTIsIm5hbWUiOiJvYmplY3RBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwia2luZCI6MTgsIm5hbWUiOiJvYmplY3RBcnJheSIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib2JqZWN0QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkFub3RoZXJUeXBlIn0sInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW0Fub3RoZXJUeXBlXSJ9LCJraW5kIjozNCwibmFtZSI6Im9iamVjdEFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbQW5vdGhlclR5cGVdIn0seyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjgxOTIsIm5hbWUiOiJvcHRPYmplY3RBcnJheSIsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJraW5kIjoxOCwibmFtZSI6Im9wdE9iamVjdEFycmF5Iiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJvcHRPYmplY3RBcnJheSIsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJ0eXBlIjoiW0Fub3RoZXJUeXBlXSJ9LCJraW5kIjozNCwibmFtZSI6Im9wdE9iamVjdEFycmF5IiwidHlwZSI6IltBbm90aGVyVHlwZV0ifSx7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJlbiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQ3VzdG9tRW51bSJ9LCJraW5kIjozNCwibmFtZSI6ImVuIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJDdXN0b21FbnVtIn0seyJlbnVtIjp7ImtpbmQiOjE2Mzg0LCJuYW1lIjoib3B0RW51bSIsInR5cGUiOiJDdXN0b21FbnVtIn0sImtpbmQiOjM0LCJuYW1lIjoib3B0RW51bSIsInR5cGUiOiJDdXN0b21FbnVtIn0seyJhcnJheSI6eyJlbnVtIjp7ImtpbmQiOjE2Mzg0LCJuYW1lIjoiZW51bUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJDdXN0b21FbnVtIn0sIml0ZW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJlbnVtQXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkN1c3RvbUVudW0ifSwia2luZCI6MTgsIm5hbWUiOiJlbnVtQXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltDdXN0b21FbnVtXSJ9LCJraW5kIjozNCwibmFtZSI6ImVudW1BcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW0N1c3RvbUVudW1dIn0seyJhcnJheSI6eyJlbnVtIjp7ImtpbmQiOjE2Mzg0LCJuYW1lIjoib3B0RW51bUFycmF5IiwidHlwZSI6IkN1c3RvbUVudW0ifSwiaXRlbSI6eyJraW5kIjoxNjM4NCwibmFtZSI6Im9wdEVudW1BcnJheSIsInR5cGUiOiJDdXN0b21FbnVtIn0sImtpbmQiOjE4LCJuYW1lIjoib3B0RW51bUFycmF5IiwidHlwZSI6IltDdXN0b21FbnVtXSJ9LCJraW5kIjozNCwibmFtZSI6Im9wdEVudW1BcnJheSIsInR5cGUiOiJbQ3VzdG9tRW51bV0ifSx7ImtpbmQiOjM0LCJtYXAiOnsia2V5Ijp7ImtpbmQiOjQsIm5hbWUiOiJtYXAiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJraW5kIjoyNjIxNDYsIm5hbWUiOiJtYXAiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJtYXAiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkludCJ9LCJ0eXBlIjoiTWFwPFN0cmluZywgSW50PiIsInZhbHVlIjp7ImtpbmQiOjQsIm5hbWUiOiJtYXAiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkludCJ9fSwibmFtZSI6Im1hcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiTWFwPFN0cmluZywgSW50PiJ9LHsia2luZCI6MzQsIm1hcCI6eyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJtYXBPZkFyciIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50In0sImtpbmQiOjE4LCJuYW1lIjoibWFwT2ZBcnIiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJtYXBPZkFyciIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50In0sInR5cGUiOiJbSW50XSJ9LCJrZXkiOnsia2luZCI6NCwibmFtZSI6Im1hcE9mQXJyIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwia2luZCI6MjYyMTQ2LCJuYW1lIjoibWFwT2ZBcnIiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6Ik1hcDxTdHJpbmcsIFtJbnRdPiIsInZhbHVlIjp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6Im1hcE9mQXJyIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJJbnQifSwia2luZCI6MTgsIm5hbWUiOiJtYXBPZkFyciIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6Im1hcE9mQXJyIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJJbnQifSwidHlwZSI6IltJbnRdIn19LCJuYW1lIjoibWFwT2ZBcnIiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6Ik1hcDxTdHJpbmcsIFtJbnRdPiJ9LHsia2luZCI6MzQsIm1hcCI6eyJrZXkiOnsia2luZCI6NCwibmFtZSI6Im1hcE9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwia2luZCI6MjYyMTQ2LCJuYW1lIjoibWFwT2ZPYmoiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im1hcE9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6Ik1hcDxTdHJpbmcsIEFub3RoZXJUeXBlPiIsInZhbHVlIjp7ImtpbmQiOjgxOTIsIm5hbWUiOiJtYXBPZk9iaiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifX0sIm5hbWUiOiJtYXBPZk9iaiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiTWFwPFN0cmluZywgQW5vdGhlclR5cGU+In0seyJraW5kIjozNCwibWFwIjp7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6ODE5MiwibmFtZSI6Im1hcE9mQXJyT2ZPYmoiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkFub3RoZXJUeXBlIn0sImtpbmQiOjE4LCJuYW1lIjoibWFwT2ZBcnJPZk9iaiIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoibWFwT2ZBcnJPZk9iaiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbQW5vdGhlclR5cGVdIn0sImtleSI6eyJraW5kIjo0LCJuYW1lIjoibWFwT2ZBcnJPZk9iaiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sImtpbmQiOjI2MjE0NiwibmFtZSI6Im1hcE9mQXJyT2ZPYmoiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6Ik1hcDxTdHJpbmcsIFtBbm90aGVyVHlwZV0+IiwidmFsdWUiOnsiaXRlbSI6eyJraW5kIjo4MTkyLCJuYW1lIjoibWFwT2ZBcnJPZk9iaiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwia2luZCI6MTgsIm5hbWUiOiJtYXBPZkFyck9mT2JqIiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJtYXBPZkFyck9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltBbm90aGVyVHlwZV0ifX0sIm5hbWUiOiJtYXBPZkFyck9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJNYXA8U3RyaW5nLCBbQW5vdGhlclR5cGVdPiJ9LHsia2luZCI6MzQsIm1hcCI6eyJrZXkiOnsia2luZCI6NCwibmFtZSI6Im1hcEN1c3RvbVZhbHVlIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwia2luZCI6MjYyMTQ2LCJuYW1lIjoibWFwQ3VzdG9tVmFsdWUiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im1hcEN1c3RvbVZhbHVlIiwidHlwZSI6IkN1c3RvbU1hcFZhbHVlIn0sInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiTWFwPFN0cmluZywgQ3VzdG9tTWFwVmFsdWU+IiwidmFsdWUiOnsia2luZCI6ODE5MiwibmFtZSI6Im1hcEN1c3RvbVZhbHVlIiwidHlwZSI6IkN1c3RvbU1hcFZhbHVlIn19LCJuYW1lIjoibWFwQ3VzdG9tVmFsdWUiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6Ik1hcDxTdHJpbmcsIEN1c3RvbU1hcFZhbHVlPiJ9XSwidHlwZSI6IkN1c3RvbVR5cGUifSx7ImtpbmQiOjEsInByb3BlcnRpZXMiOlt7ImtpbmQiOjM0LCJuYW1lIjoicHJvcCIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoicHJvcCIsInR5cGUiOiJTdHJpbmcifSwidHlwZSI6IlN0cmluZyJ9LHsia2luZCI6MzQsIm5hbWUiOiJjaXJjdWxhciIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoiY2lyY3VsYXIiLCJ0eXBlIjoiQ3VzdG9tVHlwZSJ9LCJ0eXBlIjoiQ3VzdG9tVHlwZSJ9LHsia2luZCI6MzQsIm5hbWUiOiJjb25zdCIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiY29uc3QiLCJ0eXBlIjoiU3RyaW5nIn0sInR5cGUiOiJTdHJpbmcifV0sInR5cGUiOiJBbm90aGVyVHlwZSJ9LHsia2luZCI6MSwicHJvcGVydGllcyI6W3sia2luZCI6MzQsIm5hbWUiOiJmb28iLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJmb28iLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJ0eXBlIjoiU3RyaW5nIn1dLCJ0eXBlIjoiQ3VzdG9tTWFwVmFsdWUifSx7ImtpbmQiOjEsInByb3BlcnRpZXMiOlt7ImtpbmQiOjM0LCJuYW1lIjoiZWxzZSIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6ImVsc2UiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJ0eXBlIjoiU3RyaW5nIn1dLCJ0eXBlIjoiZWxzZSJ9XSwidmVyc2lvbiI6IjAuMSJ9").decode("utf-8")) +abi = json.loads(b64decode("eyJlbnVtVHlwZXMiOlt7ImNvbnN0YW50cyI6WyJTVFJJTkciLCJCWVRFUyJdLCJraW5kIjo4LCJ0eXBlIjoiQ3VzdG9tRW51bSJ9LHsiY29uc3RhbnRzIjpbImZvciIsImluIl0sImtpbmQiOjgsInR5cGUiOiJ3aGlsZSJ9XSwiZW52VHlwZSI6eyJraW5kIjo2NTUzNiwicHJvcGVydGllcyI6W3sia2luZCI6MzQsIm5hbWUiOiJwcm9wIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoicHJvcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sInR5cGUiOiJTdHJpbmcifSx7ImtpbmQiOjM0LCJuYW1lIjoib3B0UHJvcCIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoib3B0UHJvcCIsInR5cGUiOiJTdHJpbmcifSwidHlwZSI6IlN0cmluZyJ9LHsia2luZCI6MzQsIm1hcCI6eyJrZXkiOnsia2luZCI6NCwibmFtZSI6Im9wdE1hcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sImtpbmQiOjI2MjE0NiwibmFtZSI6Im9wdE1hcCIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoib3B0TWFwIiwidHlwZSI6IkludCJ9LCJ0eXBlIjoiTWFwPFN0cmluZywgSW50PiIsInZhbHVlIjp7ImtpbmQiOjQsIm5hbWUiOiJvcHRNYXAiLCJ0eXBlIjoiSW50In19LCJuYW1lIjoib3B0TWFwIiwidHlwZSI6Ik1hcDxTdHJpbmcsIEludD4ifV0sInR5cGUiOiJFbnYifSwiaW1wb3J0ZWRFbnVtVHlwZXMiOlt7ImNvbnN0YW50cyI6WyJTVFJJTkciLCJCWVRFUyJdLCJraW5kIjo1MjAsIm5hbWVzcGFjZSI6IlRlc3RJbXBvcnQiLCJuYXRpdmVUeXBlIjoiRW51bSIsInR5cGUiOiJUZXN0SW1wb3J0X0VudW0iLCJ1cmkiOiJ0ZXN0aW1wb3J0LnVyaS5ldGgifSx7ImNvbnN0YW50cyI6WyJTVFJJTkciLCJCWVRFUyJdLCJraW5kIjo1MjAsIm5hbWVzcGFjZSI6IlRlc3RJbXBvcnQiLCJuYXRpdmVUeXBlIjoiRW51bSIsInR5cGUiOiJUZXN0SW1wb3J0X0VudW1fUmV0dXJuIiwidXJpIjoidGVzdGltcG9ydC51cmkuZXRoIn1dLCJpbXBvcnRlZEVudlR5cGVzIjpbeyJraW5kIjo1MjQyODgsIm5hbWVzcGFjZSI6IlRlc3RJbXBvcnQiLCJuYXRpdmVUeXBlIjoiRW52IiwicHJvcGVydGllcyI6W3sia2luZCI6MzQsIm5hbWUiOiJlbnZpcm9Qcm9wIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiZW52aXJvUHJvcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sInR5cGUiOiJTdHJpbmcifV0sInR5cGUiOiJUZXN0SW1wb3J0X0VudiIsInVyaSI6InRlc3RpbXBvcnQudXJpLmV0aCJ9XSwiaW1wb3J0ZWRNb2R1bGVUeXBlcyI6W3siaXNJbnRlcmZhY2UiOnRydWUsImtpbmQiOjI1NiwibWV0aG9kcyI6W3siYXJndW1lbnRzIjpbeyJraW5kIjozNCwibmFtZSI6InN0ciIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InN0ciIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sInR5cGUiOiJTdHJpbmcifSx7ImtpbmQiOjM0LCJuYW1lIjoib3B0U3RyIiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJvcHRTdHIiLCJ0eXBlIjoiU3RyaW5nIn0sInR5cGUiOiJTdHJpbmcifSx7ImtpbmQiOjM0LCJuYW1lIjoidSIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InUiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQifSwidHlwZSI6IlVJbnQifSx7ImtpbmQiOjM0LCJuYW1lIjoib3B0VSIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoib3B0VSIsInR5cGUiOiJVSW50In0sInR5cGUiOiJVSW50In0seyJhcnJheSI6eyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJ1QXJyYXlBcnJheSIsInR5cGUiOiJVSW50In0sImtpbmQiOjE4LCJuYW1lIjoidUFycmF5QXJyYXkiLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InVBcnJheUFycmF5IiwidHlwZSI6IlVJbnQifSwidHlwZSI6IltVSW50XSJ9LCJpdGVtIjp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6InVBcnJheUFycmF5IiwidHlwZSI6IlVJbnQifSwia2luZCI6MTgsIm5hbWUiOiJ1QXJyYXlBcnJheSIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoidUFycmF5QXJyYXkiLCJ0eXBlIjoiVUludCJ9LCJ0eXBlIjoiW1VJbnRdIn0sImtpbmQiOjE4LCJuYW1lIjoidUFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltbVUludF1dIn0sImtpbmQiOjM0LCJuYW1lIjoidUFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltbVUludF1dIn0seyJraW5kIjozNCwibmFtZSI6Im9iamVjdCIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib2JqZWN0IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X09iamVjdCJ9LCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlRlc3RJbXBvcnRfT2JqZWN0In0seyJraW5kIjozNCwibmFtZSI6Im9wdE9iamVjdCIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib3B0T2JqZWN0IiwidHlwZSI6IlRlc3RJbXBvcnRfT2JqZWN0In0sInR5cGUiOiJUZXN0SW1wb3J0X09iamVjdCJ9LHsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo4MTkyLCJuYW1lIjoib2JqZWN0QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlRlc3RJbXBvcnRfT2JqZWN0In0sImtpbmQiOjE4LCJuYW1lIjoib2JqZWN0QXJyYXkiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9iamVjdEFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X09iamVjdCJ9LCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltUZXN0SW1wb3J0X09iamVjdF0ifSwia2luZCI6MzQsIm5hbWUiOiJvYmplY3RBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW1Rlc3RJbXBvcnRfT2JqZWN0XSJ9LHsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo4MTkyLCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJ0eXBlIjoiVGVzdEltcG9ydF9PYmplY3QifSwia2luZCI6MTgsIm5hbWUiOiJvcHRPYmplY3RBcnJheSIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJ0eXBlIjoiVGVzdEltcG9ydF9PYmplY3QifSwidHlwZSI6IltUZXN0SW1wb3J0X09iamVjdF0ifSwia2luZCI6MzQsIm5hbWUiOiJvcHRPYmplY3RBcnJheSIsInR5cGUiOiJbVGVzdEltcG9ydF9PYmplY3RdIn0seyJlbnVtIjp7ImtpbmQiOjE2Mzg0LCJuYW1lIjoiZW4iLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlRlc3RJbXBvcnRfRW51bSJ9LCJraW5kIjozNCwibmFtZSI6ImVuIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X0VudW0ifSx7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtIiwidHlwZSI6IlRlc3RJbXBvcnRfRW51bSJ9LCJraW5kIjozNCwibmFtZSI6Im9wdEVudW0iLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0seyJhcnJheSI6eyJlbnVtIjp7ImtpbmQiOjE2Mzg0LCJuYW1lIjoiZW51bUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X0VudW0ifSwiaXRlbSI6eyJraW5kIjoxNjM4NCwibmFtZSI6ImVudW1BcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0sImtpbmQiOjE4LCJuYW1lIjoiZW51bUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbVGVzdEltcG9ydF9FbnVtXSJ9LCJraW5kIjozNCwibmFtZSI6ImVudW1BcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW1Rlc3RJbXBvcnRfRW51bV0ifSx7ImFycmF5Ijp7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtQXJyYXkiLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0sIml0ZW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtQXJyYXkiLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0sImtpbmQiOjE4LCJuYW1lIjoib3B0RW51bUFycmF5IiwidHlwZSI6IltUZXN0SW1wb3J0X0VudW1dIn0sImtpbmQiOjM0LCJuYW1lIjoib3B0RW51bUFycmF5IiwidHlwZSI6IltUZXN0SW1wb3J0X0VudW1dIn1dLCJlbnYiOnsicmVxdWlyZWQiOnRydWV9LCJraW5kIjo2NCwibmFtZSI6ImltcG9ydGVkTWV0aG9kIiwicmVxdWlyZWQiOnRydWUsInJldHVybiI6eyJraW5kIjozNCwibmFtZSI6ImltcG9ydGVkTWV0aG9kIiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJpbXBvcnRlZE1ldGhvZCIsInR5cGUiOiJUZXN0SW1wb3J0X09iamVjdCJ9LCJ0eXBlIjoiVGVzdEltcG9ydF9PYmplY3QifSwidHlwZSI6Ik1ldGhvZCJ9LHsiYXJndW1lbnRzIjpbeyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJhcmciLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJraW5kIjoxOCwibmFtZSI6ImFyZyIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6ImFyZyIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sInR5cGUiOiJbU3RyaW5nXSJ9LCJraW5kIjozNCwibmFtZSI6ImFyZyIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW1N0cmluZ10ifV0sImtpbmQiOjY0LCJuYW1lIjoiYW5vdGhlck1ldGhvZCIsInJlcXVpcmVkIjp0cnVlLCJyZXR1cm4iOnsia2luZCI6MzQsIm5hbWUiOiJhbm90aGVyTWV0aG9kIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiYW5vdGhlck1ldGhvZCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50MzIifSwidHlwZSI6IkludDMyIn0sInR5cGUiOiJNZXRob2QifSx7ImFyZ3VtZW50cyI6W3sia2luZCI6MzQsIm5hbWUiOiJhcmciLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJhcmciLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJ0eXBlIjoiU3RyaW5nIn1dLCJraW5kIjo2NCwibmFtZSI6InJldHVybnNBcnJheU9mRW51bXMiLCJyZXF1aXJlZCI6dHJ1ZSwicmV0dXJuIjp7ImFycmF5Ijp7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJyZXR1cm5zQXJyYXlPZkVudW1zIiwidHlwZSI6IlRlc3RJbXBvcnRfRW51bV9SZXR1cm4ifSwiaXRlbSI6eyJraW5kIjoxNjM4NCwibmFtZSI6InJldHVybnNBcnJheU9mRW51bXMiLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtX1JldHVybiJ9LCJraW5kIjoxOCwibmFtZSI6InJldHVybnNBcnJheU9mRW51bXMiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltUZXN0SW1wb3J0X0VudW1fUmV0dXJuXSJ9LCJraW5kIjozNCwibmFtZSI6InJldHVybnNBcnJheU9mRW51bXMiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltUZXN0SW1wb3J0X0VudW1fUmV0dXJuXSJ9LCJ0eXBlIjoiTWV0aG9kIn1dLCJuYW1lc3BhY2UiOiJUZXN0SW1wb3J0IiwibmF0aXZlVHlwZSI6Ik1vZHVsZSIsInR5cGUiOiJUZXN0SW1wb3J0X01vZHVsZSIsInVyaSI6InRlc3RpbXBvcnQudXJpLmV0aCJ9XSwiaW1wb3J0ZWRPYmplY3RUeXBlcyI6W3sia2luZCI6MTAyNSwibmFtZXNwYWNlIjoiVGVzdEltcG9ydCIsIm5hdGl2ZVR5cGUiOiJPYmplY3QiLCJwcm9wZXJ0aWVzIjpbeyJraW5kIjozNCwibmFtZSI6Im9iamVjdCIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib2JqZWN0IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3QifSwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3QifSx7ImtpbmQiOjM0LCJuYW1lIjoib3B0T2JqZWN0Iiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJvcHRPYmplY3QiLCJ0eXBlIjoiVGVzdEltcG9ydF9Bbm90aGVyT2JqZWN0In0sInR5cGUiOiJUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3QifSx7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6ODE5MiwibmFtZSI6Im9iamVjdEFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3QifSwia2luZCI6MTgsIm5hbWUiOiJvYmplY3RBcnJheSIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib2JqZWN0QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlRlc3RJbXBvcnRfQW5vdGhlck9iamVjdCJ9LCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3RdIn0sImtpbmQiOjM0LCJuYW1lIjoib2JqZWN0QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3RdIn0seyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjgxOTIsIm5hbWUiOiJvcHRPYmplY3RBcnJheSIsInR5cGUiOiJUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3QifSwia2luZCI6MTgsIm5hbWUiOiJvcHRPYmplY3RBcnJheSIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJ0eXBlIjoiVGVzdEltcG9ydF9Bbm90aGVyT2JqZWN0In0sInR5cGUiOiJbVGVzdEltcG9ydF9Bbm90aGVyT2JqZWN0XSJ9LCJraW5kIjozNCwibmFtZSI6Im9wdE9iamVjdEFycmF5IiwidHlwZSI6IltUZXN0SW1wb3J0X0Fub3RoZXJPYmplY3RdIn0seyJlbnVtIjp7ImtpbmQiOjE2Mzg0LCJuYW1lIjoiZW4iLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlRlc3RJbXBvcnRfRW51bSJ9LCJraW5kIjozNCwibmFtZSI6ImVuIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X0VudW0ifSx7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtIiwidHlwZSI6IlRlc3RJbXBvcnRfRW51bSJ9LCJraW5kIjozNCwibmFtZSI6Im9wdEVudW0iLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0seyJhcnJheSI6eyJlbnVtIjp7ImtpbmQiOjE2Mzg0LCJuYW1lIjoiZW51bUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJUZXN0SW1wb3J0X0VudW0ifSwiaXRlbSI6eyJraW5kIjoxNjM4NCwibmFtZSI6ImVudW1BcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0sImtpbmQiOjE4LCJuYW1lIjoiZW51bUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbVGVzdEltcG9ydF9FbnVtXSJ9LCJraW5kIjozNCwibmFtZSI6ImVudW1BcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW1Rlc3RJbXBvcnRfRW51bV0ifSx7ImFycmF5Ijp7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtQXJyYXkiLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0sIml0ZW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtQXJyYXkiLCJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0sImtpbmQiOjE4LCJuYW1lIjoib3B0RW51bUFycmF5IiwidHlwZSI6IltUZXN0SW1wb3J0X0VudW1dIn0sImtpbmQiOjM0LCJuYW1lIjoib3B0RW51bUFycmF5IiwidHlwZSI6IltUZXN0SW1wb3J0X0VudW1dIn1dLCJ0eXBlIjoiVGVzdEltcG9ydF9PYmplY3QiLCJ1cmkiOiJ0ZXN0aW1wb3J0LnVyaS5ldGgifSx7ImtpbmQiOjEwMjUsIm5hbWVzcGFjZSI6IlRlc3RJbXBvcnQiLCJuYXRpdmVUeXBlIjoiQW5vdGhlck9iamVjdCIsInByb3BlcnRpZXMiOlt7ImtpbmQiOjM0LCJuYW1lIjoicHJvcCIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InByb3AiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJ0eXBlIjoiU3RyaW5nIn1dLCJ0eXBlIjoiVGVzdEltcG9ydF9Bbm90aGVyT2JqZWN0IiwidXJpIjoidGVzdGltcG9ydC51cmkuZXRoIn1dLCJpbnRlcmZhY2VUeXBlcyI6W3siY2FwYWJpbGl0aWVzIjp7ImdldEltcGxlbWVudGF0aW9ucyI6eyJlbmFibGVkIjp0cnVlfX0sImtpbmQiOjMyNzY4LCJuYW1lc3BhY2UiOiJUZXN0SW1wb3J0IiwibmF0aXZlVHlwZSI6IkludGVyZmFjZSIsInR5cGUiOiJUZXN0SW1wb3J0IiwidXJpIjoidGVzdGltcG9ydC51cmkuZXRoIn1dLCJtb2R1bGVUeXBlIjp7ImltcG9ydHMiOlt7InR5cGUiOiJUZXN0SW1wb3J0X01vZHVsZSJ9LHsidHlwZSI6IlRlc3RJbXBvcnRfT2JqZWN0In0seyJ0eXBlIjoiVGVzdEltcG9ydF9Bbm90aGVyT2JqZWN0In0seyJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtIn0seyJ0eXBlIjoiVGVzdEltcG9ydF9FbnVtX1JldHVybiJ9XSwia2luZCI6MTI4LCJtZXRob2RzIjpbeyJhcmd1bWVudHMiOlt7ImtpbmQiOjM0LCJuYW1lIjoic3RyIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoic3RyIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwidHlwZSI6IlN0cmluZyJ9LHsia2luZCI6MzQsIm5hbWUiOiJvcHRTdHIiLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6Im9wdFN0ciIsInR5cGUiOiJTdHJpbmcifSwidHlwZSI6IlN0cmluZyJ9LHsiZW51bSI6eyJraW5kIjoxNjM4NCwibmFtZSI6ImVuIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJDdXN0b21FbnVtIn0sImtpbmQiOjM0LCJuYW1lIjoiZW4iLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkN1c3RvbUVudW0ifSx7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtIiwidHlwZSI6IkN1c3RvbUVudW0ifSwia2luZCI6MzQsIm5hbWUiOiJvcHRFbnVtIiwidHlwZSI6IkN1c3RvbUVudW0ifSx7ImFycmF5Ijp7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJlbnVtQXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkN1c3RvbUVudW0ifSwiaXRlbSI6eyJraW5kIjoxNjM4NCwibmFtZSI6ImVudW1BcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQ3VzdG9tRW51bSJ9LCJraW5kIjoxOCwibmFtZSI6ImVudW1BcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW0N1c3RvbUVudW1dIn0sImtpbmQiOjM0LCJuYW1lIjoiZW51bUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbQ3VzdG9tRW51bV0ifSx7ImFycmF5Ijp7ImVudW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtQXJyYXkiLCJ0eXBlIjoiQ3VzdG9tRW51bSJ9LCJpdGVtIjp7ImtpbmQiOjE2Mzg0LCJuYW1lIjoib3B0RW51bUFycmF5IiwidHlwZSI6IkN1c3RvbUVudW0ifSwia2luZCI6MTgsIm5hbWUiOiJvcHRFbnVtQXJyYXkiLCJ0eXBlIjoiW0N1c3RvbUVudW1dIn0sImtpbmQiOjM0LCJuYW1lIjoib3B0RW51bUFycmF5IiwidHlwZSI6IltDdXN0b21FbnVtXSJ9LHsia2luZCI6MzQsIm1hcCI6eyJrZXkiOnsia2luZCI6NCwibmFtZSI6Im1hcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sImtpbmQiOjI2MjE0NiwibmFtZSI6Im1hcCIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6Im1hcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50In0sInR5cGUiOiJNYXA8U3RyaW5nLCBJbnQ+IiwidmFsdWUiOnsia2luZCI6NCwibmFtZSI6Im1hcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50In19LCJuYW1lIjoibWFwIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJNYXA8U3RyaW5nLCBJbnQ+In0seyJraW5kIjozNCwibWFwIjp7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6Im1hcE9mQXJyIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJJbnQifSwia2luZCI6MTgsIm5hbWUiOiJtYXBPZkFyciIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6Im1hcE9mQXJyIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJJbnQifSwidHlwZSI6IltJbnRdIn0sImtleSI6eyJraW5kIjo0LCJuYW1lIjoibWFwT2ZBcnIiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJraW5kIjoyNjIxNDYsIm5hbWUiOiJtYXBPZkFyciIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiTWFwPFN0cmluZywgW0ludF0+IiwidmFsdWUiOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoibWFwT2ZBcnIiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkludCJ9LCJraW5kIjoxOCwibmFtZSI6Im1hcE9mQXJyIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoibWFwT2ZBcnIiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkludCJ9LCJ0eXBlIjoiW0ludF0ifX0sIm5hbWUiOiJtYXBPZkFyciIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiTWFwPFN0cmluZywgW0ludF0+In0seyJraW5kIjozNCwibWFwIjp7ImtleSI6eyJraW5kIjo0LCJuYW1lIjoibWFwT2ZNYXAiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJraW5kIjoyNjIxNDYsIm1hcCI6eyJrZXkiOnsia2luZCI6NCwibmFtZSI6Im1hcE9mTWFwIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwia2luZCI6MjYyMTQ2LCJuYW1lIjoibWFwT2ZNYXAiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJtYXBPZk1hcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50In0sInR5cGUiOiJNYXA8U3RyaW5nLCBJbnQ+IiwidmFsdWUiOnsia2luZCI6NCwibmFtZSI6Im1hcE9mTWFwIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJJbnQifX0sIm5hbWUiOiJtYXBPZk1hcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiTWFwPFN0cmluZywgTWFwPFN0cmluZywgSW50Pj4iLCJ2YWx1ZSI6eyJrZXkiOnsia2luZCI6NCwibmFtZSI6Im1hcE9mTWFwIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwia2luZCI6MjYyMTQ2LCJuYW1lIjoibWFwT2ZNYXAiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJtYXBPZk1hcCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50In0sInR5cGUiOiJNYXA8U3RyaW5nLCBJbnQ+IiwidmFsdWUiOnsia2luZCI6NCwibmFtZSI6Im1hcE9mTWFwIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJJbnQifX19LCJuYW1lIjoibWFwT2ZNYXAiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6Ik1hcDxTdHJpbmcsIE1hcDxTdHJpbmcsIEludD4+In0seyJraW5kIjozNCwibWFwIjp7ImtleSI6eyJraW5kIjo0LCJuYW1lIjoibWFwT2ZPYmoiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJraW5kIjoyNjIxNDYsIm5hbWUiOiJtYXBPZk9iaiIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoibWFwT2ZPYmoiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkFub3RoZXJUeXBlIn0sInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiTWFwPFN0cmluZywgQW5vdGhlclR5cGU+IiwidmFsdWUiOnsia2luZCI6ODE5MiwibmFtZSI6Im1hcE9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9fSwibmFtZSI6Im1hcE9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJNYXA8U3RyaW5nLCBBbm90aGVyVHlwZT4ifSx7ImtpbmQiOjM0LCJtYXAiOnsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo4MTkyLCJuYW1lIjoibWFwT2ZBcnJPZk9iaiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwia2luZCI6MTgsIm5hbWUiOiJtYXBPZkFyck9mT2JqIiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJtYXBPZkFyck9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltBbm90aGVyVHlwZV0ifSwia2V5Ijp7ImtpbmQiOjQsIm5hbWUiOiJtYXBPZkFyck9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwia2luZCI6MjYyMTQ2LCJuYW1lIjoibWFwT2ZBcnJPZk9iaiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiTWFwPFN0cmluZywgW0Fub3RoZXJUeXBlXT4iLCJ2YWx1ZSI6eyJpdGVtIjp7ImtpbmQiOjgxOTIsIm5hbWUiOiJtYXBPZkFyck9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJraW5kIjoxOCwibmFtZSI6Im1hcE9mQXJyT2ZPYmoiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im1hcE9mQXJyT2ZPYmoiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkFub3RoZXJUeXBlIn0sInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW0Fub3RoZXJUeXBlXSJ9fSwibmFtZSI6Im1hcE9mQXJyT2ZPYmoiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6Ik1hcDxTdHJpbmcsIFtBbm90aGVyVHlwZV0+In1dLCJraW5kIjo2NCwibmFtZSI6Im1vZHVsZU1ldGhvZCIsInJlcXVpcmVkIjp0cnVlLCJyZXR1cm4iOnsia2luZCI6MzQsIm5hbWUiOiJtb2R1bGVNZXRob2QiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJtb2R1bGVNZXRob2QiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkludCJ9LCJ0eXBlIjoiSW50In0sInR5cGUiOiJNZXRob2QifSx7ImFyZ3VtZW50cyI6W3sia2luZCI6MzQsIm5hbWUiOiJvYmplY3QiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9iamVjdCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LHsia2luZCI6MzQsIm5hbWUiOiJvcHRPYmplY3QiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9wdE9iamVjdCIsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJ0eXBlIjoiQW5vdGhlclR5cGUifSx7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6ODE5MiwibmFtZSI6Im9iamVjdEFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJraW5kIjoxOCwibmFtZSI6Im9iamVjdEFycmF5Iiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJvYmplY3RBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbQW5vdGhlclR5cGVdIn0sImtpbmQiOjM0LCJuYW1lIjoib2JqZWN0QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltBbm90aGVyVHlwZV0ifSx7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6ODE5MiwibmFtZSI6Im9wdE9iamVjdEFycmF5IiwidHlwZSI6IkFub3RoZXJUeXBlIn0sImtpbmQiOjE4LCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9wdE9iamVjdEFycmF5IiwidHlwZSI6IkFub3RoZXJUeXBlIn0sInR5cGUiOiJbQW5vdGhlclR5cGVdIn0sImtpbmQiOjM0LCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJ0eXBlIjoiW0Fub3RoZXJUeXBlXSJ9XSwiZW52Ijp7InJlcXVpcmVkIjp0cnVlfSwia2luZCI6NjQsIm5hbWUiOiJvYmplY3RNZXRob2QiLCJyZXF1aXJlZCI6dHJ1ZSwicmV0dXJuIjp7ImtpbmQiOjM0LCJuYW1lIjoib2JqZWN0TWV0aG9kIiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJvYmplY3RNZXRob2QiLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwidHlwZSI6IkFub3RoZXJUeXBlIn0sInR5cGUiOiJNZXRob2QifSx7ImFyZ3VtZW50cyI6W3sia2luZCI6MzQsIm5hbWUiOiJvYmplY3QiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9iamVjdCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LHsia2luZCI6MzQsIm5hbWUiOiJvcHRPYmplY3QiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9wdE9iamVjdCIsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJ0eXBlIjoiQW5vdGhlclR5cGUifSx7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6ODE5MiwibmFtZSI6Im9iamVjdEFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJraW5kIjoxOCwibmFtZSI6Im9iamVjdEFycmF5Iiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJvYmplY3RBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbQW5vdGhlclR5cGVdIn0sImtpbmQiOjM0LCJuYW1lIjoib2JqZWN0QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltBbm90aGVyVHlwZV0ifSx7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6ODE5MiwibmFtZSI6Im9wdE9iamVjdEFycmF5IiwidHlwZSI6IkFub3RoZXJUeXBlIn0sImtpbmQiOjE4LCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9wdE9iamVjdEFycmF5IiwidHlwZSI6IkFub3RoZXJUeXBlIn0sInR5cGUiOiJbQW5vdGhlclR5cGVdIn0sImtpbmQiOjM0LCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJ0eXBlIjoiW0Fub3RoZXJUeXBlXSJ9XSwiZW52Ijp7InJlcXVpcmVkIjpmYWxzZX0sImtpbmQiOjY0LCJuYW1lIjoib3B0aW9uYWxFbnZNZXRob2QiLCJyZXF1aXJlZCI6dHJ1ZSwicmV0dXJuIjp7ImtpbmQiOjM0LCJuYW1lIjoib3B0aW9uYWxFbnZNZXRob2QiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9wdGlvbmFsRW52TWV0aG9kIiwidHlwZSI6IkFub3RoZXJUeXBlIn0sInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJ0eXBlIjoiTWV0aG9kIn0seyJhcmd1bWVudHMiOlt7ImtpbmQiOjM0LCJuYW1lIjoiaWYiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6ImlmIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJlbHNlIn0sInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiZWxzZSJ9XSwia2luZCI6NjQsIm5hbWUiOiJpZiIsInJlcXVpcmVkIjp0cnVlLCJyZXR1cm4iOnsia2luZCI6MzQsIm5hbWUiOiJpZiIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoiaWYiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6ImVsc2UifSwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJlbHNlIn0sInR5cGUiOiJNZXRob2QifV0sInR5cGUiOiJNb2R1bGUifSwib2JqZWN0VHlwZXMiOlt7ImtpbmQiOjEsInByb3BlcnRpZXMiOlt7ImtpbmQiOjM0LCJuYW1lIjoic3RyIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoic3RyIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwidHlwZSI6IlN0cmluZyJ9LHsia2luZCI6MzQsIm5hbWUiOiJvcHRTdHIiLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6Im9wdFN0ciIsInR5cGUiOiJTdHJpbmcifSwidHlwZSI6IlN0cmluZyJ9LHsia2luZCI6MzQsIm5hbWUiOiJ1IiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoidSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludCJ9LCJ0eXBlIjoiVUludCJ9LHsia2luZCI6MzQsIm5hbWUiOiJvcHRVIiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJvcHRVIiwidHlwZSI6IlVJbnQifSwidHlwZSI6IlVJbnQifSx7ImtpbmQiOjM0LCJuYW1lIjoidTgiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJ1OCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDgifSwidHlwZSI6IlVJbnQ4In0seyJraW5kIjozNCwibmFtZSI6InUxNiIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InUxNiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDE2In0sInR5cGUiOiJVSW50MTYifSx7ImtpbmQiOjM0LCJuYW1lIjoidTMyIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoidTMyIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwidHlwZSI6IlVJbnQzMiJ9LHsia2luZCI6MzQsIm5hbWUiOiJpIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiaSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50In0sInR5cGUiOiJJbnQifSx7ImtpbmQiOjM0LCJuYW1lIjoiaTgiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJpOCIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50OCJ9LCJ0eXBlIjoiSW50OCJ9LHsia2luZCI6MzQsIm5hbWUiOiJpMTYiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJpMTYiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkludDE2In0sInR5cGUiOiJJbnQxNiJ9LHsia2luZCI6MzQsIm5hbWUiOiJpMzIiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJpMzIiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkludDMyIn0sInR5cGUiOiJJbnQzMiJ9LHsia2luZCI6MzQsIm5hbWUiOiJiaWdpbnQiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJiaWdpbnQiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkJpZ0ludCJ9LCJ0eXBlIjoiQmlnSW50In0seyJraW5kIjozNCwibmFtZSI6Im9wdEJpZ2ludCIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoib3B0QmlnaW50IiwidHlwZSI6IkJpZ0ludCJ9LCJ0eXBlIjoiQmlnSW50In0seyJraW5kIjozNCwibmFtZSI6ImJpZ251bWJlciIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6ImJpZ251bWJlciIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQmlnTnVtYmVyIn0sInR5cGUiOiJCaWdOdW1iZXIifSx7ImtpbmQiOjM0LCJuYW1lIjoib3B0QmlnbnVtYmVyIiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJvcHRCaWdudW1iZXIiLCJ0eXBlIjoiQmlnTnVtYmVyIn0sInR5cGUiOiJCaWdOdW1iZXIifSx7ImtpbmQiOjM0LCJuYW1lIjoianNvbiIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6Impzb24iLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkpTT04ifSwidHlwZSI6IkpTT04ifSx7ImtpbmQiOjM0LCJuYW1lIjoib3B0SnNvbiIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoib3B0SnNvbiIsInR5cGUiOiJKU09OIn0sInR5cGUiOiJKU09OIn0seyJraW5kIjozNCwibmFtZSI6ImJ5dGVzIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiYnl0ZXMiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkJ5dGVzIn0sInR5cGUiOiJCeXRlcyJ9LHsia2luZCI6MzQsIm5hbWUiOiJvcHRCeXRlcyIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoib3B0Qnl0ZXMiLCJ0eXBlIjoiQnl0ZXMifSwidHlwZSI6IkJ5dGVzIn0seyJraW5kIjozNCwibmFtZSI6ImJvb2xlYW4iLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJib29sZWFuIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJCb29sZWFuIn0sInR5cGUiOiJCb29sZWFuIn0seyJraW5kIjozNCwibmFtZSI6Im9wdEJvb2xlYW4iLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6Im9wdEJvb2xlYW4iLCJ0eXBlIjoiQm9vbGVhbiJ9LCJ0eXBlIjoiQm9vbGVhbiJ9LHsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoidV9hcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludCJ9LCJraW5kIjoxOCwibmFtZSI6InVfYXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJ1X2FycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50In0sInR5cGUiOiJbVUludF0ifSwia2luZCI6MzQsIm5hbWUiOiJ1X2FycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbVUludF0ifSx7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6InVPcHRfYXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQifSwia2luZCI6MTgsIm5hbWUiOiJ1T3B0X2FycmF5Iiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJ1T3B0X2FycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50In0sInR5cGUiOiJbVUludF0ifSwia2luZCI6MzQsIm5hbWUiOiJ1T3B0X2FycmF5IiwidHlwZSI6IltVSW50XSJ9LHsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoiX29wdF91T3B0QXJyYXkiLCJ0eXBlIjoiVUludCJ9LCJraW5kIjoxOCwibmFtZSI6Il9vcHRfdU9wdEFycmF5Iiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJfb3B0X3VPcHRBcnJheSIsInR5cGUiOiJVSW50In0sInR5cGUiOiJbVUludF0ifSwia2luZCI6MzQsIm5hbWUiOiJfb3B0X3VPcHRBcnJheSIsInR5cGUiOiJbVUludF0ifSx7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6Im9wdFN0ck9wdEFycmF5IiwidHlwZSI6IlN0cmluZyJ9LCJraW5kIjoxOCwibmFtZSI6Im9wdFN0ck9wdEFycmF5Iiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJvcHRTdHJPcHRBcnJheSIsInR5cGUiOiJTdHJpbmcifSwidHlwZSI6IltTdHJpbmddIn0sImtpbmQiOjM0LCJuYW1lIjoib3B0U3RyT3B0QXJyYXkiLCJ0eXBlIjoiW1N0cmluZ10ifSx7ImFycmF5Ijp7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6InVBcnJheUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50In0sImtpbmQiOjE4LCJuYW1lIjoidUFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJ1QXJyYXlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludCJ9LCJ0eXBlIjoiW1VJbnRdIn0sIml0ZW0iOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoidUFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQifSwia2luZCI6MTgsIm5hbWUiOiJ1QXJyYXlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InVBcnJheUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50In0sInR5cGUiOiJbVUludF0ifSwia2luZCI6MTgsIm5hbWUiOiJ1QXJyYXlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW1tVSW50XV0ifSwia2luZCI6MzQsIm5hbWUiOiJ1QXJyYXlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW1tVSW50XV0ifSx7ImFycmF5Ijp7ImFycmF5Ijp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6InVPcHRBcnJheU9wdEFycmF5IiwidHlwZSI6IlVJbnQzMiJ9LCJraW5kIjoxOCwibmFtZSI6InVPcHRBcnJheU9wdEFycmF5Iiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJ1T3B0QXJyYXlPcHRBcnJheSIsInR5cGUiOiJVSW50MzIifSwidHlwZSI6IltVSW50MzJdIn0sIml0ZW0iOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoidU9wdEFycmF5T3B0QXJyYXkiLCJ0eXBlIjoiVUludDMyIn0sImtpbmQiOjE4LCJuYW1lIjoidU9wdEFycmF5T3B0QXJyYXkiLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InVPcHRBcnJheU9wdEFycmF5IiwidHlwZSI6IlVJbnQzMiJ9LCJ0eXBlIjoiW1VJbnQzMl0ifSwia2luZCI6MTgsIm5hbWUiOiJ1T3B0QXJyYXlPcHRBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW1tVSW50MzJdXSJ9LCJraW5kIjozNCwibmFtZSI6InVPcHRBcnJheU9wdEFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbW1VJbnQzMl1dIn0seyJhcnJheSI6eyJhcnJheSI6eyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJ1QXJyYXlPcHRBcnJheUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwia2luZCI6MTgsIm5hbWUiOiJ1QXJyYXlPcHRBcnJheUFycmF5IiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoidUFycmF5T3B0QXJyYXlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sInR5cGUiOiJbVUludDMyXSJ9LCJpdGVtIjp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6InVBcnJheU9wdEFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQzMiJ9LCJraW5kIjoxOCwibmFtZSI6InVBcnJheU9wdEFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJ1QXJyYXlPcHRBcnJheUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwidHlwZSI6IltVSW50MzJdIn0sImtpbmQiOjE4LCJuYW1lIjoidUFycmF5T3B0QXJyYXlBcnJheSIsInR5cGUiOiJbW1VJbnQzMl1dIn0sIml0ZW0iOnsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoidUFycmF5T3B0QXJyYXlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sImtpbmQiOjE4LCJuYW1lIjoidUFycmF5T3B0QXJyYXlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InVBcnJheU9wdEFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQzMiJ9LCJ0eXBlIjoiW1VJbnQzMl0ifSwiaXRlbSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJ1QXJyYXlPcHRBcnJheUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwia2luZCI6MTgsIm5hbWUiOiJ1QXJyYXlPcHRBcnJheUFycmF5IiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoidUFycmF5T3B0QXJyYXlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sInR5cGUiOiJbVUludDMyXSJ9LCJraW5kIjoxOCwibmFtZSI6InVBcnJheU9wdEFycmF5QXJyYXkiLCJ0eXBlIjoiW1tVSW50MzJdXSJ9LCJraW5kIjoxOCwibmFtZSI6InVBcnJheU9wdEFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltbW1VJbnQzMl1dXSJ9LCJraW5kIjozNCwibmFtZSI6InVBcnJheU9wdEFycmF5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltbW1VJbnQzMl1dXSJ9LHsiYXJyYXkiOnsiYXJyYXkiOnsiYXJyYXkiOnsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoiY3JhenlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sImtpbmQiOjE4LCJuYW1lIjoiY3JhenlBcnJheSIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiY3JhenlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sInR5cGUiOiJbVUludDMyXSJ9LCJpdGVtIjp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6ImNyYXp5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQzMiJ9LCJraW5kIjoxOCwibmFtZSI6ImNyYXp5QXJyYXkiLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6ImNyYXp5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQzMiJ9LCJ0eXBlIjoiW1VJbnQzMl0ifSwia2luZCI6MTgsIm5hbWUiOiJjcmF6eUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbW1VJbnQzMl1dIn0sIml0ZW0iOnsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoiY3JhenlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sImtpbmQiOjE4LCJuYW1lIjoiY3JhenlBcnJheSIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiY3JhenlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sInR5cGUiOiJbVUludDMyXSJ9LCJpdGVtIjp7Iml0ZW0iOnsia2luZCI6NCwibmFtZSI6ImNyYXp5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQzMiJ9LCJraW5kIjoxOCwibmFtZSI6ImNyYXp5QXJyYXkiLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6ImNyYXp5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlVJbnQzMiJ9LCJ0eXBlIjoiW1VJbnQzMl0ifSwia2luZCI6MTgsIm5hbWUiOiJjcmF6eUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbW1VJbnQzMl1dIn0sImtpbmQiOjE4LCJuYW1lIjoiY3JhenlBcnJheSIsInR5cGUiOiJbW1tVSW50MzJdXV0ifSwiaXRlbSI6eyJhcnJheSI6eyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJjcmF6eUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwia2luZCI6MTgsIm5hbWUiOiJjcmF6eUFycmF5Iiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJjcmF6eUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwidHlwZSI6IltVSW50MzJdIn0sIml0ZW0iOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoiY3JhenlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sImtpbmQiOjE4LCJuYW1lIjoiY3JhenlBcnJheSIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiY3JhenlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sInR5cGUiOiJbVUludDMyXSJ9LCJraW5kIjoxOCwibmFtZSI6ImNyYXp5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltbVUludDMyXV0ifSwiaXRlbSI6eyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJjcmF6eUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwia2luZCI6MTgsIm5hbWUiOiJjcmF6eUFycmF5Iiwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJjcmF6eUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJVSW50MzIifSwidHlwZSI6IltVSW50MzJdIn0sIml0ZW0iOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoiY3JhenlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sImtpbmQiOjE4LCJuYW1lIjoiY3JhenlBcnJheSIsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiY3JhenlBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiVUludDMyIn0sInR5cGUiOiJbVUludDMyXSJ9LCJraW5kIjoxOCwibmFtZSI6ImNyYXp5QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltbVUludDMyXV0ifSwia2luZCI6MTgsIm5hbWUiOiJjcmF6eUFycmF5IiwidHlwZSI6IltbW1VJbnQzMl1dXSJ9LCJraW5kIjoxOCwibmFtZSI6ImNyYXp5QXJyYXkiLCJ0eXBlIjoiW1tbW1VJbnQzMl1dXV0ifSwia2luZCI6MzQsIm5hbWUiOiJjcmF6eUFycmF5IiwidHlwZSI6IltbW1tVSW50MzJdXV1dIn0seyJraW5kIjozNCwibmFtZSI6Im9iamVjdCIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib2JqZWN0IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkFub3RoZXJUeXBlIn0seyJraW5kIjozNCwibmFtZSI6Im9wdE9iamVjdCIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib3B0T2JqZWN0IiwidHlwZSI6IkFub3RoZXJUeXBlIn0sInR5cGUiOiJBbm90aGVyVHlwZSJ9LHsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo4MTkyLCJuYW1lIjoib2JqZWN0QXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkFub3RoZXJUeXBlIn0sImtpbmQiOjE4LCJuYW1lIjoib2JqZWN0QXJyYXkiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im9iamVjdEFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltBbm90aGVyVHlwZV0ifSwia2luZCI6MzQsIm5hbWUiOiJvYmplY3RBcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW0Fub3RoZXJUeXBlXSJ9LHsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo4MTkyLCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwia2luZCI6MTgsIm5hbWUiOiJvcHRPYmplY3RBcnJheSIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoib3B0T2JqZWN0QXJyYXkiLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwidHlwZSI6IltBbm90aGVyVHlwZV0ifSwia2luZCI6MzQsIm5hbWUiOiJvcHRPYmplY3RBcnJheSIsInR5cGUiOiJbQW5vdGhlclR5cGVdIn0seyJlbnVtIjp7ImtpbmQiOjE2Mzg0LCJuYW1lIjoiZW4iLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkN1c3RvbUVudW0ifSwia2luZCI6MzQsIm5hbWUiOiJlbiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQ3VzdG9tRW51bSJ9LHsiZW51bSI6eyJraW5kIjoxNjM4NCwibmFtZSI6Im9wdEVudW0iLCJ0eXBlIjoiQ3VzdG9tRW51bSJ9LCJraW5kIjozNCwibmFtZSI6Im9wdEVudW0iLCJ0eXBlIjoiQ3VzdG9tRW51bSJ9LHsiYXJyYXkiOnsiZW51bSI6eyJraW5kIjoxNjM4NCwibmFtZSI6ImVudW1BcnJheSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQ3VzdG9tRW51bSJ9LCJpdGVtIjp7ImtpbmQiOjE2Mzg0LCJuYW1lIjoiZW51bUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJDdXN0b21FbnVtIn0sImtpbmQiOjE4LCJuYW1lIjoiZW51bUFycmF5IiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbQ3VzdG9tRW51bV0ifSwia2luZCI6MzQsIm5hbWUiOiJlbnVtQXJyYXkiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IltDdXN0b21FbnVtXSJ9LHsiYXJyYXkiOnsiZW51bSI6eyJraW5kIjoxNjM4NCwibmFtZSI6Im9wdEVudW1BcnJheSIsInR5cGUiOiJDdXN0b21FbnVtIn0sIml0ZW0iOnsia2luZCI6MTYzODQsIm5hbWUiOiJvcHRFbnVtQXJyYXkiLCJ0eXBlIjoiQ3VzdG9tRW51bSJ9LCJraW5kIjoxOCwibmFtZSI6Im9wdEVudW1BcnJheSIsInR5cGUiOiJbQ3VzdG9tRW51bV0ifSwia2luZCI6MzQsIm5hbWUiOiJvcHRFbnVtQXJyYXkiLCJ0eXBlIjoiW0N1c3RvbUVudW1dIn0seyJraW5kIjozNCwibWFwIjp7ImtleSI6eyJraW5kIjo0LCJuYW1lIjoibWFwIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwia2luZCI6MjYyMTQ2LCJuYW1lIjoibWFwIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoibWFwIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJJbnQifSwidHlwZSI6Ik1hcDxTdHJpbmcsIEludD4iLCJ2YWx1ZSI6eyJraW5kIjo0LCJuYW1lIjoibWFwIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJJbnQifX0sIm5hbWUiOiJtYXAiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6Ik1hcDxTdHJpbmcsIEludD4ifSx7ImtpbmQiOjM0LCJtYXAiOnsiYXJyYXkiOnsiaXRlbSI6eyJraW5kIjo0LCJuYW1lIjoibWFwT2ZBcnIiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkludCJ9LCJraW5kIjoxOCwibmFtZSI6Im1hcE9mQXJyIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoibWFwT2ZBcnIiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkludCJ9LCJ0eXBlIjoiW0ludF0ifSwia2V5Ijp7ImtpbmQiOjQsIm5hbWUiOiJtYXBPZkFyciIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sImtpbmQiOjI2MjE0NiwibmFtZSI6Im1hcE9mQXJyIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJNYXA8U3RyaW5nLCBbSW50XT4iLCJ2YWx1ZSI6eyJpdGVtIjp7ImtpbmQiOjQsIm5hbWUiOiJtYXBPZkFyciIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50In0sImtpbmQiOjE4LCJuYW1lIjoibWFwT2ZBcnIiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJtYXBPZkFyciIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiSW50In0sInR5cGUiOiJbSW50XSJ9fSwibmFtZSI6Im1hcE9mQXJyIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJNYXA8U3RyaW5nLCBbSW50XT4ifSx7ImtpbmQiOjM0LCJtYXAiOnsia2V5Ijp7ImtpbmQiOjQsIm5hbWUiOiJtYXBPZk9iaiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sImtpbmQiOjI2MjE0NiwibmFtZSI6Im1hcE9mT2JqIiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJtYXBPZk9iaiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJNYXA8U3RyaW5nLCBBbm90aGVyVHlwZT4iLCJ2YWx1ZSI6eyJraW5kIjo4MTkyLCJuYW1lIjoibWFwT2ZPYmoiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkFub3RoZXJUeXBlIn19LCJuYW1lIjoibWFwT2ZPYmoiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6Ik1hcDxTdHJpbmcsIEFub3RoZXJUeXBlPiJ9LHsia2luZCI6MzQsIm1hcCI6eyJhcnJheSI6eyJpdGVtIjp7ImtpbmQiOjgxOTIsIm5hbWUiOiJtYXBPZkFyck9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJBbm90aGVyVHlwZSJ9LCJraW5kIjoxOCwibmFtZSI6Im1hcE9mQXJyT2ZPYmoiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6Im1hcE9mQXJyT2ZPYmoiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkFub3RoZXJUeXBlIn0sInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiW0Fub3RoZXJUeXBlXSJ9LCJrZXkiOnsia2luZCI6NCwibmFtZSI6Im1hcE9mQXJyT2ZPYmoiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IlN0cmluZyJ9LCJraW5kIjoyNjIxNDYsIm5hbWUiOiJtYXBPZkFyck9mT2JqIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJNYXA8U3RyaW5nLCBbQW5vdGhlclR5cGVdPiIsInZhbHVlIjp7Iml0ZW0iOnsia2luZCI6ODE5MiwibmFtZSI6Im1hcE9mQXJyT2ZPYmoiLCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6IkFub3RoZXJUeXBlIn0sImtpbmQiOjE4LCJuYW1lIjoibWFwT2ZBcnJPZk9iaiIsIm9iamVjdCI6eyJraW5kIjo4MTkyLCJuYW1lIjoibWFwT2ZBcnJPZk9iaiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiQW5vdGhlclR5cGUifSwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJbQW5vdGhlclR5cGVdIn19LCJuYW1lIjoibWFwT2ZBcnJPZk9iaiIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiTWFwPFN0cmluZywgW0Fub3RoZXJUeXBlXT4ifSx7ImtpbmQiOjM0LCJtYXAiOnsia2V5Ijp7ImtpbmQiOjQsIm5hbWUiOiJtYXBDdXN0b21WYWx1ZSIsInJlcXVpcmVkIjp0cnVlLCJ0eXBlIjoiU3RyaW5nIn0sImtpbmQiOjI2MjE0NiwibmFtZSI6Im1hcEN1c3RvbVZhbHVlIiwib2JqZWN0Ijp7ImtpbmQiOjgxOTIsIm5hbWUiOiJtYXBDdXN0b21WYWx1ZSIsInR5cGUiOiJDdXN0b21NYXBWYWx1ZSJ9LCJyZXF1aXJlZCI6dHJ1ZSwidHlwZSI6Ik1hcDxTdHJpbmcsIEN1c3RvbU1hcFZhbHVlPiIsInZhbHVlIjp7ImtpbmQiOjgxOTIsIm5hbWUiOiJtYXBDdXN0b21WYWx1ZSIsInR5cGUiOiJDdXN0b21NYXBWYWx1ZSJ9fSwibmFtZSI6Im1hcEN1c3RvbVZhbHVlIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJNYXA8U3RyaW5nLCBDdXN0b21NYXBWYWx1ZT4ifV0sInR5cGUiOiJDdXN0b21UeXBlIn0seyJraW5kIjoxLCJwcm9wZXJ0aWVzIjpbeyJraW5kIjozNCwibmFtZSI6InByb3AiLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6InByb3AiLCJ0eXBlIjoiU3RyaW5nIn0sInR5cGUiOiJTdHJpbmcifSx7ImtpbmQiOjM0LCJuYW1lIjoiY2lyY3VsYXIiLCJvYmplY3QiOnsia2luZCI6ODE5MiwibmFtZSI6ImNpcmN1bGFyIiwidHlwZSI6IkN1c3RvbVR5cGUifSwidHlwZSI6IkN1c3RvbVR5cGUifSx7ImtpbmQiOjM0LCJuYW1lIjoiY29uc3QiLCJzY2FsYXIiOnsia2luZCI6NCwibmFtZSI6ImNvbnN0IiwidHlwZSI6IlN0cmluZyJ9LCJ0eXBlIjoiU3RyaW5nIn1dLCJ0eXBlIjoiQW5vdGhlclR5cGUifSx7ImtpbmQiOjEsInByb3BlcnRpZXMiOlt7ImtpbmQiOjM0LCJuYW1lIjoiZm9vIiwicmVxdWlyZWQiOnRydWUsInNjYWxhciI6eyJraW5kIjo0LCJuYW1lIjoiZm9vIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwidHlwZSI6IlN0cmluZyJ9XSwidHlwZSI6IkN1c3RvbU1hcFZhbHVlIn0seyJraW5kIjoxLCJwcm9wZXJ0aWVzIjpbeyJraW5kIjozNCwibmFtZSI6ImVsc2UiLCJyZXF1aXJlZCI6dHJ1ZSwic2NhbGFyIjp7ImtpbmQiOjQsIm5hbWUiOiJlbHNlIiwicmVxdWlyZWQiOnRydWUsInR5cGUiOiJTdHJpbmcifSwidHlwZSI6IlN0cmluZyJ9XSwidHlwZSI6ImVsc2UifV0sInZlcnNpb24iOiIwLjEifQ==").decode("utf-8")) manifest = WrapManifest.parse_obj({ "name": "Test", diff --git a/packages/test-cases/cases/bind/sanity/output/plugin-rs/types.rs b/packages/test-cases/cases/bind/sanity/output/plugin-rs/types.rs index ca26e879f4..5fa5328f10 100644 --- a/packages/test-cases/cases/bind/sanity/output/plugin-rs/types.rs +++ b/packages/test-cases/cases/bind/sanity/output/plugin-rs/types.rs @@ -57,12 +57,11 @@ pub struct CustomType { pub boolean: bool, #[serde(rename = "optBoolean")] pub opt_boolean: Option, - #[serde(rename = "uArray")] pub u_array: Vec, - #[serde(rename = "uOptArray")] + #[serde(rename = "uOpt_array")] pub u_opt_array: Option>, - #[serde(rename = "optUOptArray")] - pub opt_u_opt_array: Option>>, + #[serde(rename = "_opt_uOptArray")] + pub _opt_u_opt_array: Option>>, #[serde(rename = "optStrOptArray")] pub opt_str_opt_array: Option>>, #[serde(rename = "uArrayArray")] diff --git a/packages/test-cases/cases/bind/sanity/output/plugin-rs/wrap.info.rs b/packages/test-cases/cases/bind/sanity/output/plugin-rs/wrap.info.rs index f96a902634..1df571de16 100644 --- a/packages/test-cases/cases/bind/sanity/output/plugin-rs/wrap.info.rs +++ b/packages/test-cases/cases/bind/sanity/output/plugin-rs/wrap.info.rs @@ -1460,23 +1460,23 @@ pub fn get_manifest() -> WrapManifest { "array": { "item": { "kind": 4, - "name": "uArray", + "name": "u_array", "required": true, "type": "UInt" }, "kind": 18, - "name": "uArray", + "name": "u_array", "required": true, "scalar": { "kind": 4, - "name": "uArray", + "name": "u_array", "required": true, "type": "UInt" }, "type": "[UInt]" }, "kind": 34, - "name": "uArray", + "name": "u_array", "required": true, "type": "[UInt]" }, @@ -1484,42 +1484,42 @@ pub fn get_manifest() -> WrapManifest { "array": { "item": { "kind": 4, - "name": "uOptArray", + "name": "uOpt_array", "required": true, "type": "UInt" }, "kind": 18, - "name": "uOptArray", + "name": "uOpt_array", "scalar": { "kind": 4, - "name": "uOptArray", + "name": "uOpt_array", "required": true, "type": "UInt" }, "type": "[UInt]" }, "kind": 34, - "name": "uOptArray", + "name": "uOpt_array", "type": "[UInt]" }, { "array": { "item": { "kind": 4, - "name": "optUOptArray", + "name": "_opt_uOptArray", "type": "UInt" }, "kind": 18, - "name": "optUOptArray", + "name": "_opt_uOptArray", "scalar": { "kind": 4, - "name": "optUOptArray", + "name": "_opt_uOptArray", "type": "UInt" }, "type": "[UInt]" }, "kind": 34, - "name": "optUOptArray", + "name": "_opt_uOptArray", "type": "[UInt]" }, { diff --git a/packages/test-cases/cases/bind/sanity/output/plugin-ts/types.ts b/packages/test-cases/cases/bind/sanity/output/plugin-ts/types.ts index 2c19aa819b..428ddf9e92 100644 --- a/packages/test-cases/cases/bind/sanity/output/plugin-ts/types.ts +++ b/packages/test-cases/cases/bind/sanity/output/plugin-ts/types.ts @@ -58,9 +58,9 @@ export interface CustomType { optBytes?: Types.Bytes | null; boolean: Types.Boolean; optBoolean?: Types.Boolean | null; - uArray: Array; - uOptArray?: Array | null; - optUOptArray?: Array | null; + u_array: Array; + uOpt_array?: Array | null; + _opt_uOptArray?: Array | null; optStrOptArray?: Array | null; uArrayArray: Array>; uOptArrayOptArray: Array | null>; diff --git a/packages/test-cases/cases/bind/sanity/output/plugin-ts/wrap.info.ts b/packages/test-cases/cases/bind/sanity/output/plugin-ts/wrap.info.ts index c0569780a7..c8ad69aab1 100644 --- a/packages/test-cases/cases/bind/sanity/output/plugin-ts/wrap.info.ts +++ b/packages/test-cases/cases/bind/sanity/output/plugin-ts/wrap.info.ts @@ -1458,23 +1458,23 @@ export const manifest: WrapManifest = { "array": { "item": { "kind": 4, - "name": "uArray", + "name": "u_array", "required": true, "type": "UInt" }, "kind": 18, - "name": "uArray", + "name": "u_array", "required": true, "scalar": { "kind": 4, - "name": "uArray", + "name": "u_array", "required": true, "type": "UInt" }, "type": "[UInt]" }, "kind": 34, - "name": "uArray", + "name": "u_array", "required": true, "type": "[UInt]" }, @@ -1482,42 +1482,42 @@ export const manifest: WrapManifest = { "array": { "item": { "kind": 4, - "name": "uOptArray", + "name": "uOpt_array", "required": true, "type": "UInt" }, "kind": 18, - "name": "uOptArray", + "name": "uOpt_array", "scalar": { "kind": 4, - "name": "uOptArray", + "name": "uOpt_array", "required": true, "type": "UInt" }, "type": "[UInt]" }, "kind": 34, - "name": "uOptArray", + "name": "uOpt_array", "type": "[UInt]" }, { "array": { "item": { "kind": 4, - "name": "optUOptArray", + "name": "_opt_uOptArray", "type": "UInt" }, "kind": 18, - "name": "optUOptArray", + "name": "_opt_uOptArray", "scalar": { "kind": 4, - "name": "optUOptArray", + "name": "_opt_uOptArray", "type": "UInt" }, "type": "[UInt]" }, "kind": 34, - "name": "optUOptArray", + "name": "_opt_uOptArray", "type": "[UInt]" }, { diff --git a/packages/test-cases/cases/bind/sanity/output/wasm-as/CustomType/index.ts b/packages/test-cases/cases/bind/sanity/output/wasm-as/CustomType/index.ts index 64b2cdf31c..3a0d39079e 100644 --- a/packages/test-cases/cases/bind/sanity/output/wasm-as/CustomType/index.ts +++ b/packages/test-cases/cases/bind/sanity/output/wasm-as/CustomType/index.ts @@ -36,9 +36,9 @@ export class CustomType { optBytes: ArrayBuffer | null; _boolean: bool; optBoolean: Box | null; - uArray: Array; - uOptArray: Array | null; - optUOptArray: Array | null> | null; + u_array: Array; + uOpt_array: Array | null; + _opt_uOptArray: Array | null> | null; optStrOptArray: Array | null; uArrayArray: Array>; uOptArrayOptArray: Array | null> | null>; diff --git a/packages/test-cases/cases/bind/sanity/output/wasm-as/CustomType/serialization.ts b/packages/test-cases/cases/bind/sanity/output/wasm-as/CustomType/serialization.ts index b555b83786..fa047d5f7d 100644 --- a/packages/test-cases/cases/bind/sanity/output/wasm-as/CustomType/serialization.ts +++ b/packages/test-cases/cases/bind/sanity/output/wasm-as/CustomType/serialization.ts @@ -110,21 +110,21 @@ export function writeCustomType(writer: Write, type: CustomType): void { writer.writeString("optBoolean"); writer.writeOptionalBool(type.optBoolean); writer.context().pop(); - writer.context().push("uArray", "Array", "writing property"); - writer.writeString("uArray"); - writer.writeArray(type.uArray, (writer: Write, item: u32): void => { + writer.context().push("u_array", "Array", "writing property"); + writer.writeString("u_array"); + writer.writeArray(type.u_array, (writer: Write, item: u32): void => { writer.writeUInt32(item); }); writer.context().pop(); - writer.context().push("uOptArray", "Array | null", "writing property"); - writer.writeString("uOptArray"); - writer.writeOptionalArray(type.uOptArray, (writer: Write, item: u32): void => { + writer.context().push("uOpt_array", "Array | null", "writing property"); + writer.writeString("uOpt_array"); + writer.writeOptionalArray(type.uOpt_array, (writer: Write, item: u32): void => { writer.writeUInt32(item); }); writer.context().pop(); - writer.context().push("optUOptArray", "Array | null> | null", "writing property"); - writer.writeString("optUOptArray"); - writer.writeOptionalArray(type.optUOptArray, (writer: Write, item: Box | null): void => { + writer.context().push("_opt_uOptArray", "Array | null> | null", "writing property"); + writer.writeString("_opt_uOptArray"); + writer.writeOptionalArray(type._opt_uOptArray, (writer: Write, item: Box | null): void => { writer.writeOptionalUInt32(item); }); writer.context().pop(); @@ -314,10 +314,10 @@ export function readCustomType(reader: Read): CustomType { let _boolean: bool = false; let _booleanSet: bool = false; let _optBoolean: Box | null = null; - let _uArray: Array = []; - let _uArraySet: bool = false; - let _uOptArray: Array | null = null; - let _optUOptArray: Array | null> | null = null; + let _u_array: Array = []; + let _u_arraySet: bool = false; + let _uOpt_array: Array | null = null; + let __opt_uOptArray: Array | null> | null = null; let _optStrOptArray: Array | null = null; let _uArrayArray: Array> = []; let _uArrayArraySet: bool = false; @@ -473,24 +473,24 @@ export function readCustomType(reader: Read): CustomType { _optBoolean = reader.readOptionalBool(); reader.context().pop(); } - else if (field == "uArray") { + else if (field == "u_array") { reader.context().push(field, "Array", "type found, reading property"); - _uArray = reader.readArray((reader: Read): u32 => { + _u_array = reader.readArray((reader: Read): u32 => { return reader.readUInt32(); }); - _uArraySet = true; + _u_arraySet = true; reader.context().pop(); } - else if (field == "uOptArray") { + else if (field == "uOpt_array") { reader.context().push(field, "Array | null", "type found, reading property"); - _uOptArray = reader.readOptionalArray((reader: Read): u32 => { + _uOpt_array = reader.readOptionalArray((reader: Read): u32 => { return reader.readUInt32(); }); reader.context().pop(); } - else if (field == "optUOptArray") { + else if (field == "_opt_uOptArray") { reader.context().push(field, "Array | null> | null", "type found, reading property"); - _optUOptArray = reader.readOptionalArray((reader: Read): Box | null => { + __opt_uOptArray = reader.readOptionalArray((reader: Read): Box | null => { return reader.readOptionalUInt32(); }); reader.context().pop(); @@ -758,8 +758,8 @@ export function readCustomType(reader: Read): CustomType { if (!_booleanSet) { throw new Error(reader.context().printWithContext("Missing required property: 'boolean: Boolean'")); } - if (!_uArraySet) { - throw new Error(reader.context().printWithContext("Missing required property: 'uArray: [UInt]'")); + if (!_u_arraySet) { + throw new Error(reader.context().printWithContext("Missing required property: 'u_array: [UInt]'")); } if (!_uArrayArraySet) { throw new Error(reader.context().printWithContext("Missing required property: 'uArrayArray: [[UInt]]'")); @@ -820,9 +820,9 @@ export function readCustomType(reader: Read): CustomType { optBytes: _optBytes, _boolean: _boolean, optBoolean: _optBoolean, - uArray: _uArray, - uOptArray: _uOptArray, - optUOptArray: _optUOptArray, + u_array: _u_array, + uOpt_array: _uOpt_array, + _opt_uOptArray: __opt_uOptArray, optStrOptArray: _optStrOptArray, uArrayArray: _uArrayArray, uOptArrayOptArray: _uOptArrayOptArray, diff --git a/packages/test-cases/cases/bind/sanity/output/wasm-rs/custom_type/mod.rs b/packages/test-cases/cases/bind/sanity/output/wasm-rs/custom_type/mod.rs index aae2ab3e1d..a15c664dc8 100644 --- a/packages/test-cases/cases/bind/sanity/output/wasm-rs/custom_type/mod.rs +++ b/packages/test-cases/cases/bind/sanity/output/wasm-rs/custom_type/mod.rs @@ -46,7 +46,7 @@ pub struct CustomType { pub opt_boolean: Option, pub u_array: Vec, pub u_opt_array: Option>, - pub opt_u_opt_array: Option>>, + pub _opt_u_opt_array: Option>>, pub opt_str_opt_array: Option>>, pub u_array_array: Vec>, pub u_opt_array_opt_array: Vec>>>, @@ -93,7 +93,7 @@ impl CustomType { opt_boolean: None, u_array: vec![], u_opt_array: None, - opt_u_opt_array: None, + _opt_u_opt_array: None, opt_str_opt_array: None, u_array_array: vec![], u_opt_array_opt_array: vec![], diff --git a/packages/test-cases/cases/bind/sanity/output/wasm-rs/custom_type/serialization.rs b/packages/test-cases/cases/bind/sanity/output/wasm-rs/custom_type/serialization.rs index 4626afe640..a9faa0a662 100644 --- a/packages/test-cases/cases/bind/sanity/output/wasm-rs/custom_type/serialization.rs +++ b/packages/test-cases/cases/bind/sanity/output/wasm-rs/custom_type/serialization.rs @@ -116,21 +116,21 @@ pub fn write_custom_type(args: &CustomType, writer: &mut W) -> Result< writer.write_string("optBoolean")?; writer.write_optional_bool(&args.opt_boolean)?; writer.context().pop(); - writer.context().push("uArray", "Vec", "writing property"); - writer.write_string("uArray")?; + writer.context().push("u_array", "Vec", "writing property"); + writer.write_string("u_array")?; writer.write_array(&args.u_array, |writer, item| { writer.write_u32(item) })?; writer.context().pop(); - writer.context().push("uOptArray", "Option>", "writing property"); - writer.write_string("uOptArray")?; + writer.context().push("uOpt_array", "Option>", "writing property"); + writer.write_string("uOpt_array")?; writer.write_optional_array(&args.u_opt_array, |writer, item| { writer.write_u32(item) })?; writer.context().pop(); - writer.context().push("optUOptArray", "Option>>", "writing property"); - writer.write_string("optUOptArray")?; - writer.write_optional_array(&args.opt_u_opt_array, |writer, item| { + writer.context().push("_opt_uOptArray", "Option>>", "writing property"); + writer.write_string("_opt_uOptArray")?; + writer.write_optional_array(&args._opt_u_opt_array, |writer, item| { writer.write_optional_u32(item) })?; writer.context().pop(); @@ -325,7 +325,7 @@ pub fn read_custom_type(reader: &mut R) -> Result = vec![]; let mut _u_array_set = false; let mut _u_opt_array: Option> = None; - let mut _opt_u_opt_array: Option>> = None; + let mut __opt_u_opt_array: Option>> = None; let mut _opt_str_opt_array: Option>> = None; let mut _u_array_array: Vec> = vec![]; let mut _u_array_array_set = false; @@ -481,7 +481,7 @@ pub fn read_custom_type(reader: &mut R) -> Result { + "u_array" => { reader.context().push(&field, "Vec", "type found, reading property"); _u_array = reader.read_array(|reader| { reader.read_u32() @@ -489,16 +489,16 @@ pub fn read_custom_type(reader: &mut R) -> Result { + "uOpt_array" => { reader.context().push(&field, "Option>", "type found, reading property"); _u_opt_array = reader.read_optional_array(|reader| { reader.read_u32() })?; reader.context().pop(); } - "optUOptArray" => { + "_opt_uOptArray" => { reader.context().push(&field, "Option>>", "type found, reading property"); - _opt_u_opt_array = reader.read_optional_array(|reader| { + __opt_u_opt_array = reader.read_optional_array(|reader| { reader.read_optional_u32() })?; reader.context().pop(); @@ -765,7 +765,7 @@ pub fn read_custom_type(reader: &mut R) -> Result(reader: &mut R) -> Result Date: Wed, 19 Apr 2023 01:25:19 -0500 Subject: [PATCH 15/19] chore: remove javascript-client packages --- package.json | 14 +- packages/js/asyncify/README.md | 29 - packages/js/asyncify/jest.config.js | 11 - packages/js/asyncify/package.json | 35 - packages/js/asyncify/src/AsyncWasmInstance.ts | 258 ----- .../src/__tests__/AsyncWasmInstance.spec.ts | 276 ------ .../src/__tests__/cases/multipleSleep.ts | 16 - .../src/__tests__/cases/simpleSleep.ts | 11 - packages/js/asyncify/src/index.ts | 1 - packages/js/asyncify/src/utils.ts | 53 -- packages/js/asyncify/tsconfig.build.json | 9 - packages/js/asyncify/tsconfig.json | 18 - packages/js/client-config-builder/.gitignore | 3 - packages/js/client-config-builder/README.md | 610 ------------ .../examples/quickstart.ts | 159 ---- .../examples/tsconfig.examples.json | 6 - .../js/client-config-builder/jest.config.js | 11 - .../js/client-config-builder/package.json | 91 -- .../js/client-config-builder/readme/README.md | 166 ---- .../scripts/embed-wrappers.ts | 69 -- .../src/BaseClientConfigBuilder.ts | 233 ----- .../src/ClientConfigBuilder.ts | 125 --- .../__tests__/client-config-builder.spec.ts | 861 ----------------- .../src/bundles/default.ts | 185 ---- .../embeds/async-ipfs-resolver/wrap.info | Bin 13743 -> 0 bytes .../embeds/async-ipfs-resolver/wrap.ts | 17 - .../embeds/async-ipfs-resolver/wrap.wasm | Bin 261485 -> 0 bytes .../bundles/embeds/ipfs-http-client/wrap.info | Bin 9034 -> 0 bytes .../bundles/embeds/ipfs-http-client/wrap.ts | 17 - .../bundles/embeds/ipfs-http-client/wrap.wasm | Bin 150523 -> 0 bytes .../src/bundles/index.ts | 1 - .../src/declarations.d.ts | 3 - .../js/client-config-builder/src/index.ts | 4 - .../src/types/BuildOptions.ts | 10 - .../src/types/IClientConfigBuilder.ts | 259 ----- .../src/types/configs/BuilderConfig.ts | 11 - .../src/types/configs/index.ts | 1 - .../client-config-builder/src/types/index.ts | 3 - .../client-config-builder/tsconfig.build.json | 12 - .../js/client-config-builder/tsconfig.json | 8 - packages/js/client/.gitignore | 3 - packages/js/client/README.md | 72 -- packages/js/client/examples/quickstart.ts | 38 - .../js/client/examples/tsconfig.examples.json | 6 - packages/js/client/jest.config.js | 12 - packages/js/client/package.json | 97 -- packages/js/client/readme/README.md | 53 -- packages/js/client/src/PolywrapClient.ts | 239 ----- .../__tests__/core/embedded-package.spec.ts | 179 ---- .../__tests__/core/embedded-wrapper.spec.ts | 173 ---- .../__tests__/core/error-structure.spec.ts | 533 ----------- .../src/__tests__/core/plugin-wrapper.spec.ts | 93 -- .../client/src/__tests__/core/sanity.spec.ts | 126 --- .../src/__tests__/core/type-test-cases.ts | 811 ---------------- .../core/uri-resolution/histories/sanity.json | 109 --- .../uri-resolution/uri-resolution.spec.ts | 117 --- .../src/__tests__/core/wasm-wrapper.spec.ts | 208 ---- .../__tests__/core/wrap-features/env-case.ts | 221 ----- .../interface-implementation-case.ts | 310 ------ .../core/wrap-features/subinvoke-case.ts | 32 - packages/js/client/src/__tests__/e2e.spec.ts | 15 - packages/js/client/src/__tests__/helpers.ts | 74 -- packages/js/client/src/index.ts | 6 - .../js/client/src/types/InvokerOptions.ts | 23 - .../client/src/types/TryResolveUriOptions.ts | 7 - packages/js/client/src/types/index.ts | 2 - packages/js/client/tsconfig.build.json | 12 - packages/js/client/tsconfig.json | 16 - packages/js/core-client/.gitignore | 3 - packages/js/core-client/README.md | 270 ------ .../js/core-client/examples/quickstart.ts | 34 - .../examples/tsconfig.examples.json | 6 - packages/js/core-client/jest.config.js | 11 - packages/js/core-client/package.json | 85 -- packages/js/core-client/readme/README.md | 115 --- .../js/core-client/src/PolywrapCoreClient.ts | 416 -------- .../src/__tests__/embedded-package.spec.ts | 169 ---- .../src/__tests__/embedded-wrapper.spec.ts | 169 ---- packages/js/core-client/src/index.ts | 1 - packages/js/core-client/tsconfig.build.json | 12 - packages/js/core-client/tsconfig.json | 16 - packages/js/core/.eslintignore | 1 - packages/js/core/.gitignore | 1 - packages/js/core/README.md | 711 -------------- packages/js/core/jest.config.js | 11 - packages/js/core/package.json | 46 - packages/js/core/readme/README.md | 79 -- packages/js/core/readme/config/final.json | 41 - .../js/core/readme/config/sub-sections.json | 38 - .../js/core/readme/sub-sections/base/Uri.md | 67 -- .../sub-sections/base/UriResolverInterface.md | 18 - .../sub-sections/base/uri-resolution.md | 37 - .../js/core/src/__tests__/MaybeAsync.spec.ts | 41 - packages/js/core/src/__tests__/Uri.spec.ts | 53 -- .../src/__tests__/get-implementations.spec.ts | 128 --- .../js/core/src/__tests__/is-buffer.spec.ts | 15 - .../core/src/__tests__/typesHandler.spec.ts | 57 -- .../js/core/src/algorithms/applyResolution.ts | 17 - .../clean-uri-history/CleanResolutionStep.ts | 1 - .../clean-uri-history/buildCleanUriHistory.ts | 89 -- .../src/algorithms/clean-uri-history/index.ts | 2 - .../src/algorithms/get-implementations.ts | 90 -- packages/js/core/src/algorithms/index.ts | 3 - packages/js/core/src/index.ts | 6 - packages/js/core/src/interfaces/index.ts | 1 - .../js/core/src/interfaces/uri-resolver.ts | 60 -- packages/js/core/src/types/CoreClient.ts | 122 --- packages/js/core/src/types/Env.ts | 7 - packages/js/core/src/types/IUriPackage.ts | 14 - packages/js/core/src/types/IUriRedirect.ts | 14 - packages/js/core/src/types/IUriWrapper.ts | 14 - packages/js/core/src/types/IWrapPackage.ts | 40 - packages/js/core/src/types/Invoke.ts | 97 -- packages/js/core/src/types/MaybeAsync.ts | 6 - packages/js/core/src/types/Uri.ts | 197 ---- packages/js/core/src/types/UriMap.ts | 67 -- packages/js/core/src/types/UriResolver.ts | 30 - packages/js/core/src/types/WrapError.ts | 293 ------ packages/js/core/src/types/Wrapper.ts | 46 - packages/js/core/src/types/index.ts | 13 - .../uri-resolution/IUriResolutionContext.ts | 56 -- .../src/uri-resolution/IUriResolutionStep.ts | 21 - .../core/src/uri-resolution/IUriResolver.ts | 24 - .../src/uri-resolution/UriPackageOrWrapper.ts | 25 - .../uri-resolution/UriResolutionContext.ts | 77 -- packages/js/core/src/uri-resolution/index.ts | 5 - packages/js/core/src/utils/combinePaths.ts | 17 - .../js/core/src/utils/getEnvFromUriHistory.ts | 16 - packages/js/core/src/utils/index.ts | 4 - packages/js/core/src/utils/is-buffer.ts | 7 - packages/js/core/src/utils/typesHandler.ts | 24 - packages/js/core/tsconfig.build.json | 9 - packages/js/core/tsconfig.json | 10 - packages/js/manifests/wrap/README.md | 3 - packages/js/manifests/wrap/jest.config.js | 11 - packages/js/manifests/wrap/package.json | 42 - .../js/manifests/wrap/scripts/generate.ts | 181 ---- .../scripts/templates/deserialize-ts.mustache | 52 - .../wrap/scripts/templates/index-ts.mustache | 68 -- .../scripts/templates/migrate-ts.mustache | 57 -- .../scripts/templates/serialize-ts.mustache | 18 - .../scripts/templates/validate-ts.mustache | 88 -- .../wrap/src/__tests__/WrapManifest.spec.ts | 139 --- .../js/manifests/wrap/src/compareSignature.ts | 25 - .../js/manifests/wrap/src/formats/index.ts | 1 - .../src/formats/wrap.info/0.1.schema.json | 626 ------------ .../wrap/src/formats/wrap.info/0.1.ts | 144 --- .../wrap/src/formats/wrap.info/deserialize.ts | 52 - .../wrap/src/formats/wrap.info/index.ts | 54 -- .../wrap/src/formats/wrap.info/migrate.ts | 37 - .../wrap/src/formats/wrap.info/serialize.ts | 18 - .../wrap/src/formats/wrap.info/validate.ts | 81 -- packages/js/manifests/wrap/src/index.ts | 3 - packages/js/manifests/wrap/src/types.ts | 7 - .../js/manifests/wrap/tsconfig.build.json | 9 - packages/js/manifests/wrap/tsconfig.json | 10 - packages/js/msgpack/README.md | 23 - packages/js/msgpack/jest.config.js | 11 - packages/js/msgpack/package.json | 34 - .../js/msgpack/src/__tests__/msgpack.spec.ts | 54 -- packages/js/msgpack/src/index.ts | 95 -- packages/js/msgpack/tsconfig.build.json | 9 - packages/js/msgpack/tsconfig.json | 18 - packages/js/plugin/README.md | 5 - packages/js/plugin/jest.config.js | 12 - packages/js/plugin/package.json | 41 - packages/js/plugin/src/PluginFactory.ts | 5 - packages/js/plugin/src/PluginMethod.ts | 16 - packages/js/plugin/src/PluginModule.ts | 65 -- packages/js/plugin/src/PluginPackage.ts | 60 -- packages/js/plugin/src/PluginWrapper.ts | 114 --- packages/js/plugin/src/index.ts | 5 - .../plugin/src/utils/GetPluginMethodsFunc.ts | 10 - .../src/utils/PluginModuleWithMethods.ts | 61 -- .../js/plugin/src/utils/getErrorSource.ts | 31 - packages/js/plugin/src/utils/index.ts | 2 - packages/js/plugin/tsconfig.build.json | 9 - packages/js/plugin/tsconfig.json | 10 - packages/js/result/README.md | 6 - packages/js/result/package.json | 26 - packages/js/result/src/Result.ts | 3 - packages/js/result/src/ResultErr.ts | 6 - packages/js/result/src/ResultOk.ts | 6 - packages/js/result/src/index.ts | 3 - packages/js/result/tsconfig.build.json | 9 - packages/js/result/tsconfig.json | 10 - packages/js/tracing/README.md | 27 - packages/js/tracing/package.json | 35 - packages/js/tracing/src/index.ts | 283 ------ packages/js/tracing/tsconfig.build.json | 9 - packages/js/tracing/tsconfig.json | 13 - .../js/uri-resolver-extensions/.gitignore | 4 - packages/js/uri-resolver-extensions/README.md | 259 ----- .../examples/quickstart.ts | 41 - .../examples/tsconfig.examples.json | 6 - .../js/uri-resolver-extensions/jest.config.js | 12 - .../js/uri-resolver-extensions/package.json | 88 -- .../uri-resolver-extensions/readme/README.md | 124 --- .../src/ExtendableUriResolver.ts | 134 --- .../src/ResolverExtensionLoader.ts | 55 -- .../src/UriResolverExtensionFileReader.ts | 66 -- .../src/UriResolverWrapper.ts | 139 --- .../__tests__/embeds/test-resolver/wrap.info | Bin 2337 -> 0 bytes .../__tests__/embeds/test-resolver/wrap.ts | 17 - .../__tests__/embeds/test-resolver/wrap.wasm | Bin 93333 -> 0 bytes .../src/__tests__/helpers/expectHistory.ts | 31 - .../histories/can-resolve-package.json | 14 - .../__tests__/histories/can-resolve-uri.json | 26 - .../src/__tests__/histories/not-a-match.json | 14 - .../histories/not-found-extension.json | 10 - .../shows-plugin-extension-error.json | 14 - .../histories/shows-wasm-extension-error.json | 14 - .../src/__tests__/resolver-extensions.spec.ts | 455 --------- .../wrappers/test-resolver/.gitignore | 6 - .../wrappers/test-resolver/Cargo.toml | 20 - .../test-resolver/polywrap.build.yaml | 4 - .../wrappers/test-resolver/polywrap.graphql | 5 - .../wrappers/test-resolver/polywrap.yaml | 9 - .../wrappers/test-resolver/src/lib.rs | 39 - .../wrappers/test-resolver/tsconfig.json | 28 - .../js/uri-resolver-extensions/src/index.ts | 3 - .../tsconfig.build.json | 9 - .../js/uri-resolver-extensions/tsconfig.json | 10 - packages/js/uri-resolvers/.gitignore | 4 - packages/js/uri-resolvers/README.md | 889 ------------------ .../js/uri-resolvers/examples/quickstart.ts | 32 - .../examples/tsconfig.examples.json | 6 - packages/js/uri-resolvers/jest.config.js | 12 - packages/js/uri-resolvers/package.json | 46 - packages/js/uri-resolvers/readme/README.md | 46 - .../js/uri-resolvers/readme/config/final.json | 42 - .../readme/config/sub-sections.json | 38 - .../readme/sub-sections/base/aggregator.md | 62 -- .../readme/sub-sections/base/cache.md | 45 - .../readme/sub-sections/base/helpers.md | 116 --- .../readme/sub-sections/base/static.md | 117 --- .../src/__tests__/helpers/expectHistory.ts | 22 - .../histories/can-resolve-a-package.json | 3 - .../histories/not-a-match.json | 3 - .../package-resolver/package-resolver.spec.ts | 72 -- .../histories/package-to-wrapper.json | 6 - .../histories/uri-to-uri.json | 6 - .../histories/wrapper-to-wrapper.json | 6 - .../package-to-wrapper.spec.ts | 144 --- .../can-recursively-resolve-uri.json | 6 - .../histories/not-a-match.json | 3 - .../recursive-resolver.spec.ts | 112 --- .../histories/can-redirect-a-uri.json | 3 - .../histories/not-a-match.json | 3 - .../redirect-resolver.spec.ts | 71 -- .../src/__tests__/redirects.spec.ts | 166 ---- .../histories/synchronizer-with-cache.json | 3 - .../synchronizer-with-error-and-cache.json | 3 - ...nchronizer-with-error-without-cache-2.json | 9 - ...nchronizer-with-error-without-cache-3.json | 12 - ...synchronizer-with-error-without-cache.json | 6 - .../histories/synchronizer-without-cache.json | 6 - .../request-synchronizer-resolver.spec.ts | 343 ------- .../histories/error-with-cache.json | 3 - .../histories/error-without-cache.json | 4 - .../histories/package-with-cache.json | 3 - .../histories/package-without-cache.json | 6 - .../histories/uri-with-cache.json | 1 - .../histories/uri-without-cache.json | 6 - .../histories/wrapper-with-cache.json | 3 - .../histories/wrapper-without-cache.json | 4 - .../resolution-result-cache-resolver.spec.ts | 350 ------- .../histories/package-without-cache.json | 6 - .../resolution-path-A-with-cache.json | 3 - .../resolution-path-B-with-cache.json | 3 - .../resolution-path-without-cache.json | 14 - .../resolution-path-wrapper-with-cache.json | 3 - .../histories/uri-without-cache.json | 6 - .../histories/wrapper-with-cache.json | 3 - .../histories/wrapper-without-cache.json | 6 - .../wrapper-cache-resolver.spec.ts | 311 ------ .../histories/can-resolve-a-wrapper.json | 3 - .../histories/not-a-match.json | 3 - .../wrapper-resolver/wrapper-resolver.spec.ts | 82 -- .../src/aggregator/UriResolverAggregator.ts | 112 --- .../aggregator/UriResolverAggregatorBase.ts | 144 --- .../js/uri-resolvers/src/aggregator/index.ts | 2 - .../src/cache/IResolutionResultCache.ts | 17 - .../uri-resolvers/src/cache/IWrapperCache.ts | 12 - .../src/cache/RequestSynchronizerResolver.ts | 166 ---- .../src/cache/ResolutionResultCache.ts | 24 - .../cache/ResolutionResultCacheResolver.ts | 106 --- .../uri-resolvers/src/cache/WrapperCache.ts | 23 - .../src/cache/WrapperCacheResolver.ts | 111 --- packages/js/uri-resolvers/src/cache/index.ts | 7 - .../src/helpers/InfiniteLoopError.ts | 27 - .../src/helpers/RecursiveResolver.ts | 102 -- .../src/helpers/ResolverWithHistory.ts | 76 -- .../src/helpers/ResolverWithLoopGuard.ts | 76 -- .../src/helpers/UriResolutionResult.ts | 78 -- .../uri-resolvers/src/helpers/UriResolver.ts | 79 -- .../src/helpers/UriResolverLike.ts | 20 - .../src/helpers/getUriResolutionPath.ts | 49 - .../js/uri-resolvers/src/helpers/index.ts | 8 - packages/js/uri-resolvers/src/index.ts | 7 - .../src/packages/PackageResolver.ts | 48 - .../src/packages/PackageToWrapperResolver.ts | 100 -- .../js/uri-resolvers/src/packages/index.ts | 2 - .../src/redirects/RedirectResolver.ts | 55 -- .../js/uri-resolvers/src/redirects/index.ts | 1 - .../src/static/StaticResolver.ts | 136 --- .../src/static/StaticResolverLike.ts | 13 - packages/js/uri-resolvers/src/static/index.ts | 2 - .../src/wrappers/WrapperResolver.ts | 48 - .../js/uri-resolvers/src/wrappers/index.ts | 1 - packages/js/uri-resolvers/tsconfig.build.json | 9 - packages/js/uri-resolvers/tsconfig.json | 10 - packages/js/wasm/README.md | 5 - packages/js/wasm/jest.config.js | 12 - packages/js/wasm/package.json | 43 - packages/js/wasm/src/IFileReader.ts | 5 - packages/js/wasm/src/IWasmPackage.ts | 6 - packages/js/wasm/src/InMemoryFileReader.ts | 55 -- packages/js/wasm/src/WasmPackage.ts | 80 -- packages/js/wasm/src/WasmWrapper.ts | 277 ------ .../__tests__/in-memory-file-reader.spec.ts | 129 --- .../src/__tests__/in-memory-packages.spec.ts | 155 --- .../src/__tests__/in-memory-wrappers.spec.ts | 111 --- packages/js/wasm/src/buffer.ts | 70 -- packages/js/wasm/src/constants.ts | 2 - .../js/wasm/src/helpers/createWasmPackage.ts | 48 - .../js/wasm/src/helpers/createWasmWrapper.ts | 59 -- packages/js/wasm/src/imports.ts | 252 ----- packages/js/wasm/src/index.ts | 7 - packages/js/wasm/src/types.ts | 58 -- packages/js/wasm/tsconfig.build.json | 9 - packages/js/wasm/tsconfig.json | 10 - scripts/patch-peer-deps.ts | 26 - 333 files changed, 4 insertions(+), 22238 deletions(-) delete mode 100644 packages/js/asyncify/README.md delete mode 100644 packages/js/asyncify/jest.config.js delete mode 100644 packages/js/asyncify/package.json delete mode 100644 packages/js/asyncify/src/AsyncWasmInstance.ts delete mode 100644 packages/js/asyncify/src/__tests__/AsyncWasmInstance.spec.ts delete mode 100644 packages/js/asyncify/src/__tests__/cases/multipleSleep.ts delete mode 100644 packages/js/asyncify/src/__tests__/cases/simpleSleep.ts delete mode 100644 packages/js/asyncify/src/index.ts delete mode 100644 packages/js/asyncify/src/utils.ts delete mode 100644 packages/js/asyncify/tsconfig.build.json delete mode 100644 packages/js/asyncify/tsconfig.json delete mode 100644 packages/js/client-config-builder/.gitignore delete mode 100644 packages/js/client-config-builder/README.md delete mode 100644 packages/js/client-config-builder/examples/quickstart.ts delete mode 100644 packages/js/client-config-builder/examples/tsconfig.examples.json delete mode 100644 packages/js/client-config-builder/jest.config.js delete mode 100644 packages/js/client-config-builder/package.json delete mode 100644 packages/js/client-config-builder/readme/README.md delete mode 100644 packages/js/client-config-builder/scripts/embed-wrappers.ts delete mode 100644 packages/js/client-config-builder/src/BaseClientConfigBuilder.ts delete mode 100644 packages/js/client-config-builder/src/ClientConfigBuilder.ts delete mode 100644 packages/js/client-config-builder/src/__tests__/client-config-builder.spec.ts delete mode 100644 packages/js/client-config-builder/src/bundles/default.ts delete mode 100644 packages/js/client-config-builder/src/bundles/embeds/async-ipfs-resolver/wrap.info delete mode 100644 packages/js/client-config-builder/src/bundles/embeds/async-ipfs-resolver/wrap.ts delete mode 100644 packages/js/client-config-builder/src/bundles/embeds/async-ipfs-resolver/wrap.wasm delete mode 100644 packages/js/client-config-builder/src/bundles/embeds/ipfs-http-client/wrap.info delete mode 100644 packages/js/client-config-builder/src/bundles/embeds/ipfs-http-client/wrap.ts delete mode 100644 packages/js/client-config-builder/src/bundles/embeds/ipfs-http-client/wrap.wasm delete mode 100644 packages/js/client-config-builder/src/bundles/index.ts delete mode 100644 packages/js/client-config-builder/src/declarations.d.ts delete mode 100644 packages/js/client-config-builder/src/index.ts delete mode 100644 packages/js/client-config-builder/src/types/BuildOptions.ts delete mode 100644 packages/js/client-config-builder/src/types/IClientConfigBuilder.ts delete mode 100644 packages/js/client-config-builder/src/types/configs/BuilderConfig.ts delete mode 100644 packages/js/client-config-builder/src/types/configs/index.ts delete mode 100644 packages/js/client-config-builder/src/types/index.ts delete mode 100644 packages/js/client-config-builder/tsconfig.build.json delete mode 100644 packages/js/client-config-builder/tsconfig.json delete mode 100644 packages/js/client/.gitignore delete mode 100644 packages/js/client/README.md delete mode 100644 packages/js/client/examples/quickstart.ts delete mode 100644 packages/js/client/examples/tsconfig.examples.json delete mode 100644 packages/js/client/jest.config.js delete mode 100644 packages/js/client/package.json delete mode 100644 packages/js/client/readme/README.md delete mode 100644 packages/js/client/src/PolywrapClient.ts delete mode 100644 packages/js/client/src/__tests__/core/embedded-package.spec.ts delete mode 100644 packages/js/client/src/__tests__/core/embedded-wrapper.spec.ts delete mode 100644 packages/js/client/src/__tests__/core/error-structure.spec.ts delete mode 100644 packages/js/client/src/__tests__/core/plugin-wrapper.spec.ts delete mode 100644 packages/js/client/src/__tests__/core/sanity.spec.ts delete mode 100644 packages/js/client/src/__tests__/core/type-test-cases.ts delete mode 100644 packages/js/client/src/__tests__/core/uri-resolution/histories/sanity.json delete mode 100644 packages/js/client/src/__tests__/core/uri-resolution/uri-resolution.spec.ts delete mode 100644 packages/js/client/src/__tests__/core/wasm-wrapper.spec.ts delete mode 100644 packages/js/client/src/__tests__/core/wrap-features/env-case.ts delete mode 100644 packages/js/client/src/__tests__/core/wrap-features/interface-implementation-case.ts delete mode 100644 packages/js/client/src/__tests__/core/wrap-features/subinvoke-case.ts delete mode 100644 packages/js/client/src/__tests__/e2e.spec.ts delete mode 100644 packages/js/client/src/__tests__/helpers.ts delete mode 100644 packages/js/client/src/index.ts delete mode 100644 packages/js/client/src/types/InvokerOptions.ts delete mode 100644 packages/js/client/src/types/TryResolveUriOptions.ts delete mode 100644 packages/js/client/src/types/index.ts delete mode 100644 packages/js/client/tsconfig.build.json delete mode 100644 packages/js/client/tsconfig.json delete mode 100644 packages/js/core-client/.gitignore delete mode 100644 packages/js/core-client/README.md delete mode 100644 packages/js/core-client/examples/quickstart.ts delete mode 100644 packages/js/core-client/examples/tsconfig.examples.json delete mode 100644 packages/js/core-client/jest.config.js delete mode 100644 packages/js/core-client/package.json delete mode 100644 packages/js/core-client/readme/README.md delete mode 100644 packages/js/core-client/src/PolywrapCoreClient.ts delete mode 100644 packages/js/core-client/src/__tests__/embedded-package.spec.ts delete mode 100644 packages/js/core-client/src/__tests__/embedded-wrapper.spec.ts delete mode 100644 packages/js/core-client/src/index.ts delete mode 100644 packages/js/core-client/tsconfig.build.json delete mode 100644 packages/js/core-client/tsconfig.json delete mode 100644 packages/js/core/.eslintignore delete mode 100644 packages/js/core/.gitignore delete mode 100644 packages/js/core/README.md delete mode 100644 packages/js/core/jest.config.js delete mode 100644 packages/js/core/package.json delete mode 100644 packages/js/core/readme/README.md delete mode 100644 packages/js/core/readme/config/final.json delete mode 100644 packages/js/core/readme/config/sub-sections.json delete mode 100644 packages/js/core/readme/sub-sections/base/Uri.md delete mode 100644 packages/js/core/readme/sub-sections/base/UriResolverInterface.md delete mode 100644 packages/js/core/readme/sub-sections/base/uri-resolution.md delete mode 100644 packages/js/core/src/__tests__/MaybeAsync.spec.ts delete mode 100644 packages/js/core/src/__tests__/Uri.spec.ts delete mode 100644 packages/js/core/src/__tests__/get-implementations.spec.ts delete mode 100644 packages/js/core/src/__tests__/is-buffer.spec.ts delete mode 100644 packages/js/core/src/__tests__/typesHandler.spec.ts delete mode 100644 packages/js/core/src/algorithms/applyResolution.ts delete mode 100644 packages/js/core/src/algorithms/clean-uri-history/CleanResolutionStep.ts delete mode 100644 packages/js/core/src/algorithms/clean-uri-history/buildCleanUriHistory.ts delete mode 100644 packages/js/core/src/algorithms/clean-uri-history/index.ts delete mode 100644 packages/js/core/src/algorithms/get-implementations.ts delete mode 100644 packages/js/core/src/algorithms/index.ts delete mode 100644 packages/js/core/src/index.ts delete mode 100644 packages/js/core/src/interfaces/index.ts delete mode 100644 packages/js/core/src/interfaces/uri-resolver.ts delete mode 100644 packages/js/core/src/types/CoreClient.ts delete mode 100644 packages/js/core/src/types/Env.ts delete mode 100644 packages/js/core/src/types/IUriPackage.ts delete mode 100644 packages/js/core/src/types/IUriRedirect.ts delete mode 100644 packages/js/core/src/types/IUriWrapper.ts delete mode 100644 packages/js/core/src/types/IWrapPackage.ts delete mode 100644 packages/js/core/src/types/Invoke.ts delete mode 100644 packages/js/core/src/types/MaybeAsync.ts delete mode 100644 packages/js/core/src/types/Uri.ts delete mode 100644 packages/js/core/src/types/UriMap.ts delete mode 100644 packages/js/core/src/types/UriResolver.ts delete mode 100644 packages/js/core/src/types/WrapError.ts delete mode 100644 packages/js/core/src/types/Wrapper.ts delete mode 100644 packages/js/core/src/types/index.ts delete mode 100644 packages/js/core/src/uri-resolution/IUriResolutionContext.ts delete mode 100644 packages/js/core/src/uri-resolution/IUriResolutionStep.ts delete mode 100644 packages/js/core/src/uri-resolution/IUriResolver.ts delete mode 100644 packages/js/core/src/uri-resolution/UriPackageOrWrapper.ts delete mode 100644 packages/js/core/src/uri-resolution/UriResolutionContext.ts delete mode 100644 packages/js/core/src/uri-resolution/index.ts delete mode 100644 packages/js/core/src/utils/combinePaths.ts delete mode 100644 packages/js/core/src/utils/getEnvFromUriHistory.ts delete mode 100644 packages/js/core/src/utils/index.ts delete mode 100644 packages/js/core/src/utils/is-buffer.ts delete mode 100644 packages/js/core/src/utils/typesHandler.ts delete mode 100644 packages/js/core/tsconfig.build.json delete mode 100644 packages/js/core/tsconfig.json delete mode 100644 packages/js/manifests/wrap/README.md delete mode 100644 packages/js/manifests/wrap/jest.config.js delete mode 100644 packages/js/manifests/wrap/package.json delete mode 100644 packages/js/manifests/wrap/scripts/generate.ts delete mode 100644 packages/js/manifests/wrap/scripts/templates/deserialize-ts.mustache delete mode 100644 packages/js/manifests/wrap/scripts/templates/index-ts.mustache delete mode 100644 packages/js/manifests/wrap/scripts/templates/migrate-ts.mustache delete mode 100644 packages/js/manifests/wrap/scripts/templates/serialize-ts.mustache delete mode 100644 packages/js/manifests/wrap/scripts/templates/validate-ts.mustache delete mode 100644 packages/js/manifests/wrap/src/__tests__/WrapManifest.spec.ts delete mode 100644 packages/js/manifests/wrap/src/compareSignature.ts delete mode 100644 packages/js/manifests/wrap/src/formats/index.ts delete mode 100644 packages/js/manifests/wrap/src/formats/wrap.info/0.1.schema.json delete mode 100644 packages/js/manifests/wrap/src/formats/wrap.info/0.1.ts delete mode 100644 packages/js/manifests/wrap/src/formats/wrap.info/deserialize.ts delete mode 100644 packages/js/manifests/wrap/src/formats/wrap.info/index.ts delete mode 100644 packages/js/manifests/wrap/src/formats/wrap.info/migrate.ts delete mode 100644 packages/js/manifests/wrap/src/formats/wrap.info/serialize.ts delete mode 100644 packages/js/manifests/wrap/src/formats/wrap.info/validate.ts delete mode 100644 packages/js/manifests/wrap/src/index.ts delete mode 100644 packages/js/manifests/wrap/src/types.ts delete mode 100644 packages/js/manifests/wrap/tsconfig.build.json delete mode 100644 packages/js/manifests/wrap/tsconfig.json delete mode 100644 packages/js/msgpack/README.md delete mode 100644 packages/js/msgpack/jest.config.js delete mode 100644 packages/js/msgpack/package.json delete mode 100644 packages/js/msgpack/src/__tests__/msgpack.spec.ts delete mode 100644 packages/js/msgpack/src/index.ts delete mode 100644 packages/js/msgpack/tsconfig.build.json delete mode 100644 packages/js/msgpack/tsconfig.json delete mode 100644 packages/js/plugin/README.md delete mode 100644 packages/js/plugin/jest.config.js delete mode 100644 packages/js/plugin/package.json delete mode 100644 packages/js/plugin/src/PluginFactory.ts delete mode 100644 packages/js/plugin/src/PluginMethod.ts delete mode 100644 packages/js/plugin/src/PluginModule.ts delete mode 100644 packages/js/plugin/src/PluginPackage.ts delete mode 100644 packages/js/plugin/src/PluginWrapper.ts delete mode 100644 packages/js/plugin/src/index.ts delete mode 100644 packages/js/plugin/src/utils/GetPluginMethodsFunc.ts delete mode 100644 packages/js/plugin/src/utils/PluginModuleWithMethods.ts delete mode 100644 packages/js/plugin/src/utils/getErrorSource.ts delete mode 100644 packages/js/plugin/src/utils/index.ts delete mode 100644 packages/js/plugin/tsconfig.build.json delete mode 100644 packages/js/plugin/tsconfig.json delete mode 100644 packages/js/result/README.md delete mode 100644 packages/js/result/package.json delete mode 100644 packages/js/result/src/Result.ts delete mode 100644 packages/js/result/src/ResultErr.ts delete mode 100644 packages/js/result/src/ResultOk.ts delete mode 100644 packages/js/result/src/index.ts delete mode 100644 packages/js/result/tsconfig.build.json delete mode 100644 packages/js/result/tsconfig.json delete mode 100644 packages/js/tracing/README.md delete mode 100644 packages/js/tracing/package.json delete mode 100644 packages/js/tracing/src/index.ts delete mode 100644 packages/js/tracing/tsconfig.build.json delete mode 100644 packages/js/tracing/tsconfig.json delete mode 100644 packages/js/uri-resolver-extensions/.gitignore delete mode 100644 packages/js/uri-resolver-extensions/README.md delete mode 100644 packages/js/uri-resolver-extensions/examples/quickstart.ts delete mode 100644 packages/js/uri-resolver-extensions/examples/tsconfig.examples.json delete mode 100644 packages/js/uri-resolver-extensions/jest.config.js delete mode 100644 packages/js/uri-resolver-extensions/package.json delete mode 100644 packages/js/uri-resolver-extensions/readme/README.md delete mode 100644 packages/js/uri-resolver-extensions/src/ExtendableUriResolver.ts delete mode 100644 packages/js/uri-resolver-extensions/src/ResolverExtensionLoader.ts delete mode 100644 packages/js/uri-resolver-extensions/src/UriResolverExtensionFileReader.ts delete mode 100644 packages/js/uri-resolver-extensions/src/UriResolverWrapper.ts delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/embeds/test-resolver/wrap.info delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/embeds/test-resolver/wrap.ts delete mode 100755 packages/js/uri-resolver-extensions/src/__tests__/embeds/test-resolver/wrap.wasm delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/helpers/expectHistory.ts delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/histories/can-resolve-package.json delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/histories/can-resolve-uri.json delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/histories/not-a-match.json delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/histories/not-found-extension.json delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/histories/shows-plugin-extension-error.json delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/histories/shows-wasm-extension-error.json delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/resolver-extensions.spec.ts delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/.gitignore delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/Cargo.toml delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/polywrap.build.yaml delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/polywrap.graphql delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/polywrap.yaml delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/src/lib.rs delete mode 100644 packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/tsconfig.json delete mode 100644 packages/js/uri-resolver-extensions/src/index.ts delete mode 100644 packages/js/uri-resolver-extensions/tsconfig.build.json delete mode 100644 packages/js/uri-resolver-extensions/tsconfig.json delete mode 100644 packages/js/uri-resolvers/.gitignore delete mode 100644 packages/js/uri-resolvers/README.md delete mode 100644 packages/js/uri-resolvers/examples/quickstart.ts delete mode 100644 packages/js/uri-resolvers/examples/tsconfig.examples.json delete mode 100644 packages/js/uri-resolvers/jest.config.js delete mode 100644 packages/js/uri-resolvers/package.json delete mode 100644 packages/js/uri-resolvers/readme/README.md delete mode 100644 packages/js/uri-resolvers/readme/config/final.json delete mode 100644 packages/js/uri-resolvers/readme/config/sub-sections.json delete mode 100644 packages/js/uri-resolvers/readme/sub-sections/base/aggregator.md delete mode 100644 packages/js/uri-resolvers/readme/sub-sections/base/cache.md delete mode 100644 packages/js/uri-resolvers/readme/sub-sections/base/helpers.md delete mode 100644 packages/js/uri-resolvers/readme/sub-sections/base/static.md delete mode 100644 packages/js/uri-resolvers/src/__tests__/helpers/expectHistory.ts delete mode 100644 packages/js/uri-resolvers/src/__tests__/package-resolver/histories/can-resolve-a-package.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/package-resolver/histories/not-a-match.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/package-resolver/package-resolver.spec.ts delete mode 100644 packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/histories/package-to-wrapper.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/histories/uri-to-uri.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/histories/wrapper-to-wrapper.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/package-to-wrapper.spec.ts delete mode 100644 packages/js/uri-resolvers/src/__tests__/recursive-resolver/histories/can-recursively-resolve-uri.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/recursive-resolver/histories/not-a-match.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/recursive-resolver/recursive-resolver.spec.ts delete mode 100644 packages/js/uri-resolvers/src/__tests__/redirect-resolver/histories/can-redirect-a-uri.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/redirect-resolver/histories/not-a-match.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/redirect-resolver/redirect-resolver.spec.ts delete mode 100644 packages/js/uri-resolvers/src/__tests__/redirects.spec.ts delete mode 100644 packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-and-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-without-cache-2.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-without-cache-3.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-without-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-without-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/request-synchronizer-resolver.spec.ts delete mode 100644 packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/error-with-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/error-without-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/package-with-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/package-without-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/uri-with-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/uri-without-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/wrapper-with-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/wrapper-without-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/resolution-result-cache-resolver.spec.ts delete mode 100644 packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/package-without-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-A-with-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-B-with-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-without-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-wrapper-with-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/uri-without-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/wrapper-with-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/wrapper-without-cache.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/wrapper-cache-resolver.spec.ts delete mode 100644 packages/js/uri-resolvers/src/__tests__/wrapper-resolver/histories/can-resolve-a-wrapper.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/wrapper-resolver/histories/not-a-match.json delete mode 100644 packages/js/uri-resolvers/src/__tests__/wrapper-resolver/wrapper-resolver.spec.ts delete mode 100644 packages/js/uri-resolvers/src/aggregator/UriResolverAggregator.ts delete mode 100644 packages/js/uri-resolvers/src/aggregator/UriResolverAggregatorBase.ts delete mode 100644 packages/js/uri-resolvers/src/aggregator/index.ts delete mode 100644 packages/js/uri-resolvers/src/cache/IResolutionResultCache.ts delete mode 100644 packages/js/uri-resolvers/src/cache/IWrapperCache.ts delete mode 100644 packages/js/uri-resolvers/src/cache/RequestSynchronizerResolver.ts delete mode 100644 packages/js/uri-resolvers/src/cache/ResolutionResultCache.ts delete mode 100644 packages/js/uri-resolvers/src/cache/ResolutionResultCacheResolver.ts delete mode 100644 packages/js/uri-resolvers/src/cache/WrapperCache.ts delete mode 100644 packages/js/uri-resolvers/src/cache/WrapperCacheResolver.ts delete mode 100644 packages/js/uri-resolvers/src/cache/index.ts delete mode 100644 packages/js/uri-resolvers/src/helpers/InfiniteLoopError.ts delete mode 100644 packages/js/uri-resolvers/src/helpers/RecursiveResolver.ts delete mode 100644 packages/js/uri-resolvers/src/helpers/ResolverWithHistory.ts delete mode 100644 packages/js/uri-resolvers/src/helpers/ResolverWithLoopGuard.ts delete mode 100644 packages/js/uri-resolvers/src/helpers/UriResolutionResult.ts delete mode 100644 packages/js/uri-resolvers/src/helpers/UriResolver.ts delete mode 100644 packages/js/uri-resolvers/src/helpers/UriResolverLike.ts delete mode 100644 packages/js/uri-resolvers/src/helpers/getUriResolutionPath.ts delete mode 100644 packages/js/uri-resolvers/src/helpers/index.ts delete mode 100644 packages/js/uri-resolvers/src/index.ts delete mode 100644 packages/js/uri-resolvers/src/packages/PackageResolver.ts delete mode 100644 packages/js/uri-resolvers/src/packages/PackageToWrapperResolver.ts delete mode 100644 packages/js/uri-resolvers/src/packages/index.ts delete mode 100644 packages/js/uri-resolvers/src/redirects/RedirectResolver.ts delete mode 100644 packages/js/uri-resolvers/src/redirects/index.ts delete mode 100644 packages/js/uri-resolvers/src/static/StaticResolver.ts delete mode 100644 packages/js/uri-resolvers/src/static/StaticResolverLike.ts delete mode 100644 packages/js/uri-resolvers/src/static/index.ts delete mode 100644 packages/js/uri-resolvers/src/wrappers/WrapperResolver.ts delete mode 100644 packages/js/uri-resolvers/src/wrappers/index.ts delete mode 100644 packages/js/uri-resolvers/tsconfig.build.json delete mode 100644 packages/js/uri-resolvers/tsconfig.json delete mode 100644 packages/js/wasm/README.md delete mode 100644 packages/js/wasm/jest.config.js delete mode 100644 packages/js/wasm/package.json delete mode 100644 packages/js/wasm/src/IFileReader.ts delete mode 100644 packages/js/wasm/src/IWasmPackage.ts delete mode 100644 packages/js/wasm/src/InMemoryFileReader.ts delete mode 100644 packages/js/wasm/src/WasmPackage.ts delete mode 100644 packages/js/wasm/src/WasmWrapper.ts delete mode 100644 packages/js/wasm/src/__tests__/in-memory-file-reader.spec.ts delete mode 100644 packages/js/wasm/src/__tests__/in-memory-packages.spec.ts delete mode 100644 packages/js/wasm/src/__tests__/in-memory-wrappers.spec.ts delete mode 100644 packages/js/wasm/src/buffer.ts delete mode 100644 packages/js/wasm/src/constants.ts delete mode 100644 packages/js/wasm/src/helpers/createWasmPackage.ts delete mode 100644 packages/js/wasm/src/helpers/createWasmWrapper.ts delete mode 100644 packages/js/wasm/src/imports.ts delete mode 100644 packages/js/wasm/src/index.ts delete mode 100644 packages/js/wasm/src/types.ts delete mode 100644 packages/js/wasm/tsconfig.build.json delete mode 100644 packages/js/wasm/tsconfig.json delete mode 100644 scripts/patch-peer-deps.ts diff --git a/package.json b/package.json index 007709910f..fd39ec5b09 100644 --- a/package.json +++ b/package.json @@ -19,23 +19,18 @@ ] }, "scripts": { - "postinstall": "ts-node ./scripts/patch-peer-deps.ts", "reset": "yarn clean && yarn && yarn build", "clean": "npx rimraf ./**/node_modules ./**/yarn.lock ./**/build ./**/coverage ./**/.polywrap", "install:test-wrappers": "lerna run generate:wrappers --scope @polywrap/test-cases", - "build": "yarn build:core && yarn build:config && yarn build:core:client && yarn build:client && yarn build:cli && yarn install:test-wrappers", - "build:core": "lerna run build --no-private --ignore @polywrap/*-plugin-js --ignore @polywrap/client-config-builder-js --ignore polywrap --ignore @polywrap/core-client-js --ignore @polywrap/client-js --ignore @polywrap/cli-js", - "build:config": "lerna run build --scope @polywrap/client-config-builder-js", - "build:core:client": "lerna run build --scope @polywrap/core-client-js", - "build:client": "lerna run build --scope @polywrap/client-js", + "build": "yarn build:core && yarn build:config && yarn build:cli && yarn install:test-wrappers", + "build:core": "lerna run build --no-private --ignore polywrap --ignore @polywrap/cli-js", "build:cli": "lerna run build --scope polywrap && lerna run build --scope @polywrap/cli-js", "build:docs": "lerna run build:docs", "lint": "lerna run lint", "lint:fix": "lerna run lint -- --fix", "lint:ci": "yarn lint", - "test": "lerna run test --no-private --ignore @polywrap/client-js --concurrency 1 && lerna run test --scope @polywrap/client-js", - "test:core": "lerna run test --no-private --ignore @polywrap/*-plugin-js --ignore polywrap* --ignore @polywrap/client-js --concurrency 1", - "test:client": "lerna run test --no-private --scope @polywrap/client-js --concurrency 1", + "test": "lerna run test --no-private --concurrency 1", + "test:core": "lerna run test --no-private --ignore polywrap* --concurrency 1", "test:cli": "yarn test:cli:unit && yarn test:cli:e2e", "test:cli:unit": "lerna run test:unit --no-private --scope polywrap --concurrency 1", "test:cli:e2e:p1": "lerna run test:e2e:p1 --no-private --scope polywrap --concurrency 1", @@ -65,4 +60,3 @@ "@types/react-dom": "16.9.0" } } - diff --git a/packages/js/asyncify/README.md b/packages/js/asyncify/README.md deleted file mode 100644 index 0830d96f73..0000000000 --- a/packages/js/asyncify/README.md +++ /dev/null @@ -1,29 +0,0 @@ -# @polywrap/asyncify-js - -A 0 dependency wrapper around the Node.JS & Browser `WebAssembly` instance, which adds support for [`asyncify`](https://emscripten.org/docs/porting/asyncify.html), enabling the use of async host import functions. - -## Usage - -```typescript -import { AsyncWasmInstance } from "@polywrap/asyncify-js"; - -// module.wasm must be asyncify enabled -const module: ArrayBuffer = getModule("./module.wasm"); -const memory = new WebAssembly.Memory({ initial: 1 }); - -const instance = await AsyncWasmInstance.createInstance({ - module, - imports: { - my: { - custom_import: async (arg: number): Promise => { - return await someAsyncCall(arg); - } - }, - env: { - memory - } - } -}); - -await instance.exports.main(); -``` diff --git a/packages/js/asyncify/jest.config.js b/packages/js/asyncify/jest.config.js deleted file mode 100644 index a5ca876a5a..0000000000 --- a/packages/js/asyncify/jest.config.js +++ /dev/null @@ -1,11 +0,0 @@ -module.exports = { - collectCoverage: true, - preset: 'ts-jest', - testEnvironment: 'node', - testMatch: ["**/?(*.)+(spec|test).[jt]s?(x)"], - globals: { - 'ts-jest': { - diagnostics: false - } - } -}; diff --git a/packages/js/asyncify/package.json b/packages/js/asyncify/package.json deleted file mode 100644 index 1b11714975..0000000000 --- a/packages/js/asyncify/package.json +++ /dev/null @@ -1,35 +0,0 @@ -{ - "name": "@polywrap/asyncify-js", - "description": "Async Wasm Imports Support Using Asyncify", - "version": "0.10.0", - "license": "MIT", - "repository": { - "type": "git", - "url": "https://github.com/polywrap/monorepo.git" - }, - "main": "build/index.js", - "files": [ - "build" - ], - "scripts": { - "build": "rimraf ./build && tsc --project tsconfig.build.json", - "lint": "eslint --color -c ../../../.eslintrc.js --ignore-pattern src/__tests__/cases/* src/", - "test": "jest --passWithNoTests --runInBand --verbose", - "test:watch": "yarn test -- --watch" - }, - "devDependencies": { - "@types/jest": "26.0.8", - "@types/prettier": "2.6.0", - "assemblyscript": "0.19.23", - "jest": "26.6.3", - "rimraf": "3.0.2", - "ts-jest": "26.5.4", - "ts-loader": "8.0.17", - "ts-node": "10.9.1", - "typescript": "4.9.5" - }, - "gitHead": "7346adaf5adb7e6bbb70d9247583e995650d390a", - "publishConfig": { - "access": "public" - } -} diff --git a/packages/js/asyncify/src/AsyncWasmInstance.ts b/packages/js/asyncify/src/AsyncWasmInstance.ts deleted file mode 100644 index 7d800bc329..0000000000 --- a/packages/js/asyncify/src/AsyncWasmInstance.ts +++ /dev/null @@ -1,258 +0,0 @@ -/* eslint-disable @typescript-eslint/naming-convention */ -/* eslint-disable @typescript-eslint/ban-types */ -/* eslint-disable @typescript-eslint/no-empty-function */ -import { indexOfArray, isPromise, proxyGet } from "./utils"; - -type WasmMemory = WebAssembly.Memory; -type WasmExports = WebAssembly.Exports; -type WasmImports = WebAssembly.Imports; -type WasmModuleImports = WebAssembly.ModuleImports; -type WasmImportValue = WebAssembly.ImportValue; -type WasmInstance = WebAssembly.Instance; - -interface AsyncifyExports extends WebAssembly.Exports { - asyncify_start_unwind: (dataAddr: number) => void; - asyncify_stop_unwind: () => void; - asyncify_start_rewind: (dataAddr: number) => void; - asyncify_stop_rewind: () => void; - asyncify_get_state: () => number; -} - -enum AsyncifyState { - None = 0, - Unwinding = 1, - Rewinding = 2, -} - -export class AsyncWasmInstance { - public static requiredExports: readonly string[] = [ - "asyncify_start_unwind", - "asyncify_stop_unwind", - "asyncify_start_rewind", - "asyncify_stop_rewind", - "asyncify_get_state", - ]; - - private static _dataAddr = 16; - private static _dataStart = AsyncWasmInstance._dataAddr + 8; - private static _dataEnd = 1024; - - private _instance: WasmInstance; - private _wrappedImports: WasmImports; - private _wrappedExports: AsyncifyExports; - private _importFnResult: Promise | unknown; - - private constructor() {} - - public static createMemory(config: { module: Uint8Array }): WasmMemory { - // extract the initial memory page size, as it will - // throw an error if the imported page size differs: - // https://chromium.googlesource.com/v8/v8/+/644556e6ed0e6e4fac2dfabb441439820ec59813/src/wasm/module-instantiate.cc#924 - const envMemoryImportSignature = Uint8Array.from([ - // env ; import module name - 0x65, - 0x6e, - 0x76, - // string length - 0x06, - // memory ; import field name - 0x6d, - 0x65, - 0x6d, - 0x6f, - 0x72, - 0x79, - // import kind - 0x02, - // limits ; https://github.com/sunfishcode/wasm-reference-manual/blob/master/WebAssembly.md#resizable-limits - // limits ; flags - // 0x??, - // limits ; initial - // 0x__, - ]); - - const sigIdx = indexOfArray(config.module, envMemoryImportSignature); - - if (sigIdx < 0) { - throw Error( - `Unable to find Wasm memory import section. ` + - `Modules must import memory from the "env" module's ` + - `"memory" field like so:\n` + - `(import "env" "memory" (memory (;0;) #))` - ); - } - - // Extract the initial memory page-range size - const memoryInitalLimits = - config.module[sigIdx + envMemoryImportSignature.length + 1]; - - if (memoryInitalLimits === undefined) { - throw Error( - "No initial memory number found, this should never happen..." - ); - } - - return new WebAssembly.Memory({ initial: memoryInitalLimits }); - } - - public static async createInstance(config: { - module: Uint8Array; - imports: WasmImports; - requiredExports?: readonly string[]; - }): Promise { - const instance = new AsyncWasmInstance(); - // Wrap imports - instance._wrappedImports = instance._wrapImports(config.imports); - - // Create Wasm module instance - instance._instance = ( - await WebAssembly.instantiate(config.module, instance._wrappedImports) - ).instance; - - // Ensure all required exports exist on Wasm module - const exportKeys = Object.keys(instance._instance.exports); - const missingExports = [ - ...AsyncWasmInstance.requiredExports, - ...(config.requiredExports || []), - ].filter((name) => !exportKeys.includes(name)); - - if (missingExports.length) { - throw new Error( - `Required Wasm exports were not found: ${missingExports.join(", ")}` - ); - } - - const exports = instance._instance.exports as AsyncifyExports; - - // Wrap exports - instance._wrappedExports = instance._wrapExports(exports); - - // Initialize Asyncify stack pointers - const memory = (exports.memory || - (config.imports.env && config.imports.env.memory)) as WasmMemory; - - new Int32Array(memory.buffer, AsyncWasmInstance._dataAddr).set([ - AsyncWasmInstance._dataStart, - AsyncWasmInstance._dataEnd, - ]); - return instance; - } - - get exports(): WasmExports { - return this._wrappedExports; - } - - private _getAsyncifyState(): AsyncifyState { - return this._wrappedExports.asyncify_get_state(); - } - - private _assertNoneState(): void { - const state = this._getAsyncifyState(); - if (state !== AsyncifyState.None) { - throw new Error(`Invalid asyncify state ${state}, expected 0.`); - } - } - - private _wrapImports(imports: WasmImports): WasmImports { - return proxyGet( - imports, - (moduleImports: WasmModuleImports | undefined, name: string) => { - if (moduleImports === undefined) { - throw Error( - `Unsupported wasm import namespace requested: "${name}"; ` + - `Supported wasm import namespaces: ${Object.keys(imports) - .map((x) => `"${x}"`) - .join(", ")}` - ); - } - return this._wrapModuleImports(moduleImports); - } - ); - } - - private _wrapModuleImports(imports: WasmModuleImports) { - return proxyGet( - imports, - (importValue: WasmImportValue | undefined, name: string) => { - if (importValue === undefined) { - throw Error( - `Unsupported wasm import requested: "${name}"; ` + - `Supported wasm imports: ${Object.keys(imports) - .map((x) => `"${x}"`) - .join(", ")}` - ); - } - if (typeof importValue === "function") { - return this._wrapImportFn(importValue); - } - return importValue; - } - ); - } - - private _wrapImportFn(importFn: Function) { - return (...args: unknown[]) => { - if (this._getAsyncifyState() === AsyncifyState.Rewinding) { - this._wrappedExports.asyncify_stop_rewind(); - return this._importFnResult; - } - this._assertNoneState(); - const value = importFn(...args); - if (!isPromise(value)) { - return value; - } - this._wrappedExports.asyncify_start_unwind(AsyncWasmInstance._dataAddr); - this._importFnResult = value; - }; - } - - private _wrapExports(exports: AsyncifyExports): AsyncifyExports { - const newExports = Object.create(null); - - for (const exportName in exports) { - let value = exports[exportName]; - if (typeof value === "function" && !exportName.startsWith("asyncify_")) { - value = this._wrapExportFn(value); - } - Object.defineProperty(newExports, exportName, { - enumerable: true, - value, - }); - } - - return newExports; - } - - private _wrapExportFn(exportFn: Function) { - return async (...args: unknown[]) => { - this._assertNoneState(); - - let result = exportFn(...args); - - while (this._getAsyncifyState() === AsyncifyState.Unwinding) { - try { - this._wrappedExports.asyncify_stop_unwind(); - this._importFnResult = await this._importFnResult; - this._assertNoneState(); - this._wrappedExports.asyncify_start_rewind( - AsyncWasmInstance._dataAddr - ); - result = exportFn(); - } catch (e) { - const msg = e.toString(); - if (msg.indexOf("RuntimeError: unreachable") > -1) { - throw new Error( - `${msg}. "unreachable" may be due to ASYNCIFY_STACK_SIZE not being large enough (try increasing it),` + - ` or the wasm module being too large (try optimizing it).` - ); - } - throw e; - } - } - - this._assertNoneState(); - - return result; - }; - } -} diff --git a/packages/js/asyncify/src/__tests__/AsyncWasmInstance.spec.ts b/packages/js/asyncify/src/__tests__/AsyncWasmInstance.spec.ts deleted file mode 100644 index 698e67d9b7..0000000000 --- a/packages/js/asyncify/src/__tests__/AsyncWasmInstance.spec.ts +++ /dev/null @@ -1,276 +0,0 @@ -import { AsyncWasmInstance } from ".."; -import asc from "assemblyscript/cli/asc"; -import fs from "fs"; -import path from "path"; - -jest.setTimeout(60000); - -const compileWasm = (filename: string) => - new Promise((resolve, reject) => { - asc.main( - [ - filename, - "--baseDir", - path.join(__dirname, "cases"), - "--binaryFile", - `./build/${filename.split(".")[0]}.wasm`, - "--measure", - "--runtime", - "stub", // Please use "incremental" if you need GC - "-O3", // Please use "-O3z" if you need optimize for size - "--importMemory", - "--runPasses", - "asyncify", - ], - {}, - (err) => { - if (err) { - reject(err); - return 0; - } else { - resolve(); - return 1; - } - } - ); - }); - -const casesFiles = fs - .readdirSync(path.join(__dirname, "./cases")) - .filter((caseFile) => caseFile.endsWith(".ts")); - -const getModule = async (name: string) => { - const wasmPath = path.join(__dirname, "cases", "build", `${name}.wasm`); - const buffer = fs.readFileSync(wasmPath); - const bytes = new Uint8Array(buffer).buffer; - return bytes; -}; - -describe("AsyncWasmInstance", () => { - beforeAll(async () => { - const buildDir = path.join(__dirname, "cases", "build"); - - if (!fs.existsSync(buildDir)) { - fs.mkdirSync(buildDir); - } - - const files = fs.readdirSync(buildDir); - - for (const file of files) { - fs.unlinkSync(path.join(buildDir, file)); - } - - await Promise.all( - casesFiles.map(async (file) => { - await compileWasm(file); - }) - ); - }); - - it("Short sleep", async () => { - const module = await getModule("simpleSleep"); - const memory = new WebAssembly.Memory({ initial: 1 }); - const logs: number[] = []; - const instance = await AsyncWasmInstance.createInstance({ - module, - imports: { - wrap: { - log: (x: number) => { - logs.push(x); - }, - asyncFunc: () => { - const promise = new Promise((resolve) => { - setTimeout(() => { - logs.push(-2); - resolve(); - }, 5000); - }); - - logs.push(-1); - - return promise; - }, - } as any, - env: { - memory, - }, - }, - }); - - await (instance.exports.main as () => void)(); - - expect(logs).toEqual([0, -1, -2, 1]); - }); - - it("Long sleep", async () => { - const module = await getModule("simpleSleep"); - const memory = new WebAssembly.Memory({ initial: 1 }); - const logs: number[] = []; - const instance = await AsyncWasmInstance.createInstance({ - module, - imports: { - wrap: { - log: (x: number) => { - logs.push(x); - }, - asyncFunc: () => { - const promise = new Promise((resolve) => { - setTimeout(() => { - logs.push(-2); - resolve(); - }, 40000); - }); - - logs.push(-1); - - return promise; - }, - } as any, - env: { - memory, - }, - }, - }); - - await (instance.exports.main as () => void)(); - - expect(logs).toEqual([0, -1, -2, 1]); - }); - - it("Multiple contiguous async calls", async () => { - const module = await getModule("multipleSleep"); - const memory = new WebAssembly.Memory({ initial: 1 }); - const logs: number[] = []; - const instance = await AsyncWasmInstance.createInstance({ - module, - imports: { - wrap: { - log: (x: number) => { - logs.push(x); - }, - asyncFunc: (ms: number) => - new Promise((resolve) => { - setTimeout(() => { - logs.push(-1); - resolve(); - }, ms); - }), - } as any, - env: { - memory, - }, - }, - }); - - await (instance.exports.main as () => void)(); - - expect(logs).toEqual([0, -1, 1, -1, 2, -1, -1, 3]); - }); - - it("Multiple nested async calls in import", async () => { - const module = await getModule("simpleSleep"); - const memory = new WebAssembly.Memory({ initial: 1 }); - const logs: number[] = []; - - const sleep = async (ms: number, log: number) => - new Promise((resolve) => { - setTimeout(() => { - logs.push(log); - resolve(); - }, ms); - }); - - const instance = await AsyncWasmInstance.createInstance({ - module, - imports: { - wrap: { - log: (x: number) => { - logs.push(x); - }, - asyncFunc: () => { - return new Promise(async (outerRes) => { - await sleep(3000, -1); - - await new Promise(async (innerRes) => { - await sleep(2000, -2); - - await new Promise(async (innerMostRes) => { - await sleep(1000, -3); - innerMostRes(); - }); - - logs.push(-4); - - innerRes(); - }); - - logs.push(-5); - - outerRes(); - }); - }, - } as any, - env: { - memory, - }, - }, - }); - - await (instance.exports.main as () => void)(); - - expect(logs).toEqual([0, -1, -2, -3, -4, -5, 1]); - }); - - it("Large callstack", async () => { - const logs: number[] = []; - const module = await getModule("simpleSleep"); - const memory = new WebAssembly.Memory({ initial: 1 }); - const depthSize = 1000; - - const sleep = (ms = 500) => - new Promise((resolve) => { - setTimeout(() => { - resolve(); - }, ms); - }); - - const asyncFunction = (parentResolve: any, counter = 0) => { - return new Promise(async (res) => { - await sleep(10); - - if(counter < depthSize) { - logs.push((counter + 1) * -1); - await asyncFunction(res, counter + 1) - } - - parentResolve() - }) - }; - - const instance = await AsyncWasmInstance.createInstance({ - module, - imports: { - wrap: { - log: (x: number) => { - logs.push(x); - }, - asyncFunc: () => { - return new Promise((res) => { - asyncFunction(res) - }) - }, - } as any, - env: { - memory, - }, - }, - }); - - await (instance.exports.main as () => void)(); - - const expectedArray = [...Array.from(Array(depthSize).keys()).map(i => i * -1), -depthSize, 1] - expectedArray[0] = 0 - - expect(logs).toEqual(expectedArray) - }); -}); diff --git a/packages/js/asyncify/src/__tests__/cases/multipleSleep.ts b/packages/js/asyncify/src/__tests__/cases/multipleSleep.ts deleted file mode 100644 index 469799b462..0000000000 --- a/packages/js/asyncify/src/__tests__/cases/multipleSleep.ts +++ /dev/null @@ -1,16 +0,0 @@ -@external("wrap", "asyncFunc") -declare function asyncFunc(ms: number): void; - -@external("wrap", "log") -declare function log(value: number): void; - -export function main(): void { - log(0) - asyncFunc(4000); - log(1) - asyncFunc(2000); - log(2) - asyncFunc(1000); - asyncFunc(1000); - log(3) -} diff --git a/packages/js/asyncify/src/__tests__/cases/simpleSleep.ts b/packages/js/asyncify/src/__tests__/cases/simpleSleep.ts deleted file mode 100644 index 3935cfe0ae..0000000000 --- a/packages/js/asyncify/src/__tests__/cases/simpleSleep.ts +++ /dev/null @@ -1,11 +0,0 @@ -@external("wrap", "asyncFunc") -declare function asyncFunc(): void; - -@external("wrap", "log") -declare function log(value: number): void; - -export function main(): void { - log(0) - asyncFunc(); - log(1) -} diff --git a/packages/js/asyncify/src/index.ts b/packages/js/asyncify/src/index.ts deleted file mode 100644 index 2c49f2f4a7..0000000000 --- a/packages/js/asyncify/src/index.ts +++ /dev/null @@ -1 +0,0 @@ -export * from "./AsyncWasmInstance"; diff --git a/packages/js/asyncify/src/utils.ts b/packages/js/asyncify/src/utils.ts deleted file mode 100644 index 01b2d6175e..0000000000 --- a/packages/js/asyncify/src/utils.ts +++ /dev/null @@ -1,53 +0,0 @@ -export type MaybeAsync = Promise | T; - -export function isPromise( - test?: MaybeAsync -): test is Promise { - return !!test && typeof (test as Promise).then === "function"; -} - -export function proxyGet>( - obj: T, - transform: (value: unknown, name: string) => unknown -): T { - return new Proxy(obj, { - get: (obj: T, name: string) => { - return transform(obj[name], name); - }, - }); -} - -export function indexOfArray(source: Uint8Array, search: Uint8Array): number { - let run = true; - let start = 0; - - while (run) { - const idx = source.indexOf(search[0], start); - - // not found - if (idx < start) { - run = false; - continue; - } - - // Make sure the rest of the subarray contains the search pattern - const subBuff = source.subarray(idx, idx + search.length); - - let retry = false; - let i = 1; - for (; i < search.length && !retry; ++i) { - if (subBuff[i] !== search[i]) { - retry = true; - } - } - - if (retry) { - start = idx + i; - continue; - } else { - return idx; - } - } - - return -1; -} diff --git a/packages/js/asyncify/tsconfig.build.json b/packages/js/asyncify/tsconfig.build.json deleted file mode 100644 index 77aadfdd2f..0000000000 --- a/packages/js/asyncify/tsconfig.build.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "extends": "./tsconfig.json", - "include": [ - "./src/**/*.ts" - ], - "exclude": [ - "./src/**/__tests__" - ] -} diff --git a/packages/js/asyncify/tsconfig.json b/packages/js/asyncify/tsconfig.json deleted file mode 100644 index 920efc3c9d..0000000000 --- a/packages/js/asyncify/tsconfig.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "extends": "../../../tsconfig", - "compilerOptions": { - "lib": [ - "es2020", - "es2015", - "es5", - "dom" - ], - "outDir": "build" - }, - "include": [ - "./src/**/*.ts" - ], - "exclude": [ - "./src/__tests__/cases/*.ts" - ] -} diff --git a/packages/js/client-config-builder/.gitignore b/packages/js/client-config-builder/.gitignore deleted file mode 100644 index dbb01bb64d..0000000000 --- a/packages/js/client-config-builder/.gitignore +++ /dev/null @@ -1,3 +0,0 @@ -/examples/**/*.d.ts -/examples/**/*.js -/examples/**/*.js.map diff --git a/packages/js/client-config-builder/README.md b/packages/js/client-config-builder/README.md deleted file mode 100644 index b1cc6cb955..0000000000 --- a/packages/js/client-config-builder/README.md +++ /dev/null @@ -1,610 +0,0 @@ -# PolywrapClient Config Builder - -A utility class for building the PolywrapClient config. - -Supports building configs using method chaining or imperatively. - -## Quickstart - -### Initialize - -Initialize a ClientConfigBuilder using the [constructor](#constructor) - -```typescript - // start with a blank slate (typical usage) - const builder = new ClientConfigBuilder(); -``` - -### Configure - -Add client configuration with [add](#add), or flexibly mix and match builder [configuration methods](#addwrapper) to add and remove configuration items. - -```typescript - // add multiple items to the configuration using the catch-all `add` method - builder.add({ - envs: {}, - interfaces: {}, - redirects: {}, - wrappers: {}, - packages: {}, - resolvers: [], - }); - - // add or remove items by chaining method calls - builder - .addPackage("wrap://plugin/package", httpPlugin({})) - .removePackage("wrap://plugin/package") - .addPackages({ - "wrap://plugin/http": httpPlugin({}), - "wrap://plugin/filesystem": fileSystemPlugin({}), - }); -``` - -You can add the entire [default client configuration bundle](#bundle--defaultconfig) at once with [addDefaults](#adddefaults) - -```typescript - builder.addDefaults(); -``` - -### Build - -Finally, build a ClientConfig or CoreClientConfig to pass to the PolywrapClient constructor. - -```typescript - // accepted by either the PolywrapClient or the PolywrapCoreClient - let coreClientConfig = builder.build(); - - // build with a custom cache - coreClientConfig = builder.build({ - resolutionResultCache: new ResolutionResultCache(), - }); - - // or build with a custom resolver - coreClientConfig = builder.build({ - resolver: RecursiveResolver.from([]), - }); -``` - -### Example - -A complete example using all or most of the available methods. - -```typescript= - // init - const builder = new ClientConfigBuilder(); - - // add the default bundle first to override its entries later - builder.addDefaults(); - - // add many config items at once - builder.add({ - envs: {}, - interfaces: {}, - redirects: {}, - wrappers: {}, - packages: {}, - resolvers: [], - }); - - // add and remove wrappers - builder - .addWrapper( - "wrap://ens/wrapper.eth", - await WasmWrapper.from( - new Uint8Array([1, 2, 3]), - new Uint8Array([1, 2, 3]) - ) - ) - .removeWrapper("wrap://ens/wrapper.eth") - .addWrappers({ - "wrap://ens/wrapper.eth": await WasmWrapper.from( - new Uint8Array([1, 2, 3]), - new Uint8Array([1, 2, 3]) - ), - }); - - // add and remove wrap packages - builder - .addPackage("wrap://plugin/package", httpPlugin({})) - .removePackage("wrap://plugin/package") - .addPackages({ - "wrap://plugin/package": httpPlugin({}), - }); - - // add and remove Envs - builder - .addEnv("wrap://ens/wrapper.eth", { key: "value" }) - .removeEnv("wrap://ens/wrapper.eth") - .addEnvs({ - "wrap://ens/wrapper.eth": { key: "value" }, - }); - - // override existing Env, or add new Env if one is not registered at URI - builder.setEnv("wrap://ens/wrapper.eth", { key: "value" }); - - // add or remove registration for an implementation of an interface - builder - .addInterfaceImplementation( - "wrap://ens/interface.eth", - "wrap://ens/wrapper.eth" - ) - .removeInterfaceImplementation( - "wrap://ens/interface.eth", - "wrap://ens/wrapper.eth" - ) - .addInterfaceImplementations("wrap://ens/interface.eth", [ - "wrap://ens/wrapper.eth", - ]); - - // add or remove URI redirects - builder - .addRedirect("wrap://ens/from.eth", "wrap://ens/to.eth") - .removeRedirect("wrap://ens/from.eth") - .addRedirects({ - "wrap://ens/from.eth": "wrap://ens/to.eth", - }); - - // add resolvers - builder.addResolver(RecursiveResolver.from([])); - builder.addResolvers([]); - - // build - const clientConfig = builder.build(); -``` - -# Reference - -## ClientConfigBuilder - -### Constructor -```ts - /** - * Instantiate a ClientConfigBuilder - */ - constructor() -``` - -### add -```ts - /** - * Add a partial BuilderConfig - * This is equivalent to calling each of the plural add functions: `addEnvs`, `addWrappers`, etc. - * - * @param config: a partial BuilderConfig - * @returns IClientConfigBuilder (mutated self) - */ - add(config: Partial): IClientConfigBuilder; -``` - -### addWrapper -```ts - /** - * Add an embedded wrapper - * - * @param uri: uri of wrapper - * @param wrapper: wrapper to be added - * @returns IClientConfigBuilder (mutated self) - */ - addWrapper(uri: string, wrapper: Wrapper): IClientConfigBuilder; -``` - -### addWrappers -```ts - /** - * Add one or more embedded wrappers. - * This is equivalent to calling addWrapper for each wrapper. - * - * @param uriWrappers: an object where keys are uris and wrappers are value - * @returns IClientConfigBuilder (mutated self) - */ - addWrappers(uriWrappers: Record): IClientConfigBuilder; -``` - -### removeWrapper -```ts - /** - * Remove an embedded wrapper - * - * @param uri: the wrapper's URI - * @returns IClientConfigBuilder (mutated self) - */ - removeWrapper(uri: string): IClientConfigBuilder; -``` - -### addPackage -```ts - /** - * Add an embedded wrap package - * - * @param uri: uri of wrapper - * @param wrapPackage: package to be added - * @returns IClientConfigBuilder (mutated self) - */ - addPackage(uri: string, wrapPackage: IWrapPackage): IClientConfigBuilder; -``` - -### addPackages -```ts - /** - * Add one or more embedded wrap packages - * This is equivalent to calling addPackage for each package - * - * @param uriPackages: an object where keys are uris and packages are value - * @returns IClientConfigBuilder (mutated self) - */ - addPackages(uriPackages: Record): IClientConfigBuilder; -``` - -### removePackage -```ts - /** - * Remove an embedded wrap package - * - * @param uri: the package's URI - * @returns IClientConfigBuilder (mutated self) - */ - removePackage(uri: string): IClientConfigBuilder; -``` - -### addEnv -```ts - /** - * Add an Env. - * If an Env is already associated with the uri, it is modified. - * - * @param uri: the wrapper's URI to associate with the Env - * @param env: an object with the env variables for the uri - * @returns IClientConfigBuilder (mutated self) - */ - addEnv(uri: string, env: Record): IClientConfigBuilder; -``` - -### addEnvs -```ts - /** - * Add one or more Envs - * This is equivalent to calling addEnv for each Env - * - * @param uriEnvs: and object where key is the uri and value is the another object with the env variables for the uri - * @returns IClientConfigBuilder (mutated self) - */ - addEnvs( - uriEnvs: Record> - ): IClientConfigBuilder; -``` - -### removeEnv -```ts - /** - * Remove an Env - * - * @param uri: the URI associated with the Env - * @returns IClientConfigBuilder (mutated self) - */ - removeEnv(uri: string): IClientConfigBuilder; -``` - -### setEnv -```ts - /** - * Add an Env. - * If an Env is already associated with the uri, it is replaced. - * - * @param uri: the wrapper's URI to associate with the Env - * @param env: an object with the environment variables for the uri - * @returns IClientConfigBuilder (mutated self) - */ - setEnv(uri: string, env: Record): IClientConfigBuilder; -``` - -### addInterfaceImplementation -```ts - /** - * Register an implementation of a single interface - * - * @param interfaceUri: the URI of the interface - * @param implementationUri: the URI of the implementation - * @returns IClientConfigBuilder (mutated self) - */ - addInterfaceImplementation( - interfaceUri: string, - implementationUri: string - ): IClientConfigBuilder; -``` - -### addInterfaceImplementations -```ts - /** - * Register one or more implementation of a single interface - * - * @param interfaceUri: the URI of the interface - * @param implementationUris: a list of URIs for the implementations - * @returns IClientConfigBuilder (mutated self) - */ - addInterfaceImplementations( - interfaceUri: string, - implementationUris: Array - ): IClientConfigBuilder; -``` - -### removeInterfaceImplementation -```ts - /** - * Remove an implementation of a single interface - * - * @param interfaceUri: the URI of the interface - * @param implementationUri: the URI of the implementation - * @returns IClientConfigBuilder (mutated self) - */ - removeInterfaceImplementation( - interfaceUri: string, - implementationUri: string - ): IClientConfigBuilder; -``` - -### addRedirect -```ts - /** - * Add a redirect from one URI to another - * - * @param from: the URI to redirect from - * @param to: the URI to redirect to - * @returns IClientConfigBuilder (mutated self) - */ - addRedirect(from: string, to: string): IClientConfigBuilder; -``` - -### addRedirects -```ts - /** - * Add an array of URI redirects - * - * @param redirects: an object where key is from and value is to - * @returns IClientConfigBuilder (mutated self) - */ - addRedirects(redirects: Record): IClientConfigBuilder; -``` - -### removeRedirect -```ts - /** - * Remove a URI redirect - * - * @param from: the URI that is being redirected - * @returns IClientConfigBuilder (mutated self) - */ - removeRedirect(from: string): IClientConfigBuilder; -``` - -### addResolver -```ts - /** - * Add a URI Resolver, capable of resolving a URI to a wrapper - * - * @remarks - * A UriResolverLike can be any one of: - * IUriResolver - * | IUriRedirect - * | IUriPackage - * | IUriWrapper - * | UriResolverLike[]; - * - * @param resolver: A UriResolverLike - * @returns IClientConfigBuilder (mutated self) - */ - addResolver(resolver: UriResolverLike): IClientConfigBuilder; -``` - -### addResolvers -```ts - /** - * Add one or more URI Resolvers, capable of resolving URIs to wrappers - * - * @remarks - * A UriResolverLike can be any one of: - * IUriResolver - * | IUriRedirect - * | IUriPackage - * | IUriWrapper - * | UriResolverLike[]; - * - * @param resolvers: A list of UriResolverLike - * @returns IClientConfigBuilder (mutated self) - */ - addResolvers(resolvers: UriResolverLike[]): IClientConfigBuilder; -``` - -### addDefaults -```ts - /** - * Add the default configuration bundle - * - * @returns IClientConfigBuilder (mutated self) - */ - addDefaults(): IClientConfigBuilder; -``` - -### build -```ts - /** - * Build a sanitized core client configuration that can be passed to the PolywrapClient or PolywrapCoreClient constructors - * - * @param options - Use a custom wrapper cache or resolver - * @returns CoreClientConfig that results from applying all the steps in the builder pipeline - */ - build(options?: BuildOptions): CoreClientConfig; -``` - -## Bundles - -### Bundle: DefaultConfig -```ts -export const ipfsProviders: string[] = [ - "https://ipfs.wrappers.io", - "https://ipfs.io", -]; - -interface IDefaultEmbed { - uri: Uri; - package: IWrapPackage; - source: Uri; -} - -interface IDefaultEmbeds { - ipfsHttpClient: IDefaultEmbed; - ipfsResolver: IDefaultEmbed; -} - -export const embeds: IDefaultEmbeds = { - ipfsHttpClient: { - uri: Uri.from("embed/ipfs-http-client@1.0.0"), - package: ipfsHttpClient.wasmPackage, - source: Uri.from("ens/wraps.eth:ipfs-http-client@1.0.0"), - }, - ipfsResolver: { - uri: Uri.from("embed/async-ipfs-uri-resolver-ext@1.0.1"), - package: ipfsResolver.wasmPackage, - source: Uri.from("ens/wraps.eth:async-ipfs-uri-resolver-ext@1.0.1"), - }, -}; - -type UriResolverExtBootloader = [IDefaultEmbed, IUriRedirect, ...Uri[]]; - -export const uriResolverExts: UriResolverExtBootloader = [ - embeds.ipfsResolver, - { - from: Uri.from("ens/wraps.eth:ens-text-record-uri-resolver-ext@1.0.1"), - to: Uri.from("ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs"), - }, - Uri.from("ens/wraps.eth:http-uri-resolver-ext@1.0.1"), - Uri.from("ens/wraps.eth:file-system-uri-resolver-ext@1.0.1"), - Uri.from("ens/wraps.eth:ens-uri-resolver-ext@1.0.1"), - Uri.from("ens/wraps.eth:ens-ipfs-contenthash-uri-resolver-ext@1.0.1"), -]; - -interface IDefaultPlugin { - uri: Uri; - plugin: IWrapPackage; - implements: Uri[]; -} - -interface IDefaultPlugins { - logger: IDefaultPlugin; - http: IDefaultPlugin; - fileSystem: IDefaultPlugin; - concurrent: IDefaultPlugin; - ethereumProviderV1: IDefaultPlugin; - ethereumProviderV2: IDefaultPlugin; -} - -export const plugins: IDefaultPlugins = { - logger: { - uri: Uri.from("plugin/logger@1.0.0"), - plugin: loggerPlugin({}), - implements: [Uri.from("ens/wraps.eth:logger@1.0.0")], - }, - http: { - uri: Uri.from("plugin/http@1.1.0"), - plugin: httpPlugin({}), - implements: [ - Uri.from("ens/wraps.eth:http@1.1.0"), - Uri.from("ens/wraps.eth:http@1.0.0"), - ], - }, - fileSystem: { - uri: Uri.from("plugin/file-system@1.0.0"), - plugin: fileSystemPlugin({}), - implements: [Uri.from("ens/wraps.eth:file-system@1.0.0")], - }, - concurrent: { - uri: Uri.from("plugin/concurrent@1.0.0"), - plugin: concurrentPromisePlugin({}), - implements: [Uri.from("ens/wraps.eth:concurrent@1.0.0")], - }, - ethereumProviderV1: { - uri: Uri.from("plugin/ethereum-provider@1.1.0"), - plugin: EthProviderV1.plugin({ - connections: new EthProviderV1.Connections({ - networks: { - mainnet: new EthProviderV1.Connection({ - provider: - "https://mainnet.infura.io/v3/b00b2c2cc09c487685e9fb061256d6a6", - }), - goerli: new EthProviderV1.Connection({ - provider: - "https://goerli.infura.io/v3/b00b2c2cc09c487685e9fb061256d6a6", - }), - }, - }), - }), - implements: [ - Uri.from("ens/wraps.eth:ethereum-provider@1.1.0"), - Uri.from("ens/wraps.eth:ethereum-provider@1.0.0"), - ], - }, - ethereumProviderV2: { - uri: Uri.from("plugin/ethereum-provider@2.0.0"), - plugin: EthProvider.plugin({ - connections: new EthProvider.Connections({ - networks: { - mainnet: new EthProvider.Connection({ - provider: - "https://mainnet.infura.io/v3/b00b2c2cc09c487685e9fb061256d6a6", - }), - goerli: new EthProvider.Connection({ - provider: - "https://goerli.infura.io/v3/b00b2c2cc09c487685e9fb061256d6a6", - }), - }, - }), - }), - implements: [Uri.from("ens/wraps.eth:ethereum-provider@2.0.0")], - }, -}; - -export function getConfig(): BuilderConfig { - const builder = new ClientConfigBuilder(); - - // Add all embedded packages - for (const embed of Object.values(embeds)) { - builder.addPackage(embed.uri.uri, embed.package); - - // Add source redirect - builder.addRedirect(embed.source.uri, embed.uri.uri); - - // Add source implementation - builder.addInterfaceImplementation(embed.source.uri, embed.uri.uri); - } - - // Add all plugin packages - for (const plugin of Object.values(plugins)) { - builder.addPackage(plugin.uri.uri, plugin.plugin); - - // Add all interface implementations & redirects - for (const interfaceUri of plugin.implements) { - builder.addInterfaceImplementation(interfaceUri.uri, plugin.uri.uri); - builder.addRedirect(interfaceUri.uri, plugin.uri.uri); - } - } - - // Add all uri-resolver-ext interface implementations - builder.addInterfaceImplementations( - ExtendableUriResolver.defaultExtInterfaceUris[0].uri, - [ - uriResolverExts[0].source.uri, - uriResolverExts[1].from.uri, - ...uriResolverExts.slice(2).map((x: Uri) => x.uri), - ] - ); - builder.addRedirect(uriResolverExts[1].from.uri, uriResolverExts[1].to.uri); - - // Configure the ipfs-uri-resolver provider endpoints & retry counts - builder.addEnv(embeds.ipfsResolver.source.uri, { - provider: ipfsProviders[0], - fallbackProviders: ipfsProviders.slice(1), - retries: { tryResolveUri: 2, getFile: 2 }, - }); - - return builder.config; -} -``` \ No newline at end of file diff --git a/packages/js/client-config-builder/examples/quickstart.ts b/packages/js/client-config-builder/examples/quickstart.ts deleted file mode 100644 index bc099f1977..0000000000 --- a/packages/js/client-config-builder/examples/quickstart.ts +++ /dev/null @@ -1,159 +0,0 @@ -import { ClientConfigBuilder } from "../build"; - -// eslint-disable-next-line import/no-extraneous-dependencies -import { WasmWrapper } from "@polywrap/wasm-js"; -import { httpPlugin } from "@polywrap/http-plugin-js"; -import { - RecursiveResolver, - ResolutionResultCache, -} from "@polywrap/uri-resolvers-js"; -import { fileSystemPlugin } from "@polywrap/file-system-plugin-js"; -import { CoreClientConfig } from "@polywrap/core-js"; - -export function initialize(): ClientConfigBuilder { - // $start: quickstart-initialize - // start with a blank slate (typical usage) - const builder = new ClientConfigBuilder(); - // $end - - return builder; -} - -export function configure(): ClientConfigBuilder { - const builder = new ClientConfigBuilder(); - - // $start: quickstart-configure - // add multiple items to the configuration using the catch-all `add` method - builder.add({ - envs: {}, - interfaces: {}, - redirects: {}, - wrappers: {}, - packages: {}, - resolvers: [], - }); - - // add or remove items by chaining method calls - builder - .addPackage("wrap://plugin/package", httpPlugin({})) - .removePackage("wrap://plugin/package") - .addPackages({ - "wrap://plugin/http": httpPlugin({}), - "wrap://plugin/filesystem": fileSystemPlugin({}), - }); - // $end - - // $start: quickstart-addDefaults - builder.addDefaults(); - // $end - - return builder; -} - -export function build(): ClientConfigBuilder | CoreClientConfig { - const builder = new ClientConfigBuilder(); - - // $start: quickstart-build - // accepted by either the PolywrapClient or the PolywrapCoreClient - let coreClientConfig = builder.build(); - - // build with a custom cache - coreClientConfig = builder.build({ - resolutionResultCache: new ResolutionResultCache(), - }); - - // or build with a custom resolver - coreClientConfig = builder.build({ - resolver: RecursiveResolver.from([]), - }); - // $end - - return builder ?? coreClientConfig; -} - -export async function example(): Promise { - // $start: quickstart-example - // init - const builder = new ClientConfigBuilder(); - - // add the default bundle first to override its entries later - builder.addDefaults(); - - // add many config items at once - builder.add({ - envs: {}, - interfaces: {}, - redirects: {}, - wrappers: {}, - packages: {}, - resolvers: [], - }); - - // add and remove wrappers - builder - .addWrapper( - "wrap://ens/wrapper.eth", - await WasmWrapper.from( - new Uint8Array([1, 2, 3]), - new Uint8Array([1, 2, 3]) - ) - ) - .removeWrapper("wrap://ens/wrapper.eth") - .addWrappers({ - "wrap://ens/wrapper.eth": await WasmWrapper.from( - new Uint8Array([1, 2, 3]), - new Uint8Array([1, 2, 3]) - ), - }); - - // add and remove wrap packages - builder - .addPackage("wrap://plugin/package", httpPlugin({})) - .removePackage("wrap://plugin/package") - .addPackages({ - "wrap://plugin/package": httpPlugin({}), - }); - - // add and remove Envs - builder - .addEnv("wrap://ens/wrapper.eth", { key: "value" }) - .removeEnv("wrap://ens/wrapper.eth") - .addEnvs({ - "wrap://ens/wrapper.eth": { key: "value" }, - }); - - // override existing Env, or add new Env if one is not registered at URI - builder.setEnv("wrap://ens/wrapper.eth", { key: "value" }); - - // add or remove registration for an implementation of an interface - builder - .addInterfaceImplementation( - "wrap://ens/interface.eth", - "wrap://ens/wrapper.eth" - ) - .removeInterfaceImplementation( - "wrap://ens/interface.eth", - "wrap://ens/wrapper.eth" - ) - .addInterfaceImplementations("wrap://ens/interface.eth", [ - "wrap://ens/wrapper.eth", - ]); - - // add or remove URI redirects - builder - .addRedirect("wrap://ens/from.eth", "wrap://ens/to.eth") - .removeRedirect("wrap://ens/from.eth") - .addRedirects({ - "wrap://ens/from.eth": "wrap://ens/to.eth", - }); - - // add resolvers - builder.addResolver(RecursiveResolver.from([])); - builder.addResolvers([]); - - // build - const clientConfig = builder.build(); - // $end - - return clientConfig; -} diff --git a/packages/js/client-config-builder/examples/tsconfig.examples.json b/packages/js/client-config-builder/examples/tsconfig.examples.json deleted file mode 100644 index f37de53612..0000000000 --- a/packages/js/client-config-builder/examples/tsconfig.examples.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "extends": "../tsconfig.json", - "include": [ - "./**/*.ts" - ], -} \ No newline at end of file diff --git a/packages/js/client-config-builder/jest.config.js b/packages/js/client-config-builder/jest.config.js deleted file mode 100644 index a5ca876a5a..0000000000 --- a/packages/js/client-config-builder/jest.config.js +++ /dev/null @@ -1,11 +0,0 @@ -module.exports = { - collectCoverage: true, - preset: 'ts-jest', - testEnvironment: 'node', - testMatch: ["**/?(*.)+(spec|test).[jt]s?(x)"], - globals: { - 'ts-jest': { - diagnostics: false - } - } -}; diff --git a/packages/js/client-config-builder/package.json b/packages/js/client-config-builder/package.json deleted file mode 100644 index bcf528cba7..0000000000 --- a/packages/js/client-config-builder/package.json +++ /dev/null @@ -1,91 +0,0 @@ -{ - "name": "@polywrap/client-config-builder-js", - "description": "Polywrap Javascript Client configuration", - "version": "0.10.0", - "license": "MIT", - "repository": { - "type": "git", - "url": "https://github.com/polywrap/monorepo.git" - }, - "main": "build/index.js", - "files": [ - "build" - ], - "scripts": { - "build": "yarn embed:wrappers && yarn build:fast", - "build:docs": "yarn build:snippets && yarn build:readme", - "build:fast": "rimraf ./build && tsc --project tsconfig.build.json", - "embed:wrappers": "ts-node ./scripts/embed-wrappers.ts", - "lint": "eslint --color -c ../../../.eslintrc.js src/", - "test": "jest --passWithNoTests --runInBand --verbose", - "test:watch": "yarn test -- --watch", - "build:snippets": "tsc --project ./examples/tsconfig.examples.json", - "build:readme": "yarn doc-snippets combine" - }, - "dependencies": { - "@polywrap/concurrent-plugin-js": "~0.10.0-pre", - "@polywrap/core-js": "0.10.0", - "@polywrap/ethereum-provider-js": "npm:@polywrap/ethereum-provider-js@~0.3.0", - "@polywrap/ethereum-provider-js-v1": "npm:@polywrap/ethereum-provider-js@~0.2.4", - "@polywrap/file-system-plugin-js": "~0.10.0-pre", - "@polywrap/http-plugin-js": "~0.10.0-pre", - "@polywrap/logger-plugin-js": "0.10.0-pre.10", - "@polywrap/uri-resolver-extensions-js": "0.10.0", - "@polywrap/uri-resolvers-js": "0.10.0", - "@polywrap/wasm-js": "0.10.0", - "base64-to-uint8array": "1.0.0" - }, - "devDependencies": { - "@types/jest": "26.0.8", - "@types/prettier": "2.6.0", - "doc-snippets": "~1.0.0", - "jest": "26.6.3", - "rimraf": "3.0.2", - "ts-jest": "26.5.4", - "ts-node": "10.9.1", - "typescript": "4.9.5" - }, - "gitHead": "7346adaf5adb7e6bbb70d9247583e995650d390a", - "publishConfig": { - "access": "public" - }, - "doc-snippets": { - "extract": { - "include": [ - "./src/**/*.{ts,tsx,json,yaml,txt,md,graphql,cue}", - "./examples/**/*.{ts,tsx,json,yaml,txt,md,graphql,cue}" - ], - "ignore": [ - "./**/node_modules/**", - "./**/.polywrap/**", - "./**/__tests__/**" - ], - "dir": "./" - }, - "inject": { - "dir": "./readme", - "include": "./README.md" - }, - "startTokens": [ - { - "pattern": "$start: ", - "inline": false - }, - { - "pattern": "/* $: {SNIPPET_NAME} */", - "inline": true - } - ], - "endTokens": [ - { - "pattern": "$end", - "inline": false - }, - { - "pattern": "/* $ */", - "inline": true - } - ], - "outputDir": "./" - } -} diff --git a/packages/js/client-config-builder/readme/README.md b/packages/js/client-config-builder/readme/README.md deleted file mode 100644 index 1e98bea215..0000000000 --- a/packages/js/client-config-builder/readme/README.md +++ /dev/null @@ -1,166 +0,0 @@ -# PolywrapClient Config Builder - -A utility class for building the PolywrapClient config. - -Supports building configs using method chaining or imperatively. - -## Quickstart - -### Initialize - -Initialize a ClientConfigBuilder using the [constructor](#constructor) - -```typescript -$snippet: quickstart-initialize -``` - -### Configure - -Add client configuration with [add](#add), or flexibly mix and match builder [configuration methods](#addwrapper) to add and remove configuration items. - -```typescript -$snippet: quickstart-configure -``` - -You can add the entire [default client configuration bundle](#bundle--defaultconfig) at once with [addDefaults](#adddefaults) - -```typescript -$snippet: quickstart-addDefaults -``` - -### Build - -Finally, build a ClientConfig or CoreClientConfig to pass to the PolywrapClient constructor. - -```typescript -$snippet: quickstart-build -``` - -### Example - -A complete example using all or most of the available methods. - -```typescript= -$snippet: quickstart-example -``` - -# Reference - -## ClientConfigBuilder - -### Constructor -```ts -$snippet: ClientConfigBuilder-constructor -``` - -### add -```ts -$snippet: IClientConfigBuilder-add -``` - -### addWrapper -```ts -$snippet: IClientConfigBuilder-addWrapper -``` - -### addWrappers -```ts -$snippet: IClientConfigBuilder-addWrappers -``` - -### removeWrapper -```ts -$snippet: IClientConfigBuilder-removeWrapper -``` - -### addPackage -```ts -$snippet: IClientConfigBuilder-addPackage -``` - -### addPackages -```ts -$snippet: IClientConfigBuilder-addPackages -``` - -### removePackage -```ts -$snippet: IClientConfigBuilder-removePackage -``` - -### addEnv -```ts -$snippet: IClientConfigBuilder-addEnv -``` - -### addEnvs -```ts -$snippet: IClientConfigBuilder-addEnvs -``` - -### removeEnv -```ts -$snippet: IClientConfigBuilder-removeEnv -``` - -### setEnv -```ts -$snippet: IClientConfigBuilder-setEnv -``` - -### addInterfaceImplementation -```ts -$snippet: IClientConfigBuilder-addInterfaceImplementation -``` - -### addInterfaceImplementations -```ts -$snippet: IClientConfigBuilder-addInterfaceImplementations -``` - -### removeInterfaceImplementation -```ts -$snippet: IClientConfigBuilder-removeInterfaceImplementation -``` - -### addRedirect -```ts -$snippet: IClientConfigBuilder-addRedirect -``` - -### addRedirects -```ts -$snippet: IClientConfigBuilder-addRedirects -``` - -### removeRedirect -```ts -$snippet: IClientConfigBuilder-removeRedirect -``` - -### addResolver -```ts -$snippet: IClientConfigBuilder-addResolver -``` - -### addResolvers -```ts -$snippet: IClientConfigBuilder-addResolvers -``` - -### addDefaults -```ts -$snippet: IClientConfigBuilder-addDefaults -``` - -### build -```ts -$snippet: IClientConfigBuilder-build -``` - -## Bundles - -### Bundle: DefaultConfig -```ts -$snippet: getDefaultConfig -``` \ No newline at end of file diff --git a/packages/js/client-config-builder/scripts/embed-wrappers.ts b/packages/js/client-config-builder/scripts/embed-wrappers.ts deleted file mode 100644 index 55b68a0a57..0000000000 --- a/packages/js/client-config-builder/scripts/embed-wrappers.ts +++ /dev/null @@ -1,69 +0,0 @@ -import fs from "fs"; -import path from "path"; -import { WasmPackage } from "@polywrap/wasm-js"; - -async function main() { - - const embedsDir = path.join(__dirname, "../src/bundles/embeds"); - const embedsDirents = fs.readdirSync(embedsDir, { withFileTypes: true }); - - const wrapperDirs: string[] = []; - - for (const dirent of embedsDirents) { - if (dirent.isDirectory()) { - wrapperDirs.push(path.join(embedsDir, dirent.name)); - } - } - - for (const wrapperDir of wrapperDirs) { - const wasmBytes = fs.readFileSync( - path.join(wrapperDir, "wrap.wasm") - ); - const infoBytes = fs.readFileSync( - path.join(wrapperDir, "wrap.info") - ); - - try { - // Make sure we can load the wasm module - const tryLoad = WasmPackage.from( - infoBytes, - wasmBytes - ); - const result = await tryLoad.getManifest(); - if (!result.ok) throw result.error; - } catch (err) { - throw Error(`Unable to load wrapper at ${wrapperDir}`); - } - - fs.writeFileSync( - path.join(wrapperDir, "wrap.ts"), -`// NOTE: This file is auto-generated, do not modify by hand! -// See: ./scripts/embed-wrappers.ts -import { WasmPackage } from "@polywrap/wasm-js"; -import toUint8Array from "base64-to-uint8array"; - -const wrap_wasm = toUint8Array( - "${wasmBytes.toString("base64")}" -); - -const wrap_info = toUint8Array( - "${infoBytes.toString("base64")}" -); - -export const wasmPackage = WasmPackage.from( - wrap_info, - wrap_wasm -); -` - ); - } -} - -main() - .then(() => { - process.exit(); - }) - .catch((err) => { - console.error(err); - process.abort(); - }); diff --git a/packages/js/client-config-builder/src/BaseClientConfigBuilder.ts b/packages/js/client-config-builder/src/BaseClientConfigBuilder.ts deleted file mode 100644 index d1f502b2c7..0000000000 --- a/packages/js/client-config-builder/src/BaseClientConfigBuilder.ts +++ /dev/null @@ -1,233 +0,0 @@ -import { BuilderConfig, IClientConfigBuilder } from "./types"; - -import { - CoreClientConfig, - Wrapper, - IWrapPackage, - Uri, -} from "@polywrap/core-js"; -import { UriResolverLike } from "@polywrap/uri-resolvers-js"; - -export abstract class BaseClientConfigBuilder implements IClientConfigBuilder { - protected _config: BuilderConfig = { - envs: {}, - interfaces: {}, - redirects: {}, - wrappers: {}, - packages: {}, - resolvers: [], - }; - - abstract addDefaults(): IClientConfigBuilder; - abstract build(): CoreClientConfig; - - get config(): BuilderConfig { - return this._config; - } - - add(config: Partial): IClientConfigBuilder { - if (config.envs) { - this.addEnvs(config.envs); - } - - if (config.redirects) { - this.addRedirects(config.redirects); - } - - if (config.wrappers) { - this.addWrappers(config.wrappers); - } - - if (config.packages) { - this.addPackages(config.packages); - } - - if (config.interfaces) { - for (const [interfaceUri, implementations] of Object.entries( - config.interfaces - )) { - this.addInterfaceImplementations(interfaceUri, implementations); - } - } - - if (config.resolvers) { - this.addResolvers(config.resolvers); - } - - return this; - } - - addWrapper(uri: string, wrapper: Wrapper): IClientConfigBuilder { - this._config.wrappers[this.sanitizeUri(uri)] = wrapper; - - return this; - } - - addWrappers(uriWrappers: Record): IClientConfigBuilder { - for (const uri in uriWrappers) { - this.addWrapper(this.sanitizeUri(uri), uriWrappers[uri]); - } - - return this; - } - - removeWrapper(uri: string): IClientConfigBuilder { - delete this._config.wrappers[this.sanitizeUri(uri)]; - - return this; - } - - addPackage(uri: string, wrapPackage: IWrapPackage): IClientConfigBuilder { - this._config.packages[this.sanitizeUri(uri)] = wrapPackage; - - return this; - } - - addPackages(uriPackages: Record): IClientConfigBuilder { - for (const uri in uriPackages) { - this.addPackage(this.sanitizeUri(uri), uriPackages[uri]); - } - - return this; - } - - removePackage(uri: string): IClientConfigBuilder { - delete this._config.packages[this.sanitizeUri(uri)]; - - return this; - } - - addEnv(uri: string, env: Record): IClientConfigBuilder { - const sanitizedUri = this.sanitizeUri(uri); - this._config.envs[sanitizedUri] = { - ...this._config.envs[sanitizedUri], - ...env, - }; - - return this; - } - - addEnvs(envs: Record>): IClientConfigBuilder { - for (const [uri, env] of Object.entries(envs)) { - this.addEnv(this.sanitizeUri(uri), env); - } - - return this; - } - - removeEnv(uri: string): IClientConfigBuilder { - delete this._config.envs[this.sanitizeUri(uri)]; - - return this; - } - - setEnv(uri: string, env: Record): IClientConfigBuilder { - this._config.envs[this.sanitizeUri(uri)] = env; - - return this; - } - - addInterfaceImplementation( - interfaceUri: string, - implementationUri: string - ): IClientConfigBuilder { - const existingInterface = this._config.interfaces[ - this.sanitizeUri(interfaceUri) - ]; - - if (existingInterface) { - existingInterface.add(this.sanitizeUri(implementationUri)); - } else { - this._config.interfaces[this.sanitizeUri(interfaceUri)] = new Set([ - this.sanitizeUri(implementationUri), - ]); - } - - return this; - } - - addInterfaceImplementations( - interfaceUri: string, - implementationUris: Array | Set - ): IClientConfigBuilder { - const existingInterface = this._config.interfaces[ - this.sanitizeUri(interfaceUri) - ]; - - if (existingInterface) { - for (const implementationUri of implementationUris) { - existingInterface.add(this.sanitizeUri(implementationUri)); - } - } else { - const sanitizedImplUris = [...implementationUris].map((x) => - this.sanitizeUri(x) - ); - this._config.interfaces[this.sanitizeUri(interfaceUri)] = new Set( - sanitizedImplUris - ); - } - - return this; - } - - removeInterfaceImplementation( - interfaceUri: string, - implementationUri: string - ): IClientConfigBuilder { - const existingInterface = this._config.interfaces[ - this.sanitizeUri(interfaceUri) - ]; - - if (!existingInterface) return this; - - existingInterface.delete(this.sanitizeUri(implementationUri)); - - if (existingInterface.size == 0) { - delete this.config.interfaces[this.sanitizeUri(interfaceUri)]; - } - - if (existingInterface.size == 0) { - delete this._config.interfaces[interfaceUri]; - } - - return this; - } - - addRedirect(from: string, to: string): IClientConfigBuilder { - this._config.redirects[this.sanitizeUri(from)] = this.sanitizeUri(to); - - return this; - } - - addRedirects(redirects: Record): IClientConfigBuilder { - for (const uri in redirects) { - this.addRedirect(this.sanitizeUri(uri), this.sanitizeUri(redirects[uri])); - } - - return this; - } - - removeRedirect(from: string): IClientConfigBuilder { - delete this._config.redirects[this.sanitizeUri(from)]; - - return this; - } - - addResolver(resolver: UriResolverLike): IClientConfigBuilder { - this._config.resolvers.push(resolver); - - return this; - } - - addResolvers(resolvers: UriResolverLike[]): IClientConfigBuilder { - for (const resolver of resolvers) { - this.addResolver(resolver); - } - - return this; - } - - private sanitizeUri(uri: string): string { - return Uri.from(uri).uri; - } -} diff --git a/packages/js/client-config-builder/src/ClientConfigBuilder.ts b/packages/js/client-config-builder/src/ClientConfigBuilder.ts deleted file mode 100644 index 9ceb41f01e..0000000000 --- a/packages/js/client-config-builder/src/ClientConfigBuilder.ts +++ /dev/null @@ -1,125 +0,0 @@ -import { DefaultBundle } from "./bundles"; -import { BaseClientConfigBuilder } from "./BaseClientConfigBuilder"; -import { BuildOptions, IClientConfigBuilder, BuilderConfig } from "./types"; - -import { - CoreClientConfig, - IUriPackage, - IUriRedirect, - IUriWrapper, - Uri, - WrapperEnv, - ReadonlyUriMap, - UriMap, -} from "@polywrap/core-js"; -import { - RecursiveResolver, - StaticResolver, - ResolutionResultCache, - ResolutionResultCacheResolver, - PackageToWrapperResolver, - RequestSynchronizerResolver, -} from "@polywrap/uri-resolvers-js"; -import { ExtendableUriResolver } from "@polywrap/uri-resolver-extensions-js"; - -export class ClientConfigBuilder extends BaseClientConfigBuilder { - // $start: ClientConfigBuilder-constructor - /** - * Instantiate a ClientConfigBuilder - */ - constructor() /* $ */ { - super(); - } - - addDefaults(): IClientConfigBuilder { - return this.add(DefaultBundle.getConfig()); - } - - build(options?: BuildOptions): CoreClientConfig { - const resolver = - options && "resolver" in options ? options.resolver : undefined; - const resolutionResultCache = - options && "resolutionResultCache" in options - ? options.resolutionResultCache - : undefined; - return { - envs: this.buildEnvs(), - interfaces: this.buildInterfaces(), - resolver: - resolver ?? - RecursiveResolver.from( - RequestSynchronizerResolver.from( - ResolutionResultCacheResolver.from( - PackageToWrapperResolver.from([ - StaticResolver.from([ - ...this.buildRedirects(), - ...this.buildWrappers(), - ...this.buildPackages(), - ]), - ...this._config.resolvers, - new ExtendableUriResolver(), - ]), - resolutionResultCache ?? new ResolutionResultCache() - ) - ) - ), - }; - } - - get config(): BuilderConfig { - return this._config; - } - - private buildEnvs(): ReadonlyUriMap { - const envs = new UriMap(); - - for (const uri in this._config.envs) { - envs.set(Uri.from(uri), this._config.envs[uri]); - } - - return envs; - } - - private buildInterfaces(): ReadonlyUriMap { - const interfaceImplementations = new UriMap(); - - for (const uri in this._config.interfaces) { - const uriImpls = [...this._config.interfaces[uri]].map((x) => - Uri.from(x) - ); - interfaceImplementations.set(Uri.from(uri), uriImpls); - } - - return interfaceImplementations; - } - - private buildRedirects(): IUriRedirect[] { - const redirects: IUriRedirect[] = []; - - for (const [uri, redirect] of Object.entries(this._config.redirects)) { - redirects.push({ from: Uri.from(uri), to: Uri.from(redirect) }); - } - - return redirects; - } - - private buildWrappers(): IUriWrapper[] { - const wrappers: IUriWrapper[] = []; - - for (const [uri, wrapper] of Object.entries(this._config.wrappers)) { - wrappers.push({ uri: Uri.from(uri), wrapper }); - } - - return wrappers; - } - - private buildPackages(): IUriPackage[] { - const packages: IUriPackage[] = []; - - for (const [uri, wrapPackage] of Object.entries(this._config.packages)) { - packages.push({ uri: Uri.from(uri), package: wrapPackage }); - } - - return packages; - } -} diff --git a/packages/js/client-config-builder/src/__tests__/client-config-builder.spec.ts b/packages/js/client-config-builder/src/__tests__/client-config-builder.spec.ts deleted file mode 100644 index 2f473ca838..0000000000 --- a/packages/js/client-config-builder/src/__tests__/client-config-builder.spec.ts +++ /dev/null @@ -1,861 +0,0 @@ -import { ClientConfigBuilder } from "../ClientConfigBuilder"; -import { - CoreClient, - Uri, - IUriResolver, - UriPackageOrWrapper, - UriMap, - WrapperEnv, - IWrapPackage, - Wrapper, -} from "@polywrap/core-js"; -import { Result } from "@polywrap/result"; -import { DefaultBundle } from "../bundles"; - -class MockUriResolver implements IUriResolver { - private uri: string; - - constructor(from: string, to: string) { - this.uri = from; - } - get name(): string { - return this.uri; - } - tryResolveUri( - _uri: Uri, - _client: CoreClient - ): Promise> { - throw new Error("Not implemented"); - } -} - -describe("Client config builder", () => { - const emptyBuilderConfig = new ClientConfigBuilder().config; - - const testEnv1: Record> = { - "wrap://ens/test.plugin.one": { test: "value" }, - }; - - const testEnv2: Record> = { - "wrap://ens/test.plugin.two": { test: "value" }, - }; - - const testInterface1: Record> = { - "wrap://ens/test-interface-1.polywrap.eth": new Set([ - "wrap://ens/test1.polywrap.eth", - ]), - }; - - const testInterface2: Record> = { - "wrap://ens/test-interface-2.polywrap.eth": new Set([ - "wrap://ens/test2.polywrap.eth", - ]), - }; - - const testUriRedirect1 = { - "wrap://ens/test-one.polywrap.eth": "wrap://ens/test1.polywrap.eth", - }; - - const testUriRedirect2 = { - "wrap://ens/test-two.polywrap.eth": "wrap://ens/test2.polywrap.eth", - }; - - const testEnvs: Record> = { - ...testEnv1, - ...testEnv2, - }; - - const testInterfaces: Record> = { - ...testInterface1, - ...testInterface2, - }; - - const testUriRedirects = { - ...testUriRedirect1, - ...testUriRedirect2, - }; - - const testUriResolver: IUriResolver = new MockUriResolver( - "wrap://ens/testFrom.eth", - "wrap://ens/testTo.eth" - ); - - it("should build an empty partial config", () => { - const clientConfig = new ClientConfigBuilder().build(); - - expect(clientConfig.envs).toStrictEqual(new UriMap()); - expect(clientConfig.interfaces).toStrictEqual(new UriMap()); - }); - - it("should succesfully add config object and build", () => { - const configObject = { - envs: testEnvs, - interfaces: testInterfaces, - redirects: testUriRedirects, - resolvers: [testUriResolver], - }; - - const builder = new ClientConfigBuilder().add(configObject); - - const clientConfig = builder.build(); - const builderConfig = builder.config; - - expect(clientConfig).toBeTruthy(); - expect(clientConfig.envs).toStrictEqual( - new UriMap([ - [Uri.from("wrap://ens/test.plugin.one"), { test: "value" }], - [Uri.from("wrap://ens/test.plugin.two"), { test: "value" }], - ]) - ); - expect(clientConfig.interfaces).toStrictEqual( - new UriMap([ - [ - Uri.from("wrap://ens/test-interface-1.polywrap.eth"), - [Uri.from("wrap://ens/test1.polywrap.eth")], - ], - [ - Uri.from("wrap://ens/test-interface-2.polywrap.eth"), - [Uri.from("wrap://ens/test2.polywrap.eth")], - ], - ]) - ); - - expect(builderConfig).toEqual({ - ...emptyBuilderConfig, - ...configObject, - }); - }); - - it("should succesfully add and merge two config objects and build", () => { - const builder = new ClientConfigBuilder() - .add({ - envs: testEnv1, - interfaces: testInterface1, - redirects: testUriRedirect1, - resolvers: [testUriResolver], - }) - .add({ - envs: testEnv2, - interfaces: testInterface2, - redirects: testUriRedirect2, - }); - - const clientConfig = builder.build(); - const builderConfig = builder.config; - - expect(clientConfig).toBeTruthy(); - expect(clientConfig.envs).toStrictEqual( - new UriMap([ - [Uri.from("wrap://ens/test.plugin.one"), { test: "value" }], - [Uri.from("wrap://ens/test.plugin.two"), { test: "value" }], - ]) - ); - expect(clientConfig.interfaces).toStrictEqual( - new UriMap([ - [ - Uri.from("wrap://ens/test-interface-1.polywrap.eth"), - [Uri.from("wrap://ens/test1.polywrap.eth")], - ], - [ - Uri.from("wrap://ens/test-interface-2.polywrap.eth"), - [Uri.from("wrap://ens/test2.polywrap.eth")], - ], - ]) - ); - - expect(clientConfig.resolver).toBeTruthy(); - - expect(builderConfig).toEqual({ - ...emptyBuilderConfig, - envs: { ...testEnv1, ...testEnv2 }, - interfaces: { ...testInterface1, ...testInterface2 }, - redirects: { ...testUriRedirect1, ...testUriRedirect2 }, - resolvers: [testUriResolver], - }); - }); - - it("should successfully add the default config", () => { - const builder = new ClientConfigBuilder().addDefaults(); - - const clientConfig = builder.build(); - const builderConfig = builder.config; - - expect(clientConfig).toBeTruthy(); - - const expectedBuilderConfig = DefaultBundle.getConfig(); - expect(JSON.stringify(builderConfig)).toBe( - JSON.stringify(expectedBuilderConfig) - ); - }); - - it("should successfully add an env", () => { - const envUri = "wrap://ens/some-plugin.polywrap.eth"; - const env = { - foo: "bar", - baz: { - biz: "buz", - }, - }; - - const config = new ClientConfigBuilder().addEnv(envUri, env).build(); - - if (!config.envs || config.envs.size !== 1) { - fail(["Expected 1 env, received:", config.envs]); - } - - expect(config.envs.get(Uri.from(envUri))).toEqual(env); - }); - - it("should successfully add to an existing env", () => { - const envUri = "wrap://ens/some-plugin.polywrap.eth"; - const env1 = { - foo: "bar", - }; - const env2 = { - baz: { - biz: "buz", - }, - }; - - const config = new ClientConfigBuilder() - .addEnv(envUri, env1) - .addEnv(envUri, env2) - .build(); - - const expectedEnv = { ...env1, ...env2 }; - - if (!config.envs || config.envs.size !== 1) { - fail(["Expected 1 env, received:", config.envs]); - } - - expect(config.envs.get(Uri.from(envUri))).toEqual(expectedEnv); - }); - - it("should succesfully add two separate envs", () => { - const config = new ClientConfigBuilder() - .addEnv(Object.keys(testEnvs)[0], Object.values(testEnvs)[0]) - .addEnv(Object.keys(testEnvs)[1], Object.values(testEnvs)[1]) - .build(); - - if (!config.envs || config.envs.size !== 2) { - fail(["Expected 2 envs, received:", config.envs]); - } - - expect(config.envs.get(Uri.from(Object.keys(testEnvs)[0]))).toEqual( - Object.values(testEnvs)[0] - ); - expect(config.envs.get(Uri.from(Object.keys(testEnvs)[0]))).toEqual( - Object.values(testEnvs)[1] - ); - }); - - it("should remove an env", () => { - const config = new ClientConfigBuilder() - .addEnv(Object.keys(testEnvs)[0], Object.values(testEnvs)[0]) - .addEnv(Object.keys(testEnvs)[1], Object.values(testEnvs)[1]) - .removeEnv(Object.keys(testEnvs)[0]) - .build(); - - if (!config.envs || config.envs.size !== 1) { - fail(["Expected 1 env, received:", config.envs]); - } - - expect(config.envs.get(Uri.from(Object.keys(testEnvs)[1]))).toEqual( - Object.values(testEnvs)[1] - ); - }); - - it("should set an env", () => { - const envUri = "wrap://ens/some.plugin.eth"; - - const env = { - foo: "bar", - }; - - const config = new ClientConfigBuilder().setEnv(envUri, env).build(); - - if (!config.envs || config.envs.size !== 1) { - fail(["Expected 1 env, received:", config.envs]); - } - - expect(config.envs.get(Uri.from(envUri))).toEqual(env); - }); - - it("should set an env over an existing env", () => { - const envUri = "wrap://ens/some.plugin.eth"; - - const env1 = { - foo: "bar", - }; - const env2 = { - bar: "baz", - }; - - const config = new ClientConfigBuilder() - .addEnv(envUri, env1) - .setEnv(envUri, env2) - .build(); - - if (!config.envs || config.envs.size !== 1) { - fail(["Expected 1 env, received:", config.envs]); - } - - expect(config.envs.get(Uri.from(envUri))).toEqual(env2); - }); - - it("should add an interface implementation for a non-existent interface", () => { - const interfaceUri = "wrap://ens/some.interface.eth"; - const implUri = "wrap://ens/interface.impl.eth"; - - const config = new ClientConfigBuilder() - .addInterfaceImplementation(interfaceUri, implUri) - .build(); - - if (!config.interfaces || config.interfaces.size !== 1) { - fail(["Expected 1 interface, received:", config.interfaces]); - } - - expect(config.interfaces).toStrictEqual( - new UriMap([[Uri.from(interfaceUri), [Uri.from(implUri)]]]) - ); - }); - - it("should add an interface implementation for an interface that already exists", () => { - const interfaceUri = "wrap://ens/some.interface.eth"; - const implUri1 = "wrap://ens/interface.impl1.eth"; - const implUri2 = "wrap://ens/interface.impl2.eth"; - - const config = new ClientConfigBuilder() - .addInterfaceImplementation(interfaceUri, implUri1) - .addInterfaceImplementation(interfaceUri, implUri2) - .build(); - - if (!config.interfaces || config.interfaces.size !== 1) { - fail(["Expected 1 interface, received:", config.interfaces]); - } - - expect(config.interfaces).toStrictEqual( - new UriMap([ - [Uri.from(interfaceUri), [Uri.from(implUri1), Uri.from(implUri2)]], - ]) - ); - }); - - it("should add different implementations for different interfaces", () => { - const interfaceUri1 = "wrap://ens/some.interface1.eth"; - const interfaceUri2 = "wrap://ens/some.interface2.eth"; - const implUri1 = "wrap://ens/interface.impl1.eth"; - const implUri2 = "wrap://ens/interface.impl2.eth"; - const implUri3 = "wrap://ens/interface.impl3.eth"; - const implUri4 = "wrap://ens/interface.impl4.eth"; - - const config = new ClientConfigBuilder() - .addInterfaceImplementation(interfaceUri1, implUri1) - .addInterfaceImplementation(interfaceUri2, implUri2) - .addInterfaceImplementation(interfaceUri1, implUri3) - .addInterfaceImplementation(interfaceUri2, implUri4) - .build(); - - if (!config.interfaces || config.interfaces.size !== 2) { - fail(["Expected 2 interfaces, received:", config.interfaces]); - } - - expect(config.interfaces).toStrictEqual( - new UriMap([ - [Uri.from(interfaceUri1), [Uri.from(implUri1), Uri.from(implUri3)]], - [Uri.from(interfaceUri2), [Uri.from(implUri2), Uri.from(implUri4)]], - ]) - ); - }); - - it("should add multiple implementations for a non-existent interface", () => { - const interfaceUri = "wrap://ens/some.interface.eth"; - const implUri1 = "wrap://ens/interface.impl1.eth"; - const implUri2 = "wrap://ens/interface.impl2.eth"; - - const config = new ClientConfigBuilder() - .addInterfaceImplementations(interfaceUri, [implUri1, implUri2]) - .build(); - - if (!config.interfaces || config.interfaces.size !== 1) { - fail(["Expected 1 interface, received:", config.interfaces]); - } - - expect(config.interfaces).toStrictEqual( - new UriMap([ - [Uri.from(interfaceUri), [Uri.from(implUri1), Uri.from(implUri2)]], - ]) - ); - }); - - it("should add multiple implementations for an existing interface", () => { - const interfaceUri = "wrap://ens/some.interface.eth"; - const implUri1 = "wrap://ens/interface.impl1.eth"; - const implUri2 = "wrap://ens/interface.impl2.eth"; - const implUri3 = "wrap://ens/interface.impl3.eth"; - - const config = new ClientConfigBuilder() - .addInterfaceImplementations(interfaceUri, [implUri1]) - .addInterfaceImplementations(interfaceUri, [implUri2, implUri3]) - .build(); - - if (!config.interfaces || config.interfaces.size !== 1) { - fail(["Expected 1 interface, received:", config.interfaces]); - } - - expect(config.interfaces).toStrictEqual( - new UriMap([ - [ - Uri.from(interfaceUri), - [Uri.from(implUri1), Uri.from(implUri2), Uri.from(implUri3)], - ], - ]) - ); - }); - - it("should add multiple different implementations for different interfaces", () => { - const interfaceUri1 = "wrap://ens/some.interface1.eth"; - const interfaceUri2 = "wrap://ens/some.interface2.eth"; - const implUri1 = "wrap://ens/interface.impl1.eth"; - const implUri2 = "wrap://ens/interface.impl2.eth"; - const implUri3 = "wrap://ens/interface.impl3.eth"; - const implUri4 = "wrap://ens/interface.impl4.eth"; - const implUri5 = "wrap://ens/interface.impl5.eth"; - const implUri6 = "wrap://ens/interface.impl6.eth"; - - const config = new ClientConfigBuilder() - .addInterfaceImplementation(interfaceUri1, implUri1) - .addInterfaceImplementation(interfaceUri2, implUri2) - .addInterfaceImplementations(interfaceUri1, [implUri3, implUri5]) - .addInterfaceImplementations(interfaceUri2, [implUri4, implUri6]) - .build(); - - if (!config.interfaces || config.interfaces.size !== 2) { - fail(["Expected 2 interfaces, received:", config.interfaces]); - } - - expect(config.interfaces).toStrictEqual( - new UriMap([ - [ - Uri.from(interfaceUri1), - [Uri.from(implUri1), Uri.from(implUri3), Uri.from(implUri5)], - ], - [ - Uri.from(interfaceUri2), - [Uri.from(implUri2), Uri.from(implUri4), Uri.from(implUri6)], - ], - ]) - ); - }); - - it("should remove an interface implementation", () => { - const interfaceUri1 = "wrap://ens/some.interface1.eth"; - const interfaceUri2 = "wrap://ens/some.interface2.eth"; - const implUri1 = "wrap://ens/interface.impl1.eth"; - const implUri2 = "wrap://ens/interface.impl2.eth"; - - const config = new ClientConfigBuilder() - .addInterfaceImplementations(interfaceUri1, [implUri1, implUri2]) - .addInterfaceImplementations(interfaceUri2, [implUri1, implUri2]) - .removeInterfaceImplementation(interfaceUri1, implUri2) - .build(); - - if (!config.interfaces || config.interfaces.size !== 2) { - fail(["Expected 2 interfaces, received:", config.interfaces]); - } - - expect(config.interfaces).toStrictEqual( - new UriMap([ - [Uri.from(interfaceUri1), [Uri.from(implUri1)]], - [Uri.from(interfaceUri2), [Uri.from(implUri1), Uri.from(implUri2)]], - ]) - ); - }); - - it("should completely remove an interface if there are no implementations left", () => { - const interfaceUri1 = "wrap://ens/some.interface1.eth"; - const interfaceUri2 = "wrap://ens/some.interface2.eth"; - const implUri1 = "wrap://ens/interface.impl1.eth"; - const implUri2 = "wrap://ens/interface.impl2.eth"; - - const config = new ClientConfigBuilder() - .addInterfaceImplementations(interfaceUri1, [implUri1, implUri2]) - .addInterfaceImplementations(interfaceUri2, [implUri1, implUri2]) - .removeInterfaceImplementation(interfaceUri1, implUri1) - .removeInterfaceImplementation(interfaceUri1, implUri2) - .build(); - - if (!config.interfaces || config.interfaces.size !== 1) { - fail(["Expected 1 interface, received:", config.interfaces]); - } - - expect(config.interfaces).toStrictEqual( - new UriMap([ - [Uri.from(interfaceUri2), [Uri.from(implUri1), Uri.from(implUri2)]], - ]) - ); - }); - - it("should add an uri redirect", () => { - const from = "wrap://ens/from.this.ens"; - const to = "wrap://ens/to.that.ens"; - - const builder = new ClientConfigBuilder().addRedirect(from, to); - - const config = builder.build(); - const builderConfig = builder.config; - - expect(config).toBeTruthy(); - expect(builderConfig).toStrictEqual({ - ...emptyBuilderConfig, - redirects: { - [from]: to, - }, - }); - }); - - it("should add two uri redirects with different from uris", () => { - const from1 = "wrap://ens/from.this1.ens"; - const to1 = "wrap://ens/to.that1.ens"; - const from2 = "wrap://ens/from.this2.ens"; - const to2 = "wrap://ens/to.that2.ens"; - - const builder = new ClientConfigBuilder() - .addRedirect(from1, to1) - .addRedirect(from2, to2); - - const config = builder.build(); - const builderConfig = builder.config; - - expect(config).toBeTruthy(); - expect(builderConfig).toStrictEqual({ - ...emptyBuilderConfig, - redirects: { - [from1]: to1, - [from2]: to2, - }, - }); - }); - - it("should overwrite an existing uri redirect if from matches on add", () => { - const from1 = "wrap://ens/from1.this.ens"; - const from2 = "wrap://ens/from2.this.ens"; - const to1 = "wrap://ens/to.that1.ens"; - const to2 = "wrap://ens/to.that2.ens"; - - const builder = new ClientConfigBuilder() - .addRedirect(from1, to1) - .addRedirect(from2, to1) - .addRedirect(from1, to2); - - const config = builder.build(); - const builderConfig = builder.config; - - expect(config).toBeTruthy(); - expect(builderConfig).toStrictEqual({ - ...emptyBuilderConfig, - redirects: { - [from1]: to2, - [from2]: to1, - }, - }); - }); - - it("should remove an uri redirect", () => { - const from1 = "wrap://ens/from.this1.ens"; - const to1 = "wrap://ens/to.that1.ens"; - const from2 = "wrap://ens/from.this2.ens"; - const to2 = "wrap://ens/to.that2.ens"; - const builder = new ClientConfigBuilder() - .addRedirect(from1, to1) - .addRedirect(from2, to2) - .removeRedirect(from1); - - const config = builder.build(); - const builderConfig = builder.config; - - expect(config).toBeTruthy(); - expect(builderConfig).toStrictEqual({ - ...emptyBuilderConfig, - redirects: { - [from2]: to2, - }, - }); - }); - - it("should set uri resolver", () => { - const uriResolver = new MockUriResolver( - "wrap://ens/from.eth", - "wrap://ens/to.eth" - ); - - const builder = new ClientConfigBuilder().addResolver(uriResolver); - - const config = builder.build(); - const builderConfig = builder.config; - - expect(config).toBeTruthy(); - expect(builderConfig.resolvers).toStrictEqual([uriResolver]); - }); - - it("should add multiple resolvers", () => { - const uriResolver1 = new MockUriResolver( - "wrap://ens/from1.eth", - "wrap://ens/to1.eth" - ); - const uriResolver2 = new MockUriResolver( - "wrap://ens/from2.eth", - "wrap://ens/to2.eth" - ); - - const builder = new ClientConfigBuilder() - .addResolver(uriResolver1) - .addResolver(uriResolver2); - - const config = builder.build(); - const builderConfig = builder.config; - - expect(config).toBeTruthy(); - - expect(builderConfig.resolvers).toStrictEqual([uriResolver1, uriResolver2]); - }); - - it("should sanitize incoming URIs for envs", () => { - const shortUri = "ens/some1.wrapper.eth"; - const longUri = "wrap://ens/some2.wrapper.eth"; - - const builderConfig1 = new ClientConfigBuilder() - .addEnv(shortUri, { foo: "bar" }) - .addEnv(longUri, { bar: "baz" }).config; - - expect(builderConfig1.envs).toStrictEqual({ - [Uri.from(shortUri).uri]: { - foo: "bar", - }, - [Uri.from(longUri).uri]: { - bar: "baz", - }, - }); - - const builderConfig2 = new ClientConfigBuilder() - .add(builderConfig1) - .removeEnv(shortUri).config; - - expect(builderConfig2.envs).toStrictEqual({ - [Uri.from(longUri).uri]: { - bar: "baz", - }, - }); - }); - - it("should sanitize incoming URIs for interface implementations", () => { - const shortUri = "ens/some1.wrapper.eth"; - const longUri = "wrap://ens/some2.wrapper.eth"; - - const builderConfig1 = new ClientConfigBuilder() - .addInterfaceImplementation(shortUri, longUri) - .addInterfaceImplementation(longUri, shortUri).config; - - expect(builderConfig1.interfaces).toStrictEqual({ - [Uri.from(shortUri).uri]: new Set([Uri.from(longUri).uri]), - [Uri.from(longUri).uri]: new Set([Uri.from(shortUri).uri]), - }); - - const builderConfig2 = new ClientConfigBuilder() - .add(builderConfig1) - .removeInterfaceImplementation(shortUri, longUri).config; - - expect(builderConfig2.interfaces).toStrictEqual({ - [Uri.from(longUri).uri]: new Set([Uri.from(shortUri).uri]), - }); - }); - - it("should sanitize incoming URIs for redirects", () => { - const shortUri = "ens/some1.wrapper.eth"; - const longUri = "wrap://ens/some2.wrapper.eth"; - - const builderConfig1 = new ClientConfigBuilder() - .addRedirect(shortUri, longUri) - .addRedirect(longUri, shortUri).config; - - expect(builderConfig1.redirects).toStrictEqual({ - [Uri.from(shortUri).uri]: Uri.from(longUri).uri, - [Uri.from(longUri).uri]: Uri.from(shortUri).uri, - }); - - const builderConfig2 = new ClientConfigBuilder() - .add(builderConfig1) - .removeRedirect(shortUri).config; - - expect(builderConfig2.redirects).toStrictEqual({ - [Uri.from(longUri).uri]: Uri.from(shortUri).uri, - }); - }); - - it("should add a package", () => { - const uri = "wrap://ens/some.package.eth"; - const pkg: IWrapPackage = { - createWrapper: jest.fn(), - getManifest: jest.fn(), - }; - - const builderConfig = new ClientConfigBuilder().addPackage(uri, pkg).config; - - expect(builderConfig.packages).toStrictEqual({ - [uri]: pkg, - }); - }); - - it("should add multiple packages", () => { - const uri1 = "wrap://ens/some1.package.eth"; - const uri2 = "wrap://ens/some2.package.eth"; - const pkg: IWrapPackage = { - createWrapper: jest.fn(), - getManifest: jest.fn(), - }; - - const builderConfig = new ClientConfigBuilder().addPackages({ - [uri1]: pkg, - [uri2]: pkg, - }).config; - - expect(builderConfig.packages).toStrictEqual({ - [uri1]: pkg, - [uri2]: pkg, - }); - }); - - it("should remove a package", () => { - const uri1 = "wrap://ens/some1.package.eth"; - const uri2 = "wrap://ens/some2.package.eth"; - const pkg: IWrapPackage = { - createWrapper: jest.fn(), - getManifest: jest.fn(), - }; - - const builderConfig = new ClientConfigBuilder() - .addPackages({ - [uri1]: pkg, - [uri2]: pkg, - }) - .removePackage(uri1).config; - - expect(builderConfig.packages).toStrictEqual({ - [uri2]: pkg, - }); - }); - - it("should sanitize incoming URIs for packages", () => { - const shortUri = "ens/some1.package.eth"; - const longUri = "wrap://ens/some2.package.eth"; - const pkg: IWrapPackage = { - createWrapper: jest.fn(), - getManifest: jest.fn(), - }; - - const builderConfig1 = new ClientConfigBuilder().addPackages({ - [shortUri]: pkg, - [longUri]: pkg, - }).config; - - expect(builderConfig1.packages).toStrictEqual({ - [Uri.from(shortUri).uri]: pkg, - [Uri.from(longUri).uri]: pkg, - }); - - const builderConfig2 = new ClientConfigBuilder() - .add(builderConfig1) - .removePackage(shortUri).config; - - expect(builderConfig2.packages).toStrictEqual({ - [Uri.from(longUri).uri]: pkg, - }); - }); - - it("should add a wrapper", () => { - const uri = "wrap://ens/some.wrapper.eth"; - const wrapper: Wrapper = { - getFile: jest.fn(), - getManifest: jest.fn(), - invoke: jest.fn(), - }; - - const builderConfig = new ClientConfigBuilder().addWrapper(uri, wrapper) - .config; - - expect(builderConfig.wrappers).toStrictEqual({ - [uri]: wrapper, - }); - }); - - it("should add multiple wrappers", () => { - const uri1 = "wrap://ens/some1.wrapper.eth"; - const uri2 = "wrap://ens/some2.wrapper.eth"; - - const wrapper: Wrapper = { - getFile: jest.fn(), - getManifest: jest.fn(), - invoke: jest.fn(), - }; - - const builderConfig = new ClientConfigBuilder().addWrappers({ - [uri1]: wrapper, - [uri2]: wrapper, - }).config; - - expect(builderConfig.wrappers).toStrictEqual({ - [uri1]: wrapper, - [uri2]: wrapper, - }); - }); - - it("should remove a wrapper", () => { - const uri1 = "wrap://ens/some1.wrapper.eth"; - const uri2 = "wrap://ens/some2.wrapper.eth"; - - const wrapper: Wrapper = { - getFile: jest.fn(), - getManifest: jest.fn(), - invoke: jest.fn(), - }; - - const builderConfig = new ClientConfigBuilder() - .addWrappers({ - [uri1]: wrapper, - [uri2]: wrapper, - }) - .removeWrapper(uri1).config; - - expect(builderConfig.wrappers).toStrictEqual({ - [uri2]: wrapper, - }); - }); - - it("should sanitize incoming URIs for wrappers", () => { - const shortUri = "ens/some1.wrapper.eth"; - const longUri = "wrap://ens/some2.wrapper.eth"; - const wrapper: Wrapper = { - getFile: jest.fn(), - getManifest: jest.fn(), - invoke: jest.fn(), - }; - - const builderConfig1 = new ClientConfigBuilder().addWrappers({ - [shortUri]: wrapper, - [longUri]: wrapper, - }).config; - - expect(builderConfig1.wrappers).toStrictEqual({ - [Uri.from(shortUri).uri]: wrapper, - [Uri.from(longUri).uri]: wrapper, - }); - - const builderConfig2 = new ClientConfigBuilder() - .add(builderConfig1) - .removeWrapper(shortUri).config; - - expect(builderConfig2.wrappers).toStrictEqual({ - [Uri.from(longUri).uri]: wrapper, - }); - }); -}); diff --git a/packages/js/client-config-builder/src/bundles/default.ts b/packages/js/client-config-builder/src/bundles/default.ts deleted file mode 100644 index c50d9d96a5..0000000000 --- a/packages/js/client-config-builder/src/bundles/default.ts +++ /dev/null @@ -1,185 +0,0 @@ -import { ClientConfigBuilder } from "../ClientConfigBuilder"; -import { BuilderConfig } from "../types"; -import * as ipfsHttpClient from "./embeds/ipfs-http-client/wrap"; -import * as ipfsResolver from "./embeds/async-ipfs-resolver/wrap"; - -import { IWrapPackage, Uri } from "@polywrap/core-js"; -import * as EthProviderV1 from "@polywrap/ethereum-provider-js-v1"; -import * as EthProvider from "@polywrap/ethereum-provider-js"; -import { httpPlugin } from "@polywrap/http-plugin-js"; -import { fileSystemPlugin } from "@polywrap/file-system-plugin-js"; -import { loggerPlugin } from "@polywrap/logger-plugin-js"; -import { concurrentPromisePlugin } from "@polywrap/concurrent-plugin-js"; -import { ExtendableUriResolver } from "@polywrap/uri-resolver-extensions-js"; -import { IUriRedirect } from "@polywrap/core-js"; - -// $start: getDefaultConfig -export const ipfsProviders: string[] = [ - "https://ipfs.wrappers.io", - "https://ipfs.io", -]; - -interface IDefaultEmbed { - uri: Uri; - package: IWrapPackage; - source: Uri; -} - -interface IDefaultEmbeds { - ipfsHttpClient: IDefaultEmbed; - ipfsResolver: IDefaultEmbed; -} - -export const embeds: IDefaultEmbeds = { - ipfsHttpClient: { - uri: Uri.from("embed/ipfs-http-client@1.0.0"), - package: ipfsHttpClient.wasmPackage, - source: Uri.from("ens/wraps.eth:ipfs-http-client@1.0.0"), - }, - ipfsResolver: { - uri: Uri.from("embed/async-ipfs-uri-resolver-ext@1.0.1"), - package: ipfsResolver.wasmPackage, - source: Uri.from("ens/wraps.eth:async-ipfs-uri-resolver-ext@1.0.1"), - }, -}; - -type UriResolverExtBootloader = [IDefaultEmbed, IUriRedirect, ...Uri[]]; - -export const uriResolverExts: UriResolverExtBootloader = [ - embeds.ipfsResolver, - { - from: Uri.from("ens/wraps.eth:ens-text-record-uri-resolver-ext@1.0.1"), - to: Uri.from("ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs"), - }, - Uri.from("ens/wraps.eth:http-uri-resolver-ext@1.0.1"), - Uri.from("ens/wraps.eth:file-system-uri-resolver-ext@1.0.1"), - Uri.from("ens/wraps.eth:ens-uri-resolver-ext@1.0.1"), - Uri.from("ens/wraps.eth:ens-ipfs-contenthash-uri-resolver-ext@1.0.1"), -]; - -interface IDefaultPlugin { - uri: Uri; - plugin: IWrapPackage; - implements: Uri[]; -} - -interface IDefaultPlugins { - logger: IDefaultPlugin; - http: IDefaultPlugin; - fileSystem: IDefaultPlugin; - concurrent: IDefaultPlugin; - ethereumProviderV1: IDefaultPlugin; - ethereumProviderV2: IDefaultPlugin; -} - -export const plugins: IDefaultPlugins = { - logger: { - uri: Uri.from("plugin/logger@1.0.0"), - plugin: loggerPlugin({}), - implements: [Uri.from("ens/wraps.eth:logger@1.0.0")], - }, - http: { - uri: Uri.from("plugin/http@1.1.0"), - plugin: httpPlugin({}), - implements: [ - Uri.from("ens/wraps.eth:http@1.1.0"), - Uri.from("ens/wraps.eth:http@1.0.0"), - ], - }, - fileSystem: { - uri: Uri.from("plugin/file-system@1.0.0"), - plugin: fileSystemPlugin({}), - implements: [Uri.from("ens/wraps.eth:file-system@1.0.0")], - }, - concurrent: { - uri: Uri.from("plugin/concurrent@1.0.0"), - plugin: concurrentPromisePlugin({}), - implements: [Uri.from("ens/wraps.eth:concurrent@1.0.0")], - }, - ethereumProviderV1: { - uri: Uri.from("plugin/ethereum-provider@1.1.0"), - plugin: EthProviderV1.plugin({ - connections: new EthProviderV1.Connections({ - networks: { - mainnet: new EthProviderV1.Connection({ - provider: - "https://mainnet.infura.io/v3/b00b2c2cc09c487685e9fb061256d6a6", - }), - goerli: new EthProviderV1.Connection({ - provider: - "https://goerli.infura.io/v3/b00b2c2cc09c487685e9fb061256d6a6", - }), - }, - }), - }), - implements: [ - Uri.from("ens/wraps.eth:ethereum-provider@1.1.0"), - Uri.from("ens/wraps.eth:ethereum-provider@1.0.0"), - ], - }, - ethereumProviderV2: { - uri: Uri.from("plugin/ethereum-provider@2.0.0"), - plugin: EthProvider.plugin({ - connections: new EthProvider.Connections({ - networks: { - mainnet: new EthProvider.Connection({ - provider: - "https://mainnet.infura.io/v3/b00b2c2cc09c487685e9fb061256d6a6", - }), - goerli: new EthProvider.Connection({ - provider: - "https://goerli.infura.io/v3/b00b2c2cc09c487685e9fb061256d6a6", - }), - }, - }), - }), - implements: [Uri.from("ens/wraps.eth:ethereum-provider@2.0.0")], - }, -}; - -export function getConfig(): BuilderConfig { - const builder = new ClientConfigBuilder(); - - // Add all embedded packages - for (const embed of Object.values(embeds)) { - builder.addPackage(embed.uri.uri, embed.package); - - // Add source redirect - builder.addRedirect(embed.source.uri, embed.uri.uri); - - // Add source implementation - builder.addInterfaceImplementation(embed.source.uri, embed.uri.uri); - } - - // Add all plugin packages - for (const plugin of Object.values(plugins)) { - builder.addPackage(plugin.uri.uri, plugin.plugin); - - // Add all interface implementations & redirects - for (const interfaceUri of plugin.implements) { - builder.addInterfaceImplementation(interfaceUri.uri, plugin.uri.uri); - builder.addRedirect(interfaceUri.uri, plugin.uri.uri); - } - } - - // Add all uri-resolver-ext interface implementations - builder.addInterfaceImplementations( - ExtendableUriResolver.defaultExtInterfaceUris[0].uri, - [ - uriResolverExts[0].source.uri, - uriResolverExts[1].from.uri, - ...uriResolverExts.slice(2).map((x: Uri) => x.uri), - ] - ); - builder.addRedirect(uriResolverExts[1].from.uri, uriResolverExts[1].to.uri); - - // Configure the ipfs-uri-resolver provider endpoints & retry counts - builder.addEnv(embeds.ipfsResolver.source.uri, { - provider: ipfsProviders[0], - fallbackProviders: ipfsProviders.slice(1), - retries: { tryResolveUri: 2, getFile: 2 }, - }); - - return builder.config; -} -// $end diff --git a/packages/js/client-config-builder/src/bundles/embeds/async-ipfs-resolver/wrap.info b/packages/js/client-config-builder/src/bundles/embeds/async-ipfs-resolver/wrap.info deleted file mode 100644 index 45d90783e873ee2f9043eac6720265c7061edb6d..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 13743 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 diff --git a/packages/js/client-config-builder/src/bundles/embeds/async-ipfs-resolver/wrap.ts b/packages/js/client-config-builder/src/bundles/embeds/async-ipfs-resolver/wrap.ts deleted file mode 100644 index f405d312ff..0000000000 --- a/packages/js/client-config-builder/src/bundles/embeds/async-ipfs-resolver/wrap.ts +++ /dev/null @@ -1,17 +0,0 @@ -// NOTE: This file is auto-generated, do not modify by hand! -// See: ./scripts/embed-wrappers.ts -import { WasmPackage } from "@polywrap/wasm-js"; -import toUint8Array from "base64-to-uint8array"; - -const wrap_wasm = toUint8Array( - "AGFzbQEAAAABgwETYAJ/fwF/YAN/f38Bf2ACf38AYAN/f38AYAF/AGAGf39/f39/AGAEf39/fwBgB39/f39/f38AYAF/AX9gAAF/YAF/AX5gBX9/f39/AGAFf39/f38Bf2AAAGAGf39/f39/AX9gA39/fgBgBH9/f38Bf2AHf39/f39/fwF/YAN+f38BfwKaAw4Ed3JhcBJfX3dyYXBfaW52b2tlX2FyZ3MAAgR3cmFwD19fd3JhcF9sb2FkX2VudgAEBHdyYXAZX193cmFwX2dldEltcGxlbWVudGF0aW9ucwAABHdyYXAkX193cmFwX2dldEltcGxlbWVudGF0aW9uc19yZXN1bHRfbGVuAAkEd3JhcCBfX3dyYXBfZ2V0SW1wbGVtZW50YXRpb25zX3Jlc3VsdAAEBHdyYXATX193cmFwX2ludm9rZV9lcnJvcgACBHdyYXAUX193cmFwX2ludm9rZV9yZXN1bHQAAgR3cmFwEF9fd3JhcF9zdWJpbnZva2UADgR3cmFwG19fd3JhcF9zdWJpbnZva2VfcmVzdWx0X2xlbgAJBHdyYXAXX193cmFwX3N1Ymludm9rZV9yZXN1bHQABAR3cmFwGl9fd3JhcF9zdWJpbnZva2VfZXJyb3JfbGVuAAkEd3JhcBZfX3dyYXBfc3ViaW52b2tlX2Vycm9yAAQEd3JhcAxfX3dyYXBfYWJvcnQABQNlbnYGbWVtb3J5AgACA4AC/gEGAwgLBgIBAgIBAgYBDwICBgUQAwQGAAMGAAYOAgIBAQIABwcHBwcHBQUFBQUFAgIDAwMBBwcHCAAHBwcAAgMMEQMABQASAwsAAgQABAAGAAYDAwIGAgAAAAgFBQUFBQUEBwIDAwEGAgIMAgIGAwYGAQMDAgUEBQUFBQUCBQUFBQUGBQUGBgYCBQICAgEBCwIGAwMDAgAAAwMDAAMDAwAAAgADAAAAAAAABAADBAEAAgQCAwMEAgIDAwADBAgIAgQMCAgEAgINCAIEAAQEBAgAAAAABAAGBgQAAAQABAAACwAAAgECAQMAAAMDAwEAAAEAAQEDAwkKCgoEBA0ECQQFAXABSkoGEgN/AUGAgAQLfwFBAAt/AUEACwecAQgMX3dyYXBfaW52b2tlAEAFYWxsb2MA2wEHZGVhbGxvYwDvARVhc3luY2lmeV9zdGFydF91bndp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KAIAQUBqNgIAIwIoAgAiASgCACEAIAEoAgghAiABKAIMIQMgASgCECEEIAEoAhQhByABKAIYIQggASkCHCEMIAEoAiQhCSABKAIoIQogASkCLCENIAEpAjQhDiABKAI8IQsgASgCBCEBCwJ/IwFBAkYEQCMCIwIoAgBBBGs2AgAjAigCACgCACEGCyMBRQRAIwAiB0GgAWsiAyQACyAGRUEBIwEbBEAgASACEAJBACMBQQFGDQEaIQELAkACfwJAAkACQCMBRUEAIAEgAUUjARsiARtFBEAgBkEBRkEBIwEbBEAQA0EBIwFBAUYNBxohCgsgBkECRkEBIwEbBEAgAyAKENEBQQIjAUEBRg0HGgsjAUUEQCADKAIAIQkLIAZBA0ZBASMBGwRAIAkQBEEDIwFBAUYNBxoLIwFFBEBBGxAPIgJFIgENAiACQYydBSkAADcAACACQQhqQZSdBSkAADcAACACQRBqQZydBSkAACIMNwAAIAJBF2pBo50FKAAAIgc2AAAgA0GAAWpCADcDACADQRs2AnQgAyACNgJwIANCm4CAgMAANwN4IANB8ABqIQIgA0EIaiEBCyAGQQRGQQEjARsEQCABIAkgCiACEFtBBCMBQQFGDQcaCyABIANBOGojARshASAGQQVGQQEjARsEQCABQbiVBUEgQdiVBUELQeOVBUEkEG5BBSMBQQFGDQcaCyMBRQRAIANBCGohByADQfAAaiECCyAGQQZGQQEjARsEQCACIAcQKkEGIwFBAUYNBxoLIwFFBEAgAygCcCIEQRZHIQILAkAjAUUEQAJAIAJFBEAgAygCdCECIANBADYCWCADQgQ3A1AgAg0BQQQMCAsgAykDeCENIAMoAnQhCAwCCyACrSEOQQQhB0IAIQxBACECCwNAIwFFBEAgA0EANgJoIANCATcDYCADQQM6AJABIANCgICAgIAENwNwIANB5IYFNgKMASADQQA2AoABIANBADYCeCADIANB4ABqNgKIASADQfAAaiEECyAGQQdGQQEjARsEQCAMQQEgBBBSQQcjAUEBRg0JGiEECyMBRQRAIAQNBSADKAJoIQggAygCYCEECyAGQQhGQQEjARsEQCABQfyLBUEGIAQgCEGCjAVBARBuQQgjAUEBRg0JGgsjAUUEQCADKAJkBEAgAygCYBAhCyADQQhqIQggA0HwAGoh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NgIAIwIjAigCAEEEajYCACMCKAIAIgMgADYCACADIAE2AgQgAyACNgIIIwIjAigCAEEMajYCAAuaAgECfyMBQQJGBEAjAiMCKAIAQQxrNgIAIwIoAgAiAigCACEAIAIoAgQhASACKAIIIQILAn8jAUECRgRAIwIjAigCAEEEazYCACMCKAIAKAIAIQMLIwFFBEAjAEEgayICJAAgAiAAKAIANgIEIAJBGGogAUEQaikCADcDACACQRBqIAFBCGopAgA3AwAgAiABKQIANwMIIAJBCGohASACQQRqIQALIANFQQEjARsEQCAAQYyiBSABECtBACMBQQFGDQEaIQELIwFFBEAgAkEgaiQAIAEPCwALIQMjAigCACADNgIAIwIjAigCAEEEajYCACMCKAIAIgMgADYCACADIAE2AgQgAyACNgIIIwIjAigCAEEMajYCAEEAC6kCAQJ/IwFBAkYEQCMCIwIoAgBBEGs2AgAjAigCACIDKAIAIQAgAygCBCEBIAMoAgghAiADKAIMIQMLAn8jAUECRgRAIwIjAigCAEEEazYCACMCKAIAKAIAIQQLIwFFBEAjAEEgayIDJAAgA0HUsgU2AgQgAyAANgIAIANBGGogAUEQaikCADcDACADQRBqIAFBCGopAgA3AwAgAyABKQIANwMIIANBCGohASADQQRqIQALIARFQQEjARsEQCADQaijBSAAQaijBSABIAIQUEEAIwFBAUYNARoLIwFFBEAACw8LIQQjAigCACAENgIAIwIjAigCAEEEajYCACMCKAIAIgQgADYCACAEIAE2AgQgBCACNgIIIAQgAzYCDCMCIwIoAgBBEGo2AgALmgIBAn8jAUECRgRAIwIjAigCAEEMazYCACMCKAIAIgIoAgAhACACKAIEIQEgAigCCCECCwJ/IwFBAkYEQCMCIwIoAgBBBGs2AgAjAigCACgCACEDCyMBRQRAIwBBIGsiAiQAIAIgACgCADYCBCACQRhqIAFBEGopAgA3AwAgAkEQaiABQQhqKQIANwMAIAIgASkCADcDCCACQQhqIQEgAkEEaiEACyADRUEBIwEbBEAgAEGkogUgARArQQAjAUEBRg0BGiEBCyMBRQRAIAJBIGokACABDwsACyEDIwIoAgAgAzYCACMCIwIoAgBBBGo2AgAjAigCACIDIAA2AgAgAyABNgIEIAMgAjYCCCMCIwIoAgBBDGo2AgBBAAuaAgECfyMBQQJGBEAjAiMCKAIAQQxrNgIAIwIoAgAiAigCACEAIAIoAgQhASACKAIIIQILAn8jAUECRgRAIwIjAigCAEEEazYCACMCKAIAKAIAIQMLIwFFBEAjAEEgayICJAAgAiAAKAIANgIEIAJBGGogAUEQaikCADcDACACQRBqIAFBCGopAgA3AwAgAiABKQIANwMIIAJBCGohASACQQRqIQALIANFQQEjARsEQCAAQbyiBSABECtBACMBQQFGDQEaIQELIwFFBEAgAkEgaiQAIAEPCwALIQMjAigCACADNgIAIwIjAigCAEEEajYCACMCKAIAIgMgADYCACADIAE2AgQgAyACNgIIIwIjAigCAEEMajYCAEEAC5cCAQJ/IwFBAkYEQCMCIwIoAgBBDGs2AgAjAigCACICKAIAIQAgAigCBCEBIAIoAgghAgsCfyMBQQJGBEAjAiMCKAIAQQRrNgIAIwIoAgAoAgAhAwsjAUUEQCMAQSBrIgIkACACIAA2AgQgAkEYaiABQRBqKQIANwMAIAJBEGogAUEIaikCADcDACACIAEpAgA3AwggAkEIaiEBIAJBBGohAAsgA0VBASMBGwRAIABB1IcEIAEQK0EAIwFBAUYNARohAQsjAUUEQCACQSBqJAAgAQ8LAAshAyMCKAIAIAM2AgAjAiMCKAIAQQRqNgIAIwIoAgAiAyAANgIAIAMgATYCBCADIAI2AggjAiMCKAIAQQxqNgIAQQALlwIBAn8jAUECRgRAIwIjAigCAEEMazYCACMCKAIAIgIoAgAhACACKAIEIQEgAigCCCECCwJ/IwFBAkYEQCMCIwIoAgBBBGs2AgAjAigCACgCACEDCyMBRQRAIwBBIGsiAiQAIAIgADYCBCACQRhqIAFBEGopAgA3AwAgAkEQaiABQQhqKQIANwMAIAIgASkCADcDCCACQQhqIQEgAkEEaiEACyADRUEBIwEbBEAgAEGMogUgARArQQAjAUEBRg0BGiEBCyMBRQRAIAJBIGokACABDwsACyEDIwIoAgAgAzYCACMCIwIoAgBBBGo2AgAjAigCACIDIAA2AgAgAyABNgIEIAMgAjYCCCMCIwIoAgBBDGo2AgBBAAuXAgECfyMBQQJGBEAjAiMCKAIAQQxrNgIAIwIoAgAiAigCACEAIAIoAgQhASACKAIIIQILAn8jAUECRgRAIwIjAigCAEEEazYCACMCKAIAKAIAIQMLIwFFBEAjAEEgayICJAAgAiAANgIEIAJBGGogAUEQaikCADcDACACQRBqIAFBCGopAgA3AwAgAiABKQIANwMIIAJBCGohASACQQRqIQALIANFQQEjARsEQCAAQaSiBSABECtBACMBQQFGDQEaIQELIwFFBEAgAkEgaiQAIAEPCwALIQMjAigCACADNgIAIwIjAigCAEEEajYCACMCKAIAIgMgADYCACADIAE2AgQgAyACNgIIIwIjAigCAEEMajYCAEEAC80CAQN/IwFBAkYEQCMCIwIoAgBBDGs2AgAjAigCACICKAIAIQAgAigCBCEBIAIoAgghAgsCfyMBQQJGBEAjAiMCKAIAQQRrNgIAIwIoAgAoAgAhBAsjAUUEQCMAQRBrIgIkACAAKAIAIgAtAARBBEchAwsCQAJAIwFFBEAgAw0BIAIgADYCCCACQQhqIQALIARFQQEjARsEQCABQeinBEECIABB7KcEEHZBACMBQQFGDQMaIQALIwFFDQELIwFFBEAgAiAANgIMIAJBDGohAAsgBEEBRkEBIwEbBEAgAUHUpwRBAyAAQdinBBB2QQEjAUEBRg0CGiEACwsjAUUEQCACQRBqJAAgAA8LAAshAyMCKAIAIAM2AgAjAiMCKAIAQQRqNgIAIwIoAgAiAyAANgIAIAMgATYCBCADIAI2AggjAiMCKAIAQQxqNgIAQQALUQEBfwJAIABBEGooAgAiAUUNACABQQA6AAAgAEEUaigCAEUNACAAKAIQECELAkAgAEF/Rg0AIAAgACgCBCIBQQFrNgIEIAFBAUcNACAAECELC4gCAQN/IwFBAkYEQCMCIwIoAgBBEGs2AgAjAigCACIDKAIAIQAgAygCBCEBIAMoAgghBCADKAIMIQMLAn8jAUECRgRAIwIjAigCAEEEazYCACMCKAIAKAIAIQILIwFFBEAjAEEQayIEJAAgBCAAKAIAIgA2AgggBCAAQQRqNgIMIARBDGohAyAEQQhqIQALIAJFQQEjARsEQCABIAAgAxB9QQAjAUEBRg0BGiEACyMBRQRAIARBEGokACAADwsACyECIwIoAgAgAjYCACMCIwIoAgBBBGo2AgAjAigCACICIAA2AgAgAiAB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gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAAAECAwQFBgeAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIAbAAAAAAAADBYBAAICAAAwMTIzNDU2Nzg5QUJDREVGR0hJSktMTU5PUFFSU1RVVldYWVphYmNkZWZnaGlqa2xtbm9wcXJzdHV2d3h5ejAxMjM0NTY3ODkrL0FCQ0RFRkdISUpLTE1OT1BRUlNUVVZXWFlaYWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXowMTIzNDU2Nzg5Ky9BQkNERUZHSElKS0xNTk9QUVJTVFVWV1hZWmFiY2RlZmdoaWprbG1ub3BxcnN0dXZ3eHl6MDEyMzQ1Njc4OSsvQUJDREVGR0hJSktMTU5PUFFSU1RVVldYWVphYmNkZWZnaGlqa2xtbm9wcXJzdHV2d3h5ejAxMjM0NTY3ODkrL4CAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIA+gICAPzQ1Njc4OTo7PD2AgICAgICAAAECAwQFBgcICQoLDA0ODxAREhMUFRYXGBmAgICAgIAaGxwdHh8gISIjJCUmJygpKissLS4vMDEyM4CAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAHgAAAAAmGAEAAgIAAHlibmRyZmc4ZWprbWNwcXhvdDF1d2lzemEzNDVoNzY5eWJuZHJmZzhlamttY3BxeG90MXV3aXN6YTM0NWg3Njl5Ym5kcmZnOGVqa21jcHF4b3QxdXdpc3phMzQ1aDc2OXlibmRyZmc4ZWprbWNwcXhvdDF1d2lzemEzNDVoNzY5eWJuZHJmZzhlamttY3BxeG90MXV3aXN6YTM0NWg3Njl5Ym5kcmZnOGVqa21jcHF4b3QxdXdpc3phMzQ1aDc2OXlibmRyZmc4ZWprbWNwcXhvdDF1d2lzemEzNDVoNzY5eWJuZHJmZzhlamttY3BxeG90MXV3aXN6YTM0NWg3NjmAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAEoAZGhseHQcfgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAGAEMAwgFBhwVCQqACwIQDQ4EFhETgBQPABeAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgB0AAAAAAAA0GgEAAgIAADEyMzQ1Njc4OUFCQ0RFRkdISktMTU5QUVJTVFVWV1hZWmFiY2RlZmdoaWprbW5vcHFyc3R1dnd4eXpBQkNERUZHSElKS0xNTk9QUVJTVFVWV1hZWmFiY2RlZmdoaWprbG1ub3BxcnN0dXZ3eHl6MDEyMzQ1Njc4OSsvQUJDREVGR0hJSktMTU5PUFFSU1RVVldYWVphYmNkZWZnaGlqa2xtbm9wcXJzdHV2d3h5ejAxMjM0NTY3ODkrL0FCQ0RFRkdISUpLTE1OT1BRUlNUVVZXWFlaYWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXowMTIzNDU2Nzg5Ky9BQkNERUZHSElKS0xNTk9QUVJTVFVWV1hZWmFiY2RlZmdoaWprbG1ub3BxcnN0dXZ3eHl6MDEyMzQ1Njc4OSsvgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgD6AgIA/NDU2Nzg5Ojs8PYCAgIKAgIAAAQIDBAUGBwgJCgsMDQ4PEBESExQVFhcYGYCAgICAgBobHB0eHyAhIiMkJSYnKCkqKywtLi8wMTIzgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgD0eAAAAAH4cAQACAgAAQUJDREVGR0hJSktMTU5PUFFSU1RVVldYWVphYmNkZWZnaGlqa2xtbm9wcXJzdHV2d3h5ejAxMjM0NTY3ODktX0FCQ0RFRkdISUpLTE1OT1BRUlNUVVZXWFlaYWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXowMTIzNDU2Nzg5LV9BQkNERUZHSElKS0xNTk9QUVJTVFVWV1hZWmFiY2RlZmdoaWprbG1ub3BxcnN0dXZ3eHl6MDEyMzQ1Njc4OS1fQUJDREVGR0hJSktMTU5PUFFSU1RVVldYWVphYmNkZWZnaGlqa2xtbm9wcXJzdHV2d3h5ejAxMjM0NTY3ODktX4CAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgD6AgDQ1Njc4OTo7PD2AgICAgICAAAECAwQFBgcICQoLDA0ODxAREhMUFRYXGBmAgICAP4AaGxwdHh8gISIjJCUmJygpKissLS4vMDEyM4CAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAHgAAAAAAAIweAQACAgAAMDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3ODlhYmNkZWYwMTIzNDU2Nzg5YWJjZGVmMDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3ODlhYmNkZWYwMTIzNDU2Nzg5YWJjZGVmMDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3ODlhYmNkZWYwMTIzNDU2Nzg5YWJjZGVmMDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3ODlhYmNkZWYwMTIzNDU2Nzg5YWJjZGVmMDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3ODlhYmNkZWYwMTIzNDU2Nzg5YWJjZGVmMDEyMzQ1Njc4OWFiY2RlZoCAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgAABAgMEBQYHCAmAgICAgICACgsMDQ4PgICAgICAgICAgICAgICAgICAgICAgICAgIAKCwwNDg+AgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAHAAAAAAAAJwgAQACAgAAMDEyMzQ1Njc4OUFCQ0RFRjAxMjM0NTY3ODlBQkNERUYwMTIzNDU2Nzg5QUJDREVGMDEyMzQ1Njc4OUFCQ0RFRjAxMjM0NTY3ODlBQkNERUYwMTIzNDU2Nzg5QUJDREVGMDEyMzQ1Njc4OUFCQ0RFRjAxMjM0NTY3ODlBQkNERUYwMTIzNDU2Nzg5QUJDREVGMDEyMzQ1Njc4OUFCQ0RFRjAxMjM0NTY3ODlBQkNERUYwMTIzNDU2Nzg5QUJDREVGMDEyMzQ1Njc4OUFCQ0RFRjAxMjM0NTY3ODlBQkNERUYwMTIzNDU2Nzg5QUJDREVGMDEyMzQ1Njc4OUFCQ0RFRoCAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgAABAgMEBQYHCAmAgICAgICACgsMDQ4PgICAgICAgICAgICAgICAgICAgICAgICAgIAKCwwNDg+AgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAHAAAAAAAAKwiAQACAgAAYWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXoyMzQ1NjdhYmNkZWZnaGlqa2xtbm9wcXJzdHV2d3h5ejIzNDU2N2FiY2RlZmdoaWprbG1ub3BxcnN0dXZ3eHl6MjM0NTY3YWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXoyMzQ1NjdhYmNkZWZnaGlqa2xtbm9wcXJzdHV2d3h5ejIzNDU2N2FiY2RlZmdoaWprbG1ub3BxcnN0dXZ3eHl6MjM0NTY3YWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXoyMzQ1NjdhYmNkZWZnaGlqa2xtbm9wcXJzdHV2d3h5ejIzNDU2N4CAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAGhscHR4fgICAgICAgICAAAECAwQFBgcICQoLDA0ODxAREhMUFRYXGBmAgICAgIAAAQIDBAUGBwgJCgsMDQ4PEBESExQVFhcYGYCAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAHQAAAAAAALwkAQACAgAAQUJDREVGR0hJSktMTU5PUFFSU1RVVldYWVoyMzQ1NjdBQkNERUZHSElKS0xNTk9QUVJTVFVWV1hZWjIzNDU2N0FCQ0RFRkdISUpLTE1OT1BRUlNUVVZXWFlaMjM0NTY3QUJDREVGR0hJSktMTU5PUFFSU1RVVldYWVoyMzQ1NjdBQkNERUZHSElKS0xNTk9QUVJTVFVWV1hZWjIzNDU2N0FCQ0RFRkdISUpLTE1OT1BRUlNUVVZXWFlaMjM0NTY3QUJDREVGR0hJSktMTU5PUFFSU1RVVldYWVoyMzQ1NjdBQkNERUZHSElKS0xNTk9QUVJTVFVWV1hZWjIzNDU2N4CAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAGhscHR4fgICAgICAgICAAAECAwQFBgcICQoLDA0ODxAREhMUFRYXGBmAgICAgIAAAQIDBAUGBwgJCgsMDQ4PEBESExQVFhcYGYCAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAHQAAAAAAAMwmAQACAgAAMDEyMzQ1Njc4OWFiY2RlZmdoaWprbG1ub3BxcnN0dXZ3eHl6MDEyMzQ1Njc4OUFCQ0RFRkdISUpLTE1OT1BRUlNUVVZXWFlaMTIzNDU2Nzg5YWJjZGVmZ2hpamttbm9wcXJzdHV2d3h5ekFCQ0RFRkdISktMTU5QUVJTVFVWV1hZWkFCQ0RFRkdISUpLTE1OT1BRUlNUVVZXWFlaYWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXowMTIzNDU2Nzg5LV9BQkNERUZHSElKS0xNTk9QUVJTVFVWV1hZWmFiY2RlZmdoaWprbG1ub3BxcnN0dXZ3eHl6MDEyMzQ1Njc4OS1fQUJDREVGR0hJSktMTU5PUFFSU1RVVldYWVphYmNkZWZnaGlqa2xtbm9wcXJzdHV2d3h5ejAxMjM0NTY3ODktX0FCQ0RFRkdISUpLTE1OT1BRUlNUVVZXWFlaYWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXowMTIzNDU2Nzg5LV+AgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIA+gIA0NTY3ODk6Ozw9gICAgoCAgAABAgMEBQYHCAkKCwwNDg8QERITFBUWFxgZgICAgD+AGhscHR4fICEiIyQlJicoKSorLC0uLzAxMjOAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAPR4AAAAAXikBAAICAAAwMTIzNDU2Nzg5YWJjZGVmZ2hpamtsbW5vcHFyc3R1djAxMjM0NTY3ODlhYmNkZWZnaGlqa2xtbm9wcXJzdHV2MDEyMzQ1Njc4OWFiY2RlZmdoaWprbG1ub3BxcnN0dXYwMTIzNDU2Nzg5YWJjZGVmZ2hpamtsbW5vcHFyc3R1djAxMjM0NTY3ODlhYmNkZWZnaGlqa2xtbm9wcXJzdHV2MDEyMzQ1Njc4OWFiY2RlZmdoaWprbG1ub3BxcnN0dXYwMTIzNDU2Nzg5YWJjZGVmZ2hpamtsbW5vcHFyc3R1djAxMjM0NTY3ODlhYmNkZWZnaGlqa2xtbm9wcXJzdHV2gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAAAECAwQFBgcICYCAgICAgIAKCwwNDg8QERITFBUWFxgZGhscHR4fgICAgICAgICAgAoLDA0ODxAREhMUFRYXGBkaGxwdHh+AgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIAdAAAAAAAAbCsBAAICAAAwMTIzNDU2Nzg5QUJDREVGR0hJSktMTU5PUFFSU1RVVjAxMjM0NTY3ODlBQkNERUZHSElKS0xNTk9QUVJTVFVWMDEyMzQ1Njc4OUFCQ0RFRkdISUpLTE1OT1BRUlNUVVYwMTIzNDU2Nzg5QUJDREVGR0hJSktMTU5PUFFSU1RVVjAxMjM0NTY3ODlBQkNERUZHSElKS0xNTk9QUVJTVFVWMDEyMzQ1Njc4OUFCQ0RFRkdISUpLTE1OT1BRUlNUVVYwMTIzNDU2Nzg5QUJDREVGR0hJSktMTU5PUFFSU1RVVjAxMjM0NTY3ODlBQkNERUZHSElKS0xNTk9QUVJTVFVWgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAAAECAwQFBgcICYCAgICAgIAKCwwNDg8QERITFBUWFxgZGhscHR4fgICAgICAgICAgAoLDA0ODxAREhMUFRYXGBkaGxwdHh+AgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIAdAAAAAAAAfC0BAAICAABhYmNkZWZnaGlqa2xtbm9wcXJzdHV2d3h5ejIzNDU2N2FiY2RlZmdoaWprbG1ub3BxcnN0dXZ3eHl6MjM0NTY3YWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXoyMzQ1NjdhYmNkZWZnaGlqa2xtbm9wcXJzdHV2d3h5ejIzNDU2N2FiY2RlZmdoaWprbG1ub3BxcnN0dXZ3eHl6MjM0NTY3YWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXoyMzQ1NjdhYmNkZWZnaGlqa2xtbm9wcXJzdHV2d3h5ejIzNDU2N2FiY2RlZmdoaWprbG1ub3BxcnN0dXZ3eHl6MjM0NTY3gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIAaGxwdHh+AgICAgIKAgIAAAQIDBAUGBwgJCgsMDQ4PEBESExQVFhcYGYCAgICAgAABAgMEBQYHCAkKCwwNDg8QERITFBUWFxgZgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgD0dAAAAAAAAjC8BAAICAABBQkNERUZHSElKS0xNTk9QUVJTVFVWV1hZWjIzNDU2N0FCQ0RFRkdISUpLTE1OT1BRUlNUVVZXWFlaMjM0NTY3QUJDREVGR0hJSktMTU5PUFFSU1RVVldYWVoyMzQ1NjdBQkNERUZHSElKS0xNTk9QUVJTVFVWV1hZWjIzNDU2N0FCQ0RFRkdISUpLTE1OT1BRUlNUVVZXWFlaMjM0NTY3QUJDREVGR0hJSktMTU5PUFFSU1RVVldYWVoyMzQ1NjdBQkNERUZHSElKS0xNTk9QUVJTVFVWV1hZWjIzNDU2N0FCQ0RFRkdISUpLTE1OT1BRUlNUVVZXWFlaMjM0NTY3gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIAaGxwdHh+AgICAgIKAgIAAAQIDBAUGBwgJCgsMDQ4PEBESExQVFhcYGYCAgICAgAABAgMEBQYHCAkKCwwNDg8QERITFBUWFxgZgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgD0dAAAAAAAAnDEBAAICAAAwMTIzNDU2Nzg5YWJjZGVmZ2hpamtsbW5vcHFyc3R1djAxMjM0NTY3ODlhYmNkZWZnaGlqa2xtbm9wcXJzdHV2MDEyMzQ1Njc4OWFiY2RlZmdoaWprbG1ub3BxcnN0dXYwMTIzNDU2Nzg5YWJjZGVmZ2hpamtsbW5vcHFyc3R1djAxMjM0NTY3ODlhYmNkZWZnaGlqa2xtbm9wcXJzdHV2MDEyMzQ1Njc4OWFiY2RlZmdoaWprbG1ub3BxcnN0dXYwMTIzNDU2Nzg5YWJjZGVmZ2hpamtsbW5vcHFyc3R1djAxMjM0NTY3ODlhYmNkZWZnaGlqa2xtbm9wcXJzdHV2gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAAAECAwQFBgcICYCAgIKAgIAKCwwNDg8QERITFBUWFxgZGhscHR4fgICAgICAgICAgAoLDA0ODxAREhMUFRYXGBkaGxwdHh+AgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgD0dAAAAAAAArDMBAAICAAAwMTIzNDU2Nzg5QUJDREVGR0hJSktMTU5PUFFSU1RVVjAxMjM0NTY3ODlBQkNERUZHSElKS0xNTk9QUVJTVFVWMDEyMzQ1Njc4OUFCQ0RFRkdISUpLTE1OT1BRUlNUVVYwMTIzNDU2Nzg5QUJDREVGR0hJSktMTU5PUFFSU1RVVjAxMjM0NTY3ODlBQkNERUZHSElKS0xNTk9QUVJTVFVWMDEyMzQ1Njc4OUFCQ0RFRkdISUpLTE1OT1BRUlNUVVYwMTIzNDU2Nzg5QUJDREVGR0hJSktMTU5PUFFSU1RVVjAxMjM0NTY3ODlBQkNERUZHSElKS0xNTk9QUVJTVFVWgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAAAECAwQFBgcICYCAgIKAgIAKCwwNDg8QERITFBUWFxgZGhscHR4fgICAgICAgICAgAoLDA0ODxAREhMUFRYXGBkaGxwdHh+AgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgD0dAAAAAAAAvDUBAAICAAATAAAADAAAAAQAAAAUAAAAFQAAABYAAAAXAAAAAAAAAAEAAAAYAAAAKQAAABAAAAAEAAAAKgAAACkAAAAQAAAABAAAACsAAAAvdXNyL2xvY2FsL2NhcmdvL3JlZ2lzdHJ5L3NyYy9naXRodWIuY29tLTFlY2M2Mjk5ZGI5ZWM4MjMvYmFzZS14LTAuMi4xMS9zcmMvZGVjb2Rlci5ycwAAFDgBAFYAAAAoAAAAFgAAAHNyYy93cmFwL21vZHVsZS93cmFwcGVkLnJzAAB8OAEAGgAAABcAAAAtAAAAfDgBABoAAAAjAAAADQAAAHw4AQAaAAAAIAAAADcAAAB8OAEAGgAAAC0AAAAtAAAAfDgBABoAAAA4AAAADQAAAHw4AQAaAAAANQAAADAAAABzcmMvdXRpbC9leGVjX2NhdC5yc/g4AQAUAAAAHwAAAAwAAAD4OAEAFAAAACYAAABIAAAAUmVjZWl2ZWQgZW1wdHkgcmVzdWx0IGZyb20gY29uY3VycmVudCB0YXNrbWV0aG9kYXJnc0lwZnMgdXJpIHJlc29sdmVyIHJlcXVpcmVzIGEgY29uZmlndXJlZCBFbnZzcmMvbGliLnJzAAAAizkBAAoAAAAIAAAAEwAAAEludmFsaWQgQ0lEOiAAAACoOQEADQAAAIs5AQAKAAAADwAAAAkAAAAvd3JhcC5pbmZvAABUUQEAAAAAANA5AQAKAAAAizkBAAoAAAAdAAAAEwAAAEZhaWxlZCB0byByZXNvbHZlIElQRlMgVVJJIHdpdGggZXJyb3I6IAD8OQEAJwAAAIs5AQAKAAAAMwAAABUAAAB0YXNrSWRpMzJzdGF0dXNDb25jdXJyZW50VGFza1N0YXR1c3Rhc2tJZDogSW50LnN0YXR1czogQ29uY3VycmVudF9UYXNrU3RhdHVzLlNlcmlhbGl6aW5nIChlbmNvZGluZykgaW1wb3J0ZWQgbW9kdWxlLXR5cGU6IGNhdCBBcmdzY2lkaXBmc1Byb3ZpZGVyY2F0T3B0aW9uc09wdGlvbjxDbGllbnRDYXRPcHRpb25zPkRlc2VyaWFsaXppbmcgaW1wb3J0ZWQgbW9kdWxlLXR5cGU6IGNhdCBSZXN1bHRWZWM8dTg+RGVzZXJpYWxpemluZyBlbnYtdHlwZTogRW52cmV0cmllc09wdGlvbjxSZXRyaWVzPnR5cGUgZm91bmQsIHJlYWRpbmcgcHJvcGVydHl0aW1lb3V0T3B0aW9uPHUzMj5mYWxsYmFja1Byb3ZpZGVyc09wdGlvbjxWZWM8U3RyaW5nPj5kaXNhYmxlUGFyYWxsZWxSZXF1ZXN0c09wdGlvbjxib29sPnByb3ZpZGVyOiBTdHJpbmcuABMAAAAMAAAABAAAABQAAAAVAAAAFgAAABcAAAAAAAAAAQAAABgAAABzcmMvdXRpbC9leGVjLnJzUGFyYWxsZWwgZXhlY3V0aW9uIGlzIG5vdCBhdmFpbGFibGUuIEV4ZWN1dGluZyBzZXF1ZW50aWFsbHkgaW5zdGVhZC4gUGFyYWxsZWwgZXhlY3V0aW9uIHJlcXVpcmVzIGFuIGltcGxlbWVudGF0aW9uIG9mIHRoZSBDb25jdXJyZW50IGludGVyZmFjZS4gWW91IGNhbiBkZWNsYXJlIGFuIGludGVyZmFjZSBpbXBsZW1lbnRhdGlvbiBpbiB5b3VyIFBvbHl3cmFwIENsaWVudCBjb25maWd1cmF0aW9uLgoAFDwBAOMAAAAEPAEAEAAAAEcAAAAmAAAAQW4gZXJyb3Igb2NjdXJyZWQKT3BlcmF0aW9uOiBjYXQKUHJvdmlkZXI6IApUaW1lb3V0OiAKRXJyb3I6IAAAABA9AQArAAAAOz0BAAoAAABFPQEACAAAAEV4ZWN1dGlvbiByZXF1aXJlcyBhbiBpbXBsZW1lbnRhdGlvbiBvZiB0aGUgSVBGUyBIVFRQIENsaWVudCBpbnRlcmZhY2UuIFlvdSBjYW4gZGVjbGFyZSBhbiBpbnRlcmZhY2UgaW1wbGVtZW50YXRpb24gaW4geW91ciBQb2x5d3JhcCBDbGllbnQgY29uZmlndXJhdGlvbi4AAGg9AQCaAAAABDwBABAAAABYAAAACQAAAERlc2VyaWFsaXppbmcgbW9kdWxlLXR5cGU6IHRyeV9yZXNvbHZlX3VyaSBBcmdzYXV0aG9yaXR5U3RyaW5ndHlwZSBmb3VuZCwgcmVhZGluZyBhcmd1bWVudGF1dGhvcml0eTogU3RyaW5nLnBhdGg6IFN0cmluZy5TZXJpYWxpemluZyAoZW5jb2RpbmcpIG1vZHVsZS10eXBlOiB0cnlfcmVzb2x2ZV91cmkgUmVzdWx0dHJ5UmVzb2x2ZVVyaU9wdGlvbjxVcmlSZXNvbHZlck1heWJlVXJpT3JNYW5pZmVzdD53cml0aW5nIHJlc3VsdERlc2VyaWFsaXppbmcgbW9kdWxlLXR5cGU6IGdldF9maWxlIEFyZ3NTZXJpYWxpemluZyAoZW5jb2RpbmcpIG1vZHVsZS10eXBlOiBnZXRfZmlsZSBSZXN1bHRnZXRGaWxlL3Vzci9sb2NhbC9jYXJnby9yZWdpc3RyeS9zcmMvZ2l0aHViLmNvbS0xZWNjNjI5OWRiOWVjODIzL2NpZC0wLjguNi9zcmMvY2lkLnJzABIAAAAAAAAAIAAAAAAAAAAvcnVzdGMvOTA3NDNlNzI5OGFjYTEwN2RkYWEwYzIwMmE0ZDM2MDRlMjliZmViNi9saWJyYXJ5L2NvcmUvc3JjL3N0ci9wYXR0ZXJuLnJzANA/AQBPAAAAjAUAACEAAADQPwEATwAAAJgFAAAUAAAA0D8BAE8AAACYBQAAIQAAAHE/AQBOAAAALgEAAB0AAAB1cmlPcHRpb248U3RyaW5nPm1hbmlmZXN0T3B0aW9uPFZlYzx1OD4+b2Zmc2V0T3B0aW9uPGkzMj5sZW5ndGgAEwAAAAwAAAAEAAAAFAAAABUAAAAWAAAAFwAAAAAAAAABAAAAGAAAAGNhdC91c3IvbG9jYWwvY2FyZ28vcmVnaXN0cnkvc3JjL2dpdGh1Yi5jb20tMWVjYzYyOTlkYjllYzgyMy91bnNpZ25lZC12YXJpbnQtMC43LjEvc3JjL2RlY29kZS5yc8tAAQBdAAAAewAAAAUAAAATAAAADAAAAAQAAAAUAAAAFQAAABYAAAAXAAAAAAAAAAEAAAAYAAAASW52YWxpZCB2YWx1ZSBmb3IgZW51bSAnQ29uY3VycmVudFRhc2tTdGF0dXMnOiAAYEEBAC8AAABQRU5ESU5HUlVOTklOR0NPTVBMRVRFRENBTkNFTExFREZBSUxFRF9NQVhfSW52YWxpZCBrZXkgZm9yIGVudW0gJ0NvbmN1cnJlbnRUYXNrU3RhdHVzJzogw0EBAC0AAABTZXJpYWxpemluZyAoZW5jb2RpbmcpIGltcG9ydGVkIG1vZHVsZS10eXBlOiByZXN1bHQgQXJnc3Rhc2tJZHNWZWM8aTMyPndyaXRpbmcgcHJvcGVydHlyZXR1cm5XaGVuQ29uY3VycmVudFJldHVybldoZW5EZXNlcmlhbGl6aW5nIGltcG9ydGVkIG1vZHVsZS10eXBlOiByZXN1bHQgUmVzdWx0cmVzdWx0VmVjPENvbmN1cnJlbnRUYXNrUmVzdWx0PnJlYWRpbmcgZnVuY3Rpb24gb3V0cHV0U2VyaWFsaXppbmcgKGVuY29kaW5nKSBpbXBvcnRlZCBtb2R1bGUtdHlwZTogc2NoZWR1bGUgQXJnc3Rhc2tzVmVjPENvbmN1cnJlbnRUYXNrPkRlc2VyaWFsaXppbmcgaW1wb3J0ZWQgbW9kdWxlLXR5cGU6IHNjaGVkdWxlIFJlc3VsdHNjaGVkdWxlAAAAEwAAAAwAAAAEAAAALAAAAC0AAAAWAAAAFwAAAAAAAAABAAAAGAAAABMAAAAMAAAABAAAAC4AAABGYWlsZWQgdG8gY3JlYXRlIG5ldyBkYXRhIHZpZXcvdXNyL2xvY2FsL2NhcmdvL3JlZ2lzdHJ5L3NyYy9naXRodWIuY29tLTFlY2M2Mjk5ZGI5ZWM4MjMvcG9seXdyYXAtd2FzbS1ycy0wLjEwLjAtcHJlLjEzL3NyYy9tc2dwYWNrL3JlYWRfZGVjb2Rlci5ycwAAukMBAHQAAAAUAAAALwAAAFByb3BlcnR5IG11c3QgYmUgb2YgdHlwZSAnaW50Jy4gQEQBACAAAABpbnRlZ2VyIG92ZXJmbG93OiB2YWx1ZSA9IDsgYml0cyA9IDY0AAAAaEQBABoAAACCRAEACwAAAHVuc2lnbmVkIGludGVnZXIgY2Fubm90IGJlIG5lZ2F0aXZlLiAAAACgRAEAJQAAAFByb3BlcnR5IG11c3QgYmUgb2YgdHlwZSAndWludCcuIAAAANBEAQAhAAAAUHJvcGVydHkgbXVzdCBiZSBvZiB0eXBlICdib29sJy4gAAAA/EQBACEAAAA7IGJpdHMgPSAzMgBoRAEAGgAAAChFAQALAAAAdW5zaWduZWQgaW50ZWdlciBvdmVyZmxvdzogdmFsdWUgPSAAREUBACMAAAAoRQEACwAAAFByb3BlcnR5IG11c3QgYmUgb2YgdHlwZSAnc3RyaW5nJy4gAHhFAQAjAAAAUHJvcGVydHkgbXVzdCBiZSBvZiB0eXBlICdieXRlcycuIAAApEUBACIAAABQcm9wZXJ0eSBtdXN0IGJlIG9mIHR5cGUgJ2FycmF5Jy4gAADQRQEAIgAAAGFycmF5W11Qcm9wZXJ0eSBtdXN0IGJlIG9mIHR5cGUgJ21hcCcuIAADRgEAIAAAABMAAAAMAAAABAAAACwAAAAtAAAAFgAAABcAAAAAAAAAAQAAABgAAABGb3VuZCAnRklYRVhUMTYnLkZvdW5kICdGSVhFWFQ4Jy5Gb3VuZCAnRklYRVhUNCcuRm91bmQgJ0ZJWEVYVDInLkZvdW5kICdGSVhFWFQxJy5Gb3VuZCAnaW50NjQnLkZvdW5kICdpbnQzMicuRm91bmQgJ2ludDE2Jy5Gb3VuZCAnaW50OCcuRm91bmQgJ3VpbnQ2NCcuRm91bmQgJ3VpbnQzMicuRm91bmQgJ3VpbnQxNicuRm91bmQgJ3VpbnQ4Jy5Gb3VuZCAnZmxvYXQ2NCcuRm91bmQgJ2Zsb2F0MzInLkZvdW5kICdFWFQzMicuRm91bmQgJ0VYVDE2Jy5Gb3VuZCAnRVhUOCcuRm91bmQgJ0JJTjMyJy5Gb3VuZCAnQklOMTYnLkZvdW5kICdCSU44Jy5Gb3VuZCAnYm9vbCcuRm91bmQgJ3Jlc2VydmVkJy5Gb3VuZCAnbmlsJy5Gb3VuZCAnc3RyaW5nJy5Gb3VuZCAnYXJyYXknLkZvdW5kICdtYXAnLkZvdW5kICdpbnQnLklPRXJyb3IAFwAAAAQAAAAEAAAALwAAAFR5cGVXcml0ZUVycm9yU3RyV3JpdGVFcnJvckludDMyV3JpdGVFcnJvckludDE2V3JpdGVFcnJvckludDhXcml0ZUVycm9yVWludDMyV3JpdGVFcnJvclVpbnQxNldyaXRlRXJyb3JVaW50OFdyaXRlRXJyb3JGbG9hdDY0V3JpdGVFcnJvckZsb2F0MzJXcml0ZUVycm9ySlNPTldyaXRlRXJyb3JCaWdJbnRXcml0ZUVycm9yQmluV3JpdGVFcnJvckJvb2xlYW5Xcml0ZUVycm9yRm9ybWF0V3JpdGVFcnJvck5pbFdyaXRlRXJyb3JUeXBlUmVhZEVycm9yTWlzc2luZ0ZpZWxkV3JvbmdNc2dQYWNrRm9ybWF0VW5rbm93bkZpZWxkTmFtZUVudW1SZWFkRXJyb3JTdHJSZWFkRXJyb3JFeHRHZW5lcmljTWFwUmVhZEVycm9yTWFwUmVhZEVycm9yQXJyYXlSZWFkRXJyb3JJbnRSYW5nZUVycm9ySlNPTlJlYWRFcnJvckJpZ051bWJlclJlYWRFcnJvckJpZ0ludFJlYWRFcnJvckZsb2F0UmVhZEVycm9yVWludFJlYWRFcnJvckludFJlYWRFcnJvclBhcnNlQmlnTnVtYmVyRXJyb3JQYXJzZUJpZ0ludEVycm9yQnl0ZXNSZWFkRXJyb3JCb29sZWFuUmVhZEVycm9yRm91bmROaWxCdXRFeHBlY3RlZE1pc3NpbmcgcmVxdWlyZWQgZmllbGQ6ICcnAAAAK0oBABkAAABESgEAAQAAAFVua25vd25GaWVsZE5hbWU6ICcAWEoBABMAAABESgEAAQAAAEZvdW5kIE5JTCwgYnV0IGV4cGVjdGVkOiAnAAB8SgEAGgAAAERKAQABAAAAKQAAABAAAAAEAAAAKgAAAF9fd3JhcF9nZXRJbXBsZW1lbnRhdGlvbnNfcmVzdWx0VmVjPFN0cmluZz5fX3dyYXBfZ2V0SW1wbGVtZW50YXRpb25zIHN1Y2Nlc3NmdWwvdXNyL2xvY2FsL2NhcmdvL3JlZ2lzdHJ5L3NyYy9naXRodWIuY29tLTFlY2M2Mjk5ZGI5ZWM4MjMvcG9seXdyYXAtd2FzbS1ycy0wLjEwLjAtcHJlLjEzL3NyYy9nZXRfaW1wbGVtZW50YXRpb25zLnJzAAAHSwEAcwAAACUAAAA3AAAAdW5rbm93biBlcnJvckNvdWxkIG5vdCBmaW5kIGludm9rZSBmdW5jdGlvbiCZSwEAHwAAABMAAAAMAAAABAAAACwAAAAtAAAAFgAAAGEgRGlzcGxheSBpbXBsZW1lbnRhdGlvbiByZXR1cm5lZCBhbiBlcnJvciB1bmV4cGVjdGVkbHkAFwAAAAAAAAABAAAAGAAAAC9ydXN0Yy85MDc0M2U3Mjk4YWNhMTA3ZGRhYTBjMjAyYTRkMzYwNGUyOWJmZWI2L2xpYnJhcnkvYWxsb2Mvc3JjL3N0cmluZy5ycwAgTAEASwAAAOgJAAAJAAAAL3J1c3RjLzkwNzQzZTcyOThhY2ExMDdkZGFhMGMyMDJhNGQzNjA0ZTI5YmZlYjYvbGlicmFyeS9zdGQvc3JjL2lvL21vZC5ycwAAAHxMAQBJAAAAxwEAABwAAABmYWlsZWQgdG8gZmlsbCB3aG9sZSBidWZmZXIA2EwBABsAAAAlAAAAfEwBAEkAAACHAQAAGwAAAHxMAQBJAAAAlgEAADAAAAAvcnVzdGMvOTA3NDNlNzI5OGFjYTEwN2RkYWEwYzIwMmE0ZDM2MDRlMjliZmViNi9saWJyYXJ5L3N0ZC9zcmMvaW8vcmVhZGJ1Zi5ycwAAACBNAQBNAAAA/QAAABYAAAAgTQEATQAAANMAAAA1AAAAIE0BAE0AAADLAAAANgAAAG51bWJlciBvZiByZWFkIGJ5dGVzIGV4Y2VlZHMgbGltaXQAAKBNAQAiAAAAfEwBAEkAAAAeCgAACQAAAHxMAQBJAAAAMAoAACYAAABhdHRlbXB0IHRvIGpvaW4gaW50byBjb2xsZWN0aW9uIHdpdGggbGVuID4gdXNpemU6Ok1BWC9ydXN0Yy85MDc0M2U3Mjk4YWNhMTA3ZGRhYTBjMjAyYTRkMzYwNGUyOWJmZWI2L2xpYnJhcnkvYWxsb2Mvc3JjL3N0ci5ycwAAACFOAQBIAAAAsAAAABYAAAAhTgEASAAAAJQAAAAYAAAAY29udGV4dCBkZXNjcmlwdGlvbiBub3Qgc2V0RXJyb3I6IHRyaWVkIHRvIHBvcCBhbiBpdGVtIGZyb20gYW4gZW1wdHkgQ29udGV4dCBzdGFjawAAp04BADcAAAAvdXNyL2xvY2FsL2NhcmdvL3JlZ2lzdHJ5L3NyYy9naXRodWIuY29tLTFlY2M2Mjk5ZGI5ZWM4MjMvcG9seXdyYXAtd2FzbS1ycy0wLjEwLjAtcHJlLjEzL3NyYy9kZWJ1Zy9jb250ZXh0LnJzAAAA6E4BAG0AAAArAAAADQAAAOhOAQBtAAAALQAAACUAAAAgPj4geE8BAAQAAABUUQEAAAAAAB9WAQACAAAAVFEBAAAAAAAKIAAAnU8BAAEAAAAAAAAAIAAAAAAAAAACAAAAAAAAAAEAAAABAAAAAwAAAJxPAQABAAAAQ29udGV4dDogY29udGV4dCBzdGFjayBpcyBlbXB0eWF0ICA6IAAAAO9PAQADAAAA8k8BAAMAAAB4TwEABAAAAC9ydXN0Yy85MDc0M2U3Mjk4YWNhMTA3ZGRhYTBjMjAyYTRkMzYwNGUyOWJmZWI2L2xpYnJhcnkvc3RkL3NyYy9pby9pbXBscy5ycwAQUAEASwAAAPIAAAANAAAAL3J1c3RjLzkwNzQzZTcyOThhY2ExMDdkZGFhMGMyMDJhNGQzNjA0ZTI5YmZlYjYvbGlicmFyeS9zdGQvc3JjL2lvL2N1cnNvci5yc2xQAQBMAAAA6wAAAAoAAABjdXJzb3IgcG9zaXRpb24gZXhjZWVkcyBtYXhpbXVtIHBvc3NpYmxlIHZlY3RvciBsZW5ndGgAAMhQAQA2AAAAFAAAABcAAAAEAAAABAAAADAAAAAxAAAAMgAAABkAAAAEAAAABAAAADMAAAA0AAAANQAAABkAAAAEAAAABAAAADYAAAA3AAAAOAAAAGFscmVhZHkgYm9ycm93ZWQZAAAAAAAAAAEAAAA5AAAAAGFzc2VydGlvbiBmYWlsZWQ6IG1pZCA8PSBzZWxmLmxlbigpGQAAAAQAAAAEAAAAOgAAABkAAAAEAAAABAAAADsAAABjYWxsZWQgYE9wdGlvbjo6dW53cmFwKClgIG9uIGEgYE5vbmVgIHZhbHVlY2FsbGVkIGBSZXN1bHQ6OnVud3JhcCgpYCBvbiBhbiBgRXJyYCB2YWx1ZWxpYnJhcnkvc3RkL3NyYy90aHJlYWQvbW9kLnJzZmFpbGVkIHRvIGdlbmVyYXRlIHVuaXF1ZSB0aHJlYWQgSUQ6IGJpdHNwYWNlIGV4aGF1c3RlZAAAK1IBADcAAAAOUgEAHQAAAFYEAAANAAAAVFEBAAAAAABsaWJyYXJ5L3N0ZC9zcmMvaW8vYnVmZmVyZWQvbGluZXdyaXRlcnNoaW0ucnMAAACEUgEALQAAAAEBAAApAAAAdW5jYXRlZ29yaXplZCBlcnJvcm90aGVyIGVycm9yb3V0IG9mIG1lbW9yeXVuZXhwZWN0ZWQgZW5kIG9mIGZpbGV1bnN1cHBvcnRlZG9wZXJhdGlvbiBpbnRlcnJ1cHRlZGFyZ3VtZW50IGxpc3QgdG9vIGxvbmdpbnZhbGlkIGZpbGVuYW1ldG9vIG1hbnkgbGlua3Njcm9zcy1kZXZpY2UgbGluayBvciByZW5hbWVkZWFkbG9ja2V4ZWN1dGFibGUgZmlsZSBidXN5cmVzb3VyY2UgYnVzeWZpbGUgdG9vIGxhcmdlZmlsZXN5c3RlbSBxdW90YSBleGNlZWRlZHNlZWsgb24gdW5zZWVrYWJsZSBmaWxlbm8gc3RvcmFnZSBzcGFjZXdyaXRlIHplcm90aW1lZCBvdXRpbnZhbGlkIGRhdGFpbnZhbGlkIGlucHV0IHBhcmFtZXRlcnN0YWxlIG5ldHdvcmsgZmlsZSBoYW5kbGVmaWxlc3lzdGVtIGxvb3Agb3IgaW5kaXJlY3Rpb24gbGltaXQgKGUuZy4gc3ltbGluayBsb29wKXJlYWQtb25seSBmaWxlc3lzdGVtIG9yIHN0b3JhZ2UgbWVkaXVtZGlyZWN0b3J5IG5vdCBlbXB0eWlzIGEgZGlyZWN0b3J5bm90IGEgZGlyZWN0b3J5b3BlcmF0aW9uIHdvdWxkIGJsb2NrZW50aXR5IGFscmVhZHkgZXhpc3RzYnJva2VuIHBpcGVuZXR3b3JrIGRvd25hZGRyZXNzIG5vdCBhdmFpbGFibGVhZGRyZXNzIGluIHVzZW5vdCBjb25uZWN0ZWRjb25uZWN0aW9uIGFib3J0ZWRuZXR3b3JrIHVucmVhY2hhYmxlaG9zdCB1bnJlYWNoYWJsZWNvbm5lY3Rpb24gcmVzZXRjb25uZWN0aW9uIHJlZnVzZWRwZXJtaXNzaW9uIGRlbmllZGVudGl0eSBub3QgZm91bmRFcnJvcmtpbmQgKG9zIGVycm9yICkAAFRRAQAAAAAAulUBAAsAAADFVQEAAQAAAGxpYnJhcnkvc3RkL3NyYy9pby9zdGRpby5ycwDgVQEAGwAAAOACAAAUAAAAZmFpbGVkIHByaW50aW5nIHRvIDogAAAADFYBABMAAAAfVgEAAgAAAOBVAQAbAAAA8QMAAAkAAABzdGRvdXRmb3JtYXR0ZXIgZXJyb3IAAABKVgEADwAAACgAAAA8AAAADAAAAAQAAAA9AAAAPgAAAD8AAABsaWJyYXJ5L3N0ZC9zcmMvc3luYy9vbmNlLnJzgFYBABwAAADKAAAAFAAAAIBWAQAcAAAAygAAACgAAABQb2lzb25FcnJvcmxvY2sgY291bnQgb3ZlcmZsb3cgaW4gcmVlbnRyYW50IG11dGV4bGlicmFyeS9zdGQvc3JjL3N5c19jb21tb24vcmVtdXRleC5ycwAA7VYBACUAAACPAAAAIgAAAGxpYnJhcnkvc3RkL3NyYy9zeXNfY29tbW9uL3RocmVhZF9pbmZvLnJzAAAAJFcBACkAAAAWAAAAMwAAAGNhbm5vdCBtb2RpZnkgdGhlIHBhbmljIGhvb2sgZnJvbSBhIHBhbmlja2luZyB0aHJlYWRgVwEANAAAAGxpYnJhcnkvc3RkL3NyYy9wYW5pY2tpbmcucnOcVwEAHAAAAIYAAAAJAAAAnFcBABwAAAA+AgAADwAAAEAAAAAMAAAABAAAAEEAAAAZAAAACAAAAAQAAABCAAAAQwAAABAAAAAEAAAARAAAAEUAAAAZAAAACAAAAAQAAABGAAAARwAAAGVycm9yb3BlcmF0aW9uIHN1Y2Nlc3NmdWxjb25kdmFyIHdhaXQgbm90IHN1cHBvcnRlZAA5WAEAGgAAAGxpYnJhcnkvc3RkL3NyYy9zeXMvd2FzbS8uLi91bnN1cHBvcnRlZC9sb2Nrcy9jb25kdmFyLnJzXFgBADgAAAAWAAAACQAAAGNhbm5vdCByZWN1cnNpdmVseSBhY3F1aXJlIG11dGV4pFgBACAAAABsaWJyYXJ5L3N0ZC9zcmMvc3lzL3dhc20vLi4vdW5zdXBwb3J0ZWQvbG9ja3MvbXV0ZXgucnMAAMxYAQA2AAAAFgAAAAkAAABhc3NlcnRpb24gZmFpbGVkOiBzdGF0ZV9hbmRfcXVldWUuYWRkcigpICYgU1RBVEVfTUFTSyA9PSBSVU5OSU5HAgAAAGxpYnJhcnkvc3RkL3NyYy9zeXNfY29tbW9uL29uY2UvZ2VuZXJpYy5ycwAAWFkBACoAAAD4AAAACQAAAFhZAQAqAAAABQEAAB4AAABIAAAACAAAAAQAAABJAAAAbGlicmFyeS9zdGQvc3JjL3N5c19jb21tb24vdGhyZWFkX3Bhcmtlci9nZW5lcmljLnJzALRZAQAzAAAAJwAAABUAAABpbmNvbnNpc3RlbnQgcGFyayBzdGF0ZQD4WQEAFwAAALRZAQAzAAAANQAAABcAAABwYXJrIHN0YXRlIGNoYW5nZWQgdW5leHBlY3RlZGx5AChaAQAfAAAAtFkBADMAAAAyAAAAEQAAAGluY29uc2lzdGVudCBzdGF0ZSBpbiB1bnBhcmtgWgEAHAAAALRZAQAzAAAAbAAAABIAAAC0WQEAMwAAAHoAAAAOAAAADgAAABAAAAAWAAAAFQAAAAsAAAAWAAAADQAAAAsAAAATAAAAEAAAABAAAAAQAAAAEAAAABAAAAAQAAAAEAAAABAAAAAQAAAAEAAAABAAAAAQAAAAEAAAABAAAAAQAAAAEAAAABAAAAAQAAAAEAAAABAAAAAQAAAAEAAAABAAAAAQAAAAEQAAABIAAAAQAAAAEAAAABMAAAASAAAADQAAAA4AAAAVAAAADAAAAAsAAAAVAAAAFQAAAA8AAAAOAAAAEwAAACYAAAA4AAAAGQAAABcAAAAMAAAACQAAAAoAAAAQAAAAFwAAABkAAAAOAAAADQAAABQAAAAIAAAAGwAAAEtTAQA7UwEAJVMBABBTAQAFUwEA71IBAOJSAQDXUgEAxFIBAKFVAQChVQEAoVUBAKFVAQChVQEAoVUBAKFVAQChVQEAoVUBAKFVAQChVQEAoVUBAKFVAQChVQEAoVUBAKFVAQChVQEAoVUBAKFVAQChVQEAoVUBAKFVAQChVQEAoVUBAJBVAQB+VQEAblUBAF5VAQBLVQEAOVUBACxVAQAeVQEACVUBAP1UAQDyVAEA3VQBAMhUAQC5VAEAq1QBAJhUAQByVAEAOlQBACFUAQAKVAEA/lMBAPVTAQDrUwEA21MBAMRTAQCrUwEAnVMBAJBTAQB8UwEAdFMBAFlTAQAAQai5BQuUBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAfwlwcm9kdWNlcnMCCGxhbmd1YWdlAQRSdXN0AAxwcm9jZXNzZWQtYnkEBXJ1c3RjHTEuNjYuMSAoOTA3NDNlNzI5IDIwMjMtMDEtMTApBndhbHJ1cwYwLjEyLjAMd2FzbS1iaW5kZ2VuBjAuMi44NAl3YXNtLXNuaXAFMC40LjA=" -); - -const wrap_info = toUint8Array( - "hKd2ZXJzaW9uozAuMaRuYW1lumlwZnMtdXJpLXJlc29sdmVyLXJzLWFzeW5jpHR5cGWkd2FzbaNhYmmIp3ZlcnNpb26jMC4xq29iamVjdFR5cGVzkYSkdHlwZadSZXRyaWVzp2NvbW1lbnTZR051bWJlciBvZiB0aW1lcyB0byByZXRyeSByZXF1ZXN0IG9uIGZhaWx1cmUgKGV4Y2x1ZGluZyBpbml0aWFsIHJlcXVlc3QppGtpbmQBqnByb3BlcnRpZXOShKR0eXBlplVJbnQzMqRuYW1lrXRyeVJlc29sdmVVcmmka2luZCKmc2NhbGFyg6RuYW1lrXRyeVJlc29sdmVVcmmkdHlwZaZVSW50MzKka2luZASEpHR5cGWmVUludDMypG5hbWWnZ2V0RmlsZaRraW5kIqZzY2FsYXKDpG5hbWWnZ2V0RmlsZaR0eXBlplVJbnQzMqRraW5kBKptb2R1bGVUeXBlhadpbXBvcnRz3AAQgaR0eXBlslVyaVJlc29sdmVyX01vZHVsZYGkdHlwZb5VcmlSZXNvbHZlcl9NYXliZVVyaU9yTWFuaWZlc3SBpHR5cGWtQ2xpZW50X01vZHVsZYGkdHlwZbFDbGllbnRfQ2F0T3B0aW9uc4GkdHlwZbVDbGllbnRfUmVzb2x2ZU9wdGlvbnOBpHR5cGW0Q2xpZW50X1Jlc29sdmVSZXN1bHSBpHR5cGWwQ2xpZW50X0ZpbGVFbnRyeYGkdHlwZbFDbGllbnRfQWRkT3B0aW9uc4GkdHlwZbBDbGllbnRfQWRkUmVzdWx0gaR0eXBltUNsaWVudF9EaXJlY3RvcnlFbnRyeYGkdHlwZatDbGllbnRfQmxvYoGkdHlwZbFDb25jdXJyZW50X01vZHVsZYGkdHlwZbVDb25jdXJyZW50X1JldHVybldoZW6BpHR5cGW1Q29uY3VycmVudF9UYXNrUmVzdWx0gaR0eXBltUNvbmN1cnJlbnRfVGFza1N0YXR1c4GkdHlwZa9Db25jdXJyZW50X1Rhc2uqaW50ZXJmYWNlc5GCpHR5cGWyVXJpUmVzb2x2ZXJfTW9kdWxlpGtpbmTNCACkdHlwZaZNb2R1bGWka2luZMyAp21ldGhvZHOSh6RuYW1lrXRyeVJlc29sdmVVcmmmcmV0dXJuhKR0eXBlvlVyaVJlc29sdmVyX01heWJlVXJpT3JNYW5pZmVzdKRuYW1lrXRyeVJlc29sdmVVcmmka2luZCKmb2JqZWN0g6RuYW1lrXRyeVJlc29sdmVVcmmkdHlwZb5VcmlSZXNvbHZlcl9NYXliZVVyaU9yTWFuaWZlc3Ska2luZM0gAKR0eXBlpk1ldGhvZKRraW5kQKhyZXF1aXJlZMOjZW52gahyZXF1aXJlZMKpYXJndW1lbnRzkoWkdHlwZaZTdHJpbmekbmFtZalhdXRob3JpdHmocmVxdWlyZWTDpGtpbmQipnNjYWxhcoSkbmFtZalhdXRob3JpdHmkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEhaR0eXBlplN0cmluZ6RuYW1lpHBhdGiocmVxdWlyZWTDpGtpbmQipnNjYWxhcoSkbmFtZaRwYXRopHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBIekbmFtZadnZXRGaWxlpnJldHVyboSkdHlwZaVCeXRlc6RuYW1lp2dldEZpbGWka2luZCKmc2NhbGFyg6RuYW1lp2dldEZpbGWkdHlwZaVCeXRlc6RraW5kBKR0eXBlpk1ldGhvZKRraW5kQKhyZXF1aXJlZMOjZW52gahyZXF1aXJlZMKpYXJndW1lbnRzkYWkdHlwZaZTdHJpbmekbmFtZaRwYXRoqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWkcGF0aKR0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASuaW50ZXJmYWNlVHlwZXOShqR0eXBlqkNvbmN1cnJlbnSjdXJp2SV3cmFwOi8vZW5zL3dyYXBzLmV0aDpjb25jdXJyZW50QDEuMC4wqW5hbWVzcGFjZapDb25jdXJyZW50rGNhcGFiaWxpdGllc4GyZ2V0SW1wbGVtZW50YXRpb25zgadlbmFibGVkw6RraW5kzYAAqm5hdGl2ZVR5cGWpSW50ZXJmYWNlhqR0eXBlpkNsaWVudKN1cmnZK3dyYXA6Ly9lbnMvd3JhcHMuZXRoOmlwZnMtaHR0cC1jbGllbnRAMS4wLjCpbmFtZXNwYWNlpkNsaWVudKxjYXBhYmlsaXRpZXOBsmdldEltcGxlbWVudGF0aW9uc4GnZW5hYmxlZMOka2luZM2AAKpuYXRpdmVUeXBlqUludGVyZmFjZbNpbXBvcnRlZE9iamVjdFR5cGVzm4akdHlwZb5VcmlSZXNvbHZlcl9NYXliZVVyaU9yTWFuaWZlc3SjdXJp2St3cmFwOi8vZW5zL3dyYXBzLmV0aDp1cmktcmVzb2x2ZXItZXh0QDEuMS4wqW5hbWVzcGFjZatVcmlSZXNvbHZlcqpuYXRpdmVUeXBlsk1heWJlVXJpT3JNYW5pZmVzdKRraW5kzQQBqnByb3BlcnRpZXOShaR0eXBlplN0cmluZ6RuYW1lo3Vyaadjb21tZW502T1BIG5ldyBVUkkgdG8gYmUgdXNlZCBmb3IgcmVzb2x2aW5nIHRoZSB3cmFwcGVyIChyZWRpcmVjdGlvbikupGtpbmQipnNjYWxhcoOkbmFtZaN1cmmkdHlwZaZTdHJpbmeka2luZASFpHR5cGWlQnl0ZXOkbmFtZahtYW5pZmVzdKdjb21tZW502SxUaGUgd3JhcHBlcidzIG1hbmlmZXN0LCBpZiBmb3VuZCAoZmluYWxpdHkpLqRraW5kIqZzY2FsYXKDpG5hbWWobWFuaWZlc3SkdHlwZaVCeXRlc6RraW5kBIakdHlwZbFDbGllbnRfQ2F0T3B0aW9uc6N1cmnZK3dyYXA6Ly9lbnMvd3JhcHMuZXRoOmlwZnMtaHR0cC1jbGllbnRAMS4wLjCpbmFtZXNwYWNlpkNsaWVudKpuYXRpdmVUeXBlqkNhdE9wdGlvbnOka2luZM0EAapwcm9wZXJ0aWVzkoSkdHlwZaVJbnQzMqRuYW1lpm9mZnNldKRraW5kIqZzY2FsYXKDpG5hbWWmb2Zmc2V0pHR5cGWlSW50MzKka2luZASEpHR5cGWlSW50MzKkbmFtZaZsZW5ndGika2luZCKmc2NhbGFyg6RuYW1lpmxlbmd0aKR0eXBlpUludDMypGtpbmQEhqR0eXBltUNsaWVudF9SZXNvbHZlT3B0aW9uc6N1cmnZK3dyYXA6Ly9lbnMvd3JhcHMuZXRoOmlwZnMtaHR0cC1jbGllbnRAMS4wLjCpbmFtZXNwYWNlpkNsaWVudKpuYXRpdmVUeXBlrlJlc29sdmVPcHRpb25zpGtpbmTNBAGqcHJvcGVydGllc5OEpHR5cGWnQm9vbGVhbqRuYW1lqXJlY3Vyc2l2ZaRraW5kIqZzY2FsYXKDpG5hbWWpcmVjdXJzaXZlpHR5cGWnQm9vbGVhbqRraW5kBISkdHlwZaVJbnQzMqRuYW1lrmRodFJlY29yZENvdW50pGtpbmQipnNjYWxhcoOkbmFtZa5kaHRSZWNvcmRDb3VudKR0eXBlpUludDMypGtpbmQEhKR0eXBlplN0cmluZ6RuYW1lqmRodFRpbWVvdXSka2luZCKmc2NhbGFyg6RuYW1lqmRodFRpbWVvdXSkdHlwZaZTdHJpbmeka2luZASGpHR5cGW0Q2xpZW50X1Jlc29sdmVSZXN1bHSjdXJp2St3cmFwOi8vZW5zL3dyYXBzLmV0aDppcGZzLWh0dHAtY2xpZW50QDEuMC4wqW5hbWVzcGFjZaZDbGllbnSqbmF0aXZlVHlwZa1SZXNvbHZlUmVzdWx0pGtpbmTNBAGqcHJvcGVydGllc5KFpHR5cGWmU3RyaW5npG5hbWWjY2lkqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWjY2lkpHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBIWkdHlwZaZTdHJpbmekbmFtZahwcm92aWRlcqhyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lqHByb3ZpZGVypHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBIakdHlwZbBDbGllbnRfRmlsZUVudHJ5o3Vyadkrd3JhcDovL2Vucy93cmFwcy5ldGg6aXBmcy1odHRwLWNsaWVudEAxLjAuMKluYW1lc3BhY2WmQ2xpZW50qm5hdGl2ZVR5cGWpRmlsZUVudHJ5pGtpbmTNBAGqcHJvcGVydGllc5KFpHR5cGWmU3RyaW5npG5hbWWkbmFtZahyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lpG5hbWWkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEhaR0eXBlpUJ5dGVzpG5hbWWkZGF0YahyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lpGRhdGGkdHlwZaVCeXRlc6hyZXF1aXJlZMOka2luZASGpHR5cGWxQ2xpZW50X0FkZE9wdGlvbnOjdXJp2St3cmFwOi8vZW5zL3dyYXBzLmV0aDppcGZzLWh0dHAtY2xpZW50QDEuMC4wqW5hbWVzcGFjZaZDbGllbnSqbmF0aXZlVHlwZapBZGRPcHRpb25zpGtpbmTNBAGqcHJvcGVydGllc5OEpHR5cGWnQm9vbGVhbqRuYW1lo3BpbqRraW5kIqZzY2FsYXKDpG5hbWWjcGlupHR5cGWnQm9vbGVhbqRraW5kBISkdHlwZadCb29sZWFupG5hbWWob25seUhhc2ika2luZCKmc2NhbGFyg6RuYW1lqG9ubHlIYXNopHR5cGWnQm9vbGVhbqRraW5kBISkdHlwZadCb29sZWFupG5hbWWxd3JhcFdpdGhEaXJlY3Rvcnmka2luZCKmc2NhbGFyg6RuYW1lsXdyYXBXaXRoRGlyZWN0b3J5pHR5cGWnQm9vbGVhbqRraW5kBIakdHlwZbBDbGllbnRfQWRkUmVzdWx0o3Vyadkrd3JhcDovL2Vucy93cmFwcy5ldGg6aXBmcy1odHRwLWNsaWVudEAxLjAuMKluYW1lc3BhY2WmQ2xpZW50qm5hdGl2ZVR5cGWpQWRkUmVzdWx0pGtpbmTNBAGqcHJvcGVydGllc5OFpHR5cGWmU3RyaW5npG5hbWWkbmFtZahyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lpG5hbWWkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEhaR0eXBlplN0cmluZ6RuYW1lpGhhc2iocmVxdWlyZWTDpGtpbmQipnNjYWxhcoSkbmFtZaRoYXNopHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBIWkdHlwZaZTdHJpbmekbmFtZaRzaXplqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWkc2l6ZaR0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASGpHR5cGW1Q2xpZW50X0RpcmVjdG9yeUVudHJ5o3Vyadkrd3JhcDovL2Vucy93cmFwcy5ldGg6aXBmcy1odHRwLWNsaWVudEAxLjAuMKluYW1lc3BhY2WmQ2xpZW50qm5hdGl2ZVR5cGWuRGlyZWN0b3J5RW50cnmka2luZM0EAapwcm9wZXJ0aWVzk4WkdHlwZaZTdHJpbmekbmFtZaRuYW1lqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWkbmFtZaR0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASEpHR5cGW3W0NsaWVudF9EaXJlY3RvcnlFbnRyeV2kbmFtZatkaXJlY3Rvcmllc6RraW5kIqVhcnJheYWkbmFtZatkaXJlY3Rvcmllc6R0eXBlt1tDbGllbnRfRGlyZWN0b3J5RW50cnldpm9iamVjdISkbmFtZatkaXJlY3Rvcmllc6hyZXF1aXJlZMOkdHlwZbVDbGllbnRfRGlyZWN0b3J5RW50cnmka2luZM0gAKRraW5kEqRpdGVthKRuYW1lq2RpcmVjdG9yaWVzqHJlcXVpcmVkw6R0eXBltUNsaWVudF9EaXJlY3RvcnlFbnRyeaRraW5kzSAAhKR0eXBlsltDbGllbnRfRmlsZUVudHJ5XaRuYW1lpWZpbGVzpGtpbmQipWFycmF5haRuYW1lpWZpbGVzpHR5cGWyW0NsaWVudF9GaWxlRW50cnldpm9iamVjdISkbmFtZaVmaWxlc6hyZXF1aXJlZMOkdHlwZbBDbGllbnRfRmlsZUVudHJ5pGtpbmTNIACka2luZBKkaXRlbYSkbmFtZaVmaWxlc6hyZXF1aXJlZMOkdHlwZbBDbGllbnRfRmlsZUVudHJ5pGtpbmTNIACGpHR5cGWrQ2xpZW50X0Jsb2KjdXJp2St3cmFwOi8vZW5zL3dyYXBzLmV0aDppcGZzLWh0dHAtY2xpZW50QDEuMC4wqW5hbWVzcGFjZaZDbGllbnSqbmF0aXZlVHlwZaRCbG9ipGtpbmTNBAGqcHJvcGVydGllc5KEpHR5cGW3W0NsaWVudF9EaXJlY3RvcnlFbnRyeV2kbmFtZatkaXJlY3Rvcmllc6RraW5kIqVhcnJheYWkbmFtZatkaXJlY3Rvcmllc6R0eXBlt1tDbGllbnRfRGlyZWN0b3J5RW50cnldpm9iamVjdISkbmFtZatkaXJlY3Rvcmllc6hyZXF1aXJlZMOkdHlwZbVDbGllbnRfRGlyZWN0b3J5RW50cnmka2luZM0gAKRraW5kEqRpdGVthKRuYW1lq2RpcmVjdG9yaWVzqHJlcXVpcmVkw6R0eXBltUNsaWVudF9EaXJlY3RvcnlFbnRyeaRraW5kzSAAhKR0eXBlsltDbGllbnRfRmlsZUVudHJ5XaRuYW1lpWZpbGVzpGtpbmQipWFycmF5haRuYW1lpWZpbGVzpHR5cGWyW0NsaWVudF9GaWxlRW50cnldpm9iamVjdISkbmFtZaVmaWxlc6hyZXF1aXJlZMOkdHlwZbBDbGllbnRfRmlsZUVudHJ5pGtpbmTNIACka2luZBKkaXRlbYSkbmFtZaVmaWxlc6hyZXF1aXJlZMOkdHlwZbBDbGllbnRfRmlsZUVudHJ5pGtpbmTNIACGpHR5cGW1Q29uY3VycmVudF9UYXNrUmVzdWx0o3Vyadkld3JhcDovL2Vucy93cmFwcy5ldGg6Y29uY3VycmVudEAxLjAuMKluYW1lc3BhY2WqQ29uY3VycmVudKpuYXRpdmVUeXBlqlRhc2tSZXN1bHSka2luZM0EAapwcm9wZXJ0aWVzlIWkdHlwZaNJbnSkbmFtZaZ0YXNrSWSocmVxdWlyZWTDpGtpbmQipnNjYWxhcoSkbmFtZaZ0YXNrSWSkdHlwZaNJbnSocmVxdWlyZWTDpGtpbmQEhKR0eXBlpUJ5dGVzpG5hbWWmcmVzdWx0pGtpbmQipnNjYWxhcoOkbmFtZaZyZXN1bHSkdHlwZaVCeXRlc6RraW5kBISkdHlwZaZTdHJpbmekbmFtZaVlcnJvcqRraW5kIqZzY2FsYXKDpG5hbWWlZXJyb3KkdHlwZaZTdHJpbmeka2luZASFpHR5cGW1Q29uY3VycmVudF9UYXNrU3RhdHVzpG5hbWWmc3RhdHVzqHJlcXVpcmVkw6RraW5kIqRlbnVthKRuYW1lpnN0YXR1c6hyZXF1aXJlZMOkdHlwZbVDb25jdXJyZW50X1Rhc2tTdGF0dXOka2luZM1AAIakdHlwZa9Db25jdXJyZW50X1Rhc2ujdXJp2SV3cmFwOi8vZW5zL3dyYXBzLmV0aDpjb25jdXJyZW50QDEuMC4wqW5hbWVzcGFjZapDb25jdXJyZW50qm5hdGl2ZVR5cGWkVGFza6RraW5kzQQBqnByb3BlcnRpZXOThaR0eXBlplN0cmluZ6RuYW1lo3VyaahyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lo3VyaaR0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASFpHR5cGWmU3RyaW5npG5hbWWmbWV0aG9kqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWmbWV0aG9kpHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBIWkdHlwZaVCeXRlc6RuYW1lpGFyZ3OocmVxdWlyZWTDpGtpbmQipnNjYWxhcoSkbmFtZaRhcmdzpHR5cGWlQnl0ZXOocmVxdWlyZWTDpGtpbmQEs2ltcG9ydGVkTW9kdWxlVHlwZXOTh6N1cmnZK3dyYXA6Ly9lbnMvd3JhcHMuZXRoOnVyaS1yZXNvbHZlci1leHRAMS4xLjCpbmFtZXNwYWNlq1VyaVJlc29sdmVyqm5hdGl2ZVR5cGWmTW9kdWxlq2lzSW50ZXJmYWNlwqR0eXBlslVyaVJlc29sdmVyX01vZHVsZaRraW5kzQEAp21ldGhvZHOSiKRuYW1lrXRyeVJlc29sdmVVcmmmcmV0dXJuhKR0eXBlvlVyaVJlc29sdmVyX01heWJlVXJpT3JNYW5pZmVzdKRuYW1lrXRyeVJlc29sdmVVcmmka2luZCKmb2JqZWN0g6RuYW1lrXRyeVJlc29sdmVVcmmkdHlwZb5VcmlSZXNvbHZlcl9NYXliZVVyaU9yTWFuaWZlc3Ska2luZM0gAKdjb21tZW502YhBdHRlbXB0IHRvIHJlc29sdmUgYSB3cmFwcGVyIGZyb20gaXRzIFVSSS4KQHBhcmFtIGF1dGhvcml0eSAtIFVSSSBhdXRob3JpdHkgKGV4OiAiZmlsZSIpCkBwYXJhbSBwYXRoIC0gVVJJIHBhdGggKGV4OiAiL3BhdGgvdG8vd3JhcHBlciIppHR5cGWmTWV0aG9kpGtpbmRAqHJlcXVpcmVkw6NlbnaBqHJlcXVpcmVkwqlhcmd1bWVudHOShaR0eXBlplN0cmluZ6RuYW1lqWF1dGhvcml0eahyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lqWF1dGhvcml0eaR0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASFpHR5cGWmU3RyaW5npG5hbWWkcGF0aKhyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lpHBhdGikdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEiKRuYW1lp2dldEZpbGWmcmV0dXJuhKR0eXBlpUJ5dGVzpG5hbWWnZ2V0RmlsZaRraW5kIqZzY2FsYXKDpG5hbWWnZ2V0RmlsZaR0eXBlpUJ5dGVzpGtpbmQEp2NvbW1lbnTZUUF0dGVtcHQgdG8gcmVhZCBhIGZpbGUuCkBwYXJhbSBwYXRoIC0gVVJJIHBhdGggKGV4OiAiL3BhdGgvdG8vd3JhcHBlci93cmFwLndhc20iKaR0eXBlpk1ldGhvZKRraW5kQKhyZXF1aXJlZMOjZW52gahyZXF1aXJlZMKpYXJndW1lbnRzkYWkdHlwZaZTdHJpbmekbmFtZaRwYXRoqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWkcGF0aKR0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASHo3Vyadkrd3JhcDovL2Vucy93cmFwcy5ldGg6aXBmcy1odHRwLWNsaWVudEAxLjAuMKluYW1lc3BhY2WmQ2xpZW50qm5hdGl2ZVR5cGWmTW9kdWxlq2lzSW50ZXJmYWNlw6R0eXBlrUNsaWVudF9Nb2R1bGWka2luZM0BAKdtZXRob2RzlYakbmFtZaNjYXSmcmV0dXJuhaR0eXBlpUJ5dGVzpG5hbWWjY2F0qHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWjY2F0pHR5cGWlQnl0ZXOocmVxdWlyZWTDpGtpbmQEpHR5cGWmTWV0aG9kpGtpbmRAqHJlcXVpcmVkw6lhcmd1bWVudHOUhaR0eXBlplN0cmluZ6RuYW1lo2NpZKhyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lo2NpZKR0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASFpHR5cGWmU3RyaW5npG5hbWWsaXBmc1Byb3ZpZGVyqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWsaXBmc1Byb3ZpZGVypHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBISkdHlwZaZVSW50MzKkbmFtZad0aW1lb3V0pGtpbmQipnNjYWxhcoOkbmFtZad0aW1lb3V0pHR5cGWmVUludDMypGtpbmQEhKR0eXBlsUNsaWVudF9DYXRPcHRpb25zpG5hbWWqY2F0T3B0aW9uc6RraW5kIqZvYmplY3SDpG5hbWWqY2F0T3B0aW9uc6R0eXBlsUNsaWVudF9DYXRPcHRpb25zpGtpbmTNIACGpG5hbWWncmVzb2x2ZaZyZXR1cm6FpHR5cGW0Q2xpZW50X1Jlc29sdmVSZXN1bHSkbmFtZadyZXNvbHZlqHJlcXVpcmVkw6RraW5kIqZvYmplY3SEpG5hbWWncmVzb2x2ZahyZXF1aXJlZMOkdHlwZbRDbGllbnRfUmVzb2x2ZVJlc3VsdKRraW5kzSAApHR5cGWmTWV0aG9kpGtpbmRAqHJlcXVpcmVkw6lhcmd1bWVudHOUhaR0eXBlplN0cmluZ6RuYW1lo2NpZKhyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lo2NpZKR0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASFpHR5cGWmU3RyaW5npG5hbWWsaXBmc1Byb3ZpZGVyqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWsaXBmc1Byb3ZpZGVypHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBISkdHlwZaZVSW50MzKkbmFtZad0aW1lb3V0pGtpbmQipnNjYWxhcoOkbmFtZad0aW1lb3V0pHR5cGWmVUludDMypGtpbmQEhKR0eXBltUNsaWVudF9SZXNvbHZlT3B0aW9uc6RuYW1lrnJlc29sdmVPcHRpb25zpGtpbmQipm9iamVjdIOkbmFtZa5yZXNvbHZlT3B0aW9uc6R0eXBltUNsaWVudF9SZXNvbHZlT3B0aW9uc6RraW5kzSAAhqRuYW1lp2FkZEZpbGWmcmV0dXJuhaR0eXBlsENsaWVudF9BZGRSZXN1bHSkbmFtZadhZGRGaWxlqHJlcXVpcmVkw6RraW5kIqZvYmplY3SEpG5hbWWnYWRkRmlsZahyZXF1aXJlZMOkdHlwZbBDbGllbnRfQWRkUmVzdWx0pGtpbmTNIACkdHlwZaZNZXRob2Ska2luZECocmVxdWlyZWTDqWFyZ3VtZW50c5SFpHR5cGWwQ2xpZW50X0ZpbGVFbnRyeaRuYW1lpGRhdGGocmVxdWlyZWTDpGtpbmQipm9iamVjdISkbmFtZaRkYXRhqHJlcXVpcmVkw6R0eXBlsENsaWVudF9GaWxlRW50cnmka2luZM0gAIWkdHlwZaZTdHJpbmekbmFtZaxpcGZzUHJvdmlkZXKocmVxdWlyZWTDpGtpbmQipnNjYWxhcoSkbmFtZaxpcGZzUHJvdmlkZXKkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEhKR0eXBlplVJbnQzMqRuYW1lp3RpbWVvdXSka2luZCKmc2NhbGFyg6RuYW1lp3RpbWVvdXSkdHlwZaZVSW50MzKka2luZASEpHR5cGWxQ2xpZW50X0FkZE9wdGlvbnOkbmFtZaphZGRPcHRpb25zpGtpbmQipm9iamVjdIOkbmFtZaphZGRPcHRpb25zpHR5cGWxQ2xpZW50X0FkZE9wdGlvbnOka2luZM0gAIakbmFtZaZhZGREaXKmcmV0dXJuhaR0eXBlsltDbGllbnRfQWRkUmVzdWx0XaRuYW1lpmFkZERpcqhyZXF1aXJlZMOka2luZCKlYXJyYXmGpHR5cGWyW0NsaWVudF9BZGRSZXN1bHRdpG5hbWWmYWRkRGlyqHJlcXVpcmVkw6ZvYmplY3SEpG5hbWWmYWRkRGlyqHJlcXVpcmVkw6R0eXBlsENsaWVudF9BZGRSZXN1bHSka2luZM0gAKRraW5kEqRpdGVthKRuYW1lpmFkZERpcqhyZXF1aXJlZMOkdHlwZbBDbGllbnRfQWRkUmVzdWx0pGtpbmTNIACkdHlwZaZNZXRob2Ska2luZECocmVxdWlyZWTDqWFyZ3VtZW50c5SFpHR5cGW1Q2xpZW50X0RpcmVjdG9yeUVudHJ5pG5hbWWkZGF0YahyZXF1aXJlZMOka2luZCKmb2JqZWN0hKRuYW1lpGRhdGGocmVxdWlyZWTDpHR5cGW1Q2xpZW50X0RpcmVjdG9yeUVudHJ5pGtpbmTNIACFpHR5cGWmU3RyaW5npG5hbWWsaXBmc1Byb3ZpZGVyqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWsaXBmc1Byb3ZpZGVypHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBISkdHlwZaZVSW50MzKkbmFtZad0aW1lb3V0pGtpbmQipnNjYWxhcoOkbmFtZad0aW1lb3V0pHR5cGWmVUludDMypGtpbmQEhKR0eXBlsUNsaWVudF9BZGRPcHRpb25zpG5hbWWqYWRkT3B0aW9uc6RraW5kIqZvYmplY3SDpG5hbWWqYWRkT3B0aW9uc6R0eXBlsUNsaWVudF9BZGRPcHRpb25zpGtpbmTNIACGpG5hbWWnYWRkQmxvYqZyZXR1cm6FpHR5cGWyW0NsaWVudF9BZGRSZXN1bHRdpG5hbWWnYWRkQmxvYqhyZXF1aXJlZMOka2luZCKlYXJyYXmGpHR5cGWyW0NsaWVudF9BZGRSZXN1bHRdpG5hbWWnYWRkQmxvYqhyZXF1aXJlZMOmb2JqZWN0hKRuYW1lp2FkZEJsb2KocmVxdWlyZWTDpHR5cGWwQ2xpZW50X0FkZFJlc3VsdKRraW5kzSAApGtpbmQSpGl0ZW2EpG5hbWWnYWRkQmxvYqhyZXF1aXJlZMOkdHlwZbBDbGllbnRfQWRkUmVzdWx0pGtpbmTNIACkdHlwZaZNZXRob2Ska2luZECocmVxdWlyZWTDqWFyZ3VtZW50c5SFpHR5cGWrQ2xpZW50X0Jsb2KkbmFtZaRkYXRhqHJlcXVpcmVkw6RraW5kIqZvYmplY3SEpG5hbWWkZGF0YahyZXF1aXJlZMOkdHlwZatDbGllbnRfQmxvYqRraW5kzSAAhaR0eXBlplN0cmluZ6RuYW1lrGlwZnNQcm92aWRlcqhyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lrGlwZnNQcm92aWRlcqR0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASEpHR5cGWmVUludDMypG5hbWWndGltZW91dKRraW5kIqZzY2FsYXKDpG5hbWWndGltZW91dKR0eXBlplVJbnQzMqRraW5kBISkdHlwZbFDbGllbnRfQWRkT3B0aW9uc6RuYW1lqmFkZE9wdGlvbnOka2luZCKmb2JqZWN0g6RuYW1lqmFkZE9wdGlvbnOkdHlwZbFDbGllbnRfQWRkT3B0aW9uc6RraW5kzSAAh6N1cmnZJXdyYXA6Ly9lbnMvd3JhcHMuZXRoOmNvbmN1cnJlbnRAMS4wLjCpbmFtZXNwYWNlqkNvbmN1cnJlbnSqbmF0aXZlVHlwZaZNb2R1bGWraXNJbnRlcmZhY2XDpHR5cGWxQ29uY3VycmVudF9Nb2R1bGWka2luZM0BAKdtZXRob2RzlIakbmFtZaZyZXN1bHSmcmV0dXJuhaR0eXBlt1tDb25jdXJyZW50X1Rhc2tSZXN1bHRdpG5hbWWmcmVzdWx0qHJlcXVpcmVkw6RraW5kIqVhcnJheYakdHlwZbdbQ29uY3VycmVudF9UYXNrUmVzdWx0XaRuYW1lpnJlc3VsdKhyZXF1aXJlZMOmb2JqZWN0hKRuYW1lpnJlc3VsdKhyZXF1aXJlZMOkdHlwZbVDb25jdXJyZW50X1Rhc2tSZXN1bHSka2luZM0gAKRraW5kEqRpdGVthKRuYW1lpnJlc3VsdKhyZXF1aXJlZMOkdHlwZbVDb25jdXJyZW50X1Rhc2tSZXN1bHSka2luZM0gAKR0eXBlpk1ldGhvZKRraW5kQKhyZXF1aXJlZMOpYXJndW1lbnRzkoWkdHlwZaVbSW50XaRuYW1lp3Rhc2tJZHOocmVxdWlyZWTDpGtpbmQipWFycmF5hqRuYW1lp3Rhc2tJZHOkdHlwZaVbSW50XahyZXF1aXJlZMOmc2NhbGFyhKRuYW1lp3Rhc2tJZHOkdHlwZaNJbnSocmVxdWlyZWTDpGtpbmQEpGtpbmQSpGl0ZW2EpG5hbWWndGFza0lkc6R0eXBlo0ludKhyZXF1aXJlZMOka2luZASFpHR5cGW1Q29uY3VycmVudF9SZXR1cm5XaGVupG5hbWWqcmV0dXJuV2hlbqhyZXF1aXJlZMOka2luZCKkZW51bYSkbmFtZapyZXR1cm5XaGVuqHJlcXVpcmVkw6R0eXBltUNvbmN1cnJlbnRfUmV0dXJuV2hlbqRraW5kzUAAhqRuYW1lpnN0YXR1c6ZyZXR1cm6FpHR5cGW3W0NvbmN1cnJlbnRfVGFza1N0YXR1c12kbmFtZaZzdGF0dXOocmVxdWlyZWTDpGtpbmQipWFycmF5hqR0eXBlt1tDb25jdXJyZW50X1Rhc2tTdGF0dXNdpG5hbWWmc3RhdHVzqHJlcXVpcmVkw6RlbnVthKRuYW1lpnN0YXR1c6hyZXF1aXJlZMOkdHlwZbVDb25jdXJyZW50X1Rhc2tTdGF0dXOka2luZM1AAKRraW5kEqRpdGVthKRuYW1lpnN0YXR1c6hyZXF1aXJlZMOkdHlwZbVDb25jdXJyZW50X1Rhc2tTdGF0dXOka2luZM1AAKR0eXBlpk1ldGhvZKRraW5kQKhyZXF1aXJlZMOpYXJndW1lbnRzkYWkdHlwZaVbSW50XaRuYW1lp3Rhc2tJZHOocmVxdWlyZWTDpGtpbmQipWFycmF5hqRuYW1lp3Rhc2tJZHOkdHlwZaVbSW50XahyZXF1aXJlZMOmc2NhbGFyhKRuYW1lp3Rhc2tJZHOkdHlwZaNJbnSocmVxdWlyZWTDpGtpbmQEpGtpbmQSpGl0ZW2EpG5hbWWndGFza0lkc6R0eXBlo0ludKhyZXF1aXJlZMOka2luZASGpG5hbWWoc2NoZWR1bGWmcmV0dXJuhaR0eXBlpVtJbnRdpG5hbWWoc2NoZWR1bGWocmVxdWlyZWTDpGtpbmQipWFycmF5hqR0eXBlpVtJbnRdpG5hbWWoc2NoZWR1bGWocmVxdWlyZWTDpnNjYWxhcoSkbmFtZahzY2hlZHVsZaR0eXBlo0ludKhyZXF1aXJlZMOka2luZASka2luZBKkaXRlbYSkbmFtZahzY2hlZHVsZaR0eXBlo0ludKhyZXF1aXJlZMOka2luZASkdHlwZaZNZXRob2Ska2luZECocmVxdWlyZWTDqWFyZ3VtZW50c5GFpHR5cGWxW0NvbmN1cnJlbnRfVGFza12kbmFtZaV0YXNrc6hyZXF1aXJlZMOka2luZCKlYXJyYXmGpG5hbWWldGFza3OkdHlwZbFbQ29uY3VycmVudF9UYXNrXahyZXF1aXJlZMOmb2JqZWN0hKRuYW1lpXRhc2tzqHJlcXVpcmVkw6R0eXBlr0NvbmN1cnJlbnRfVGFza6RraW5kzSAApGtpbmQSpGl0ZW2EpG5hbWWldGFza3OocmVxdWlyZWTDpHR5cGWvQ29uY3VycmVudF9UYXNrpGtpbmTNIACGpG5hbWWlYWJvcnSmcmV0dXJuhaR0eXBlqVtCb29sZWFuXaRuYW1lpWFib3J0qHJlcXVpcmVkw6RraW5kIqVhcnJheYakdHlwZalbQm9vbGVhbl2kbmFtZaVhYm9ydKhyZXF1aXJlZMOmc2NhbGFyhKRuYW1lpWFib3J0pHR5cGWnQm9vbGVhbqhyZXF1aXJlZMOka2luZASka2luZBKkaXRlbYSkbmFtZaVhYm9ydKR0eXBlp0Jvb2xlYW6ocmVxdWlyZWTDpGtpbmQEpHR5cGWmTWV0aG9kpGtpbmRAqHJlcXVpcmVkw6lhcmd1bWVudHORhaR0eXBlqFtTdHJpbmddpG5hbWWndGFza0lkc6hyZXF1aXJlZMOka2luZCKlYXJyYXmGpG5hbWWndGFza0lkc6R0eXBlqFtTdHJpbmddqHJlcXVpcmVkw6ZzY2FsYXKEpG5hbWWndGFza0lkc6R0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASka2luZBKkaXRlbYSkbmFtZad0YXNrSWRzpHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBLFpbXBvcnRlZEVudW1UeXBlc5KGpHR5cGW1Q29uY3VycmVudF9SZXR1cm5XaGVuqWNvbnN0YW50c5OvRklSU1RfQ09NUExFVEVErUFOWV9DT01QTEVURUStQUxMX0NPTVBMRVRFRKN1cmnZJXdyYXA6Ly9lbnMvd3JhcHMuZXRoOmNvbmN1cnJlbnRAMS4wLjCpbmFtZXNwYWNlqkNvbmN1cnJlbnSqbmF0aXZlVHlwZapSZXR1cm5XaGVupGtpbmTNAgiGpHR5cGW1Q29uY3VycmVudF9UYXNrU3RhdHVzqWNvbnN0YW50c5WnUEVORElOR6dSVU5OSU5HqUNPTVBMRVRFRKlDQU5DRUxMRUSmRkFJTEVEo3Vyadkld3JhcDovL2Vucy93cmFwcy5ldGg6Y29uY3VycmVudEAxLjAuMKluYW1lc3BhY2WqQ29uY3VycmVudKpuYXRpdmVUeXBlqlRhc2tTdGF0dXOka2luZM0CCKdlbnZUeXBlg6R0eXBlo0VudqRraW5kzgABAACqcHJvcGVydGllc5WFpHR5cGWnUmV0cmllc6RuYW1lp3JldHJpZXOnY29tbWVudLhSZXRyeSByZXF1ZXN0IG9uIGZhaWx1cmWka2luZCKmb2JqZWN0g6RuYW1lp3JldHJpZXOkdHlwZadSZXRyaWVzpGtpbmTNIACFpHR5cGWmVUludDMypG5hbWWndGltZW91dKdjb21tZW502SJSZXNwb25zZSB0aW1lb3V0IGZvciBIVFRQIHJlcXVlc3RzpGtpbmQipnNjYWxhcoOkbmFtZad0aW1lb3V0pHR5cGWmVUludDMypGtpbmQEhqR0eXBlplN0cmluZ6RuYW1lqHByb3ZpZGVyp2NvbW1lbnSwRGVmYXVsdCBwcm92aWRlcqhyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lqHByb3ZpZGVypHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBIWkdHlwZahbU3RyaW5nXaRuYW1lsWZhbGxiYWNrUHJvdmlkZXJzp2NvbW1lbnSyRmFsbGJhY2sgcHJvdmlkZXJzpGtpbmQipWFycmF5haRuYW1lsWZhbGxiYWNrUHJvdmlkZXJzpHR5cGWoW1N0cmluZ12mc2NhbGFyhKRuYW1lsWZhbGxiYWNrUHJvdmlkZXJzpHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBKRraW5kEqRpdGVthKRuYW1lsWZhbGxiYWNrUHJvdmlkZXJzpHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBIWkdHlwZadCb29sZWFupG5hbWW3ZGlzYWJsZVBhcmFsbGVsUmVxdWVzdHOnY29tbWVudNk6RGlzYWJsZSBxdWVyeWluZyBwcm92aWRlcnMgaW4gcGFyYWxsZWwgd2hlbiByZXNvbHZpbmcgVVJJc6RraW5kIqZzY2FsYXKDpG5hbWW3ZGlzYWJsZVBhcmFsbGVsUmVxdWVzdHOkdHlwZadCb29sZWFupGtpbmQE" -); - -export const wasmPackage = WasmPackage.from( - wrap_info, - wrap_wasm -); diff --git a/packages/js/client-config-builder/src/bundles/embeds/async-ipfs-resolver/wrap.wasm b/packages/js/client-config-builder/src/bundles/embeds/async-ipfs-resolver/wrap.wasm deleted file mode 100644 index 6e918072324252a7beb46646f3d95fe38417940f..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 261485 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 diff --git a/packages/js/client-config-builder/src/bundles/embeds/ipfs-http-client/wrap.info b/packages/js/client-config-builder/src/bundles/embeds/ipfs-http-client/wrap.info deleted file mode 100644 index 93c262a1ca8e91700ed2c22ea61432603a63e54c..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 9034 zcmeHM&2Jk;6i-nOh$DZ&&`Ur{9Lm?BLa0qY)E+{sVg#r{W#S#j3+vrwW}IM7AWAvY z0^)ARPMo%)lsgh!fjj&)ypP%S>_;3Y1%#ldBs=f>{ob25FE__qN}Di=2hTT74P)6= z55u%=Ryx+EE3GJ0v0ag7X#1%eZcEc0$c^xp&$FLwysuie2?XZb&xmkxPTDJ}1)*m6 zK^O-oCaF$RrERFp?VCihb2+vzzCij$NxN;7CCZZ{(~^mJM&}Y<;6MJUn-!QhjNgVYrNmFO)^lUCs z54N>T-wJK#e5fJ*iSE}}Rzp-3&at?EO_?OxQb&o$9%$|XdbU)JZtt+Fvy#I5LC0QG ztwaasl3rYghB5^Tt)gP|hSg!bN$Hw^%x2hCNv}?xe~Pj)PRbp}agI%pY>_Jk3p9@jB$q)hppQ}W?SQWVo#j_O#N|#8pT4A|4)hyxc)gGY! z0FUle)sxjTRTIT5wKYOJPy@4tBE=Dfn($*aTPRY@66ykUF^trO*t(KBB;|iufOgjU zRvC_FAg!G33Q~|O%vK^^bVZ#vhkAGZo_uq0e|Np8{9W>FKXB~|?gB249jUeKe_lPs zqO1rR@pZ$X_l0=@K*sw;<)rFYu|Pkc9)?zRk1K+`+rOTJgdN*y188boa^KM=pQqpl z)08~e%M~1G{G5D@h2dJ1Y>=n|pdTm8!{5IkS(9!O^di*+yxbgz-89kGeElg^`u-&t z%5JRFIe)oJU#`J@qm1QG58Nk{!uUmE`1|+t{bHiK=b>{@JK%$R1qMs=%6L-NGsdZF*kOvZ{e8-W4ua>*AxywapQRlmF@bPre`8>?s&u`;JH-f0JnlmJM?eU3 zR3ZEO*MXX!4?OrdqHALiy}M0un2`L3DrBzb(Kl_j}Y zKZaX&^#I&(NS%$hv79ml47vF^kAgX#)sK&~>8ua;`eS@8Jmf)I z1y`oa$~)Yf3M2HOr^6p{v37cORmEl%e>Dy06Q?^cdY?JfIMsN557S~&*-}HCoF}og zumEd9M;W_8oQAz$7yW0}H~h?cxGvLIc{W@Y{PQ&$s>dBAVZ~zxU7507b);@P>Sim) zGV78dOMY8eTzI0W>kDCDbo?0o-z$`x2NA` z3GyAEkAq$3f~!8nCAyDlwR>88MW{yy_T1hMrX@nFT(x_Kn5*x6A7KZhJQkmtYVsTG4tponp~e= zzr21yp!?!kyt@tD=z-c&5w@~MH~AP^nQSC_6YlwyH{Vzdl9pM0OKq%PYBsN~u1OQN z%#EadgZ@NWH&B*&t|88=wuCMM0ZfGIrnc__R@)7cscJl9rMP%|G<@#Di;QlSI%x8J zG=QxWp=tyT)b>mXP+8;|evXDrN5&Fy4f-Z5wW&TT6Bi|WbbesU3Jw_`{;TtnUqpPB zR?F~!D>k2Td3oDJxPJM?qru88g7-rM7*M(mL+?+NHGdV&kUO!E?TK%@J@KZ>_Qagb zBHjs#1E6tr&ubcPH1ruur^JG>!0QH&4t>7guD*L97*PpmMQ|d);ixP;8ORUVbJ7@9 z<4b;oMi)7qI~=ZInwUf5MMO19`1}7RVh^(C+yxkyn*?-jsnx-FuLb`Gfq~JQ+r#FC bx0|E2%delk_Rgb~#oesiqHc!&6HopL3w>fj diff --git a/packages/js/client-config-builder/src/bundles/embeds/ipfs-http-client/wrap.ts b/packages/js/client-config-builder/src/bundles/embeds/ipfs-http-client/wrap.ts deleted file mode 100644 index d8b661e177..0000000000 --- a/packages/js/client-config-builder/src/bundles/embeds/ipfs-http-client/wrap.ts +++ /dev/null @@ -1,17 +0,0 @@ -// NOTE: This file is auto-generated, do not modify by hand! -// See: ./scripts/embed-wrappers.ts -import { WasmPackage } from "@polywrap/wasm-js"; -import toUint8Array from "base64-to-uint8array"; - -const wrap_wasm = toUint8Array( - "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AmoiAy0AADoAACADQQJqIQEgACADLQABOgABIABBAmohAAsgAkEIcQRAIAAgAS0AADoAACAAIAEtAAE6AAEgAEECaiIAIAFBAmoiAS0AADoAACAAIAEtAAE6AAEgAEECaiIAIAFBAmoiAS0AADoAACAAIAEtAAE6AAEgAEECaiIAIAFBAmoiAy0AADoAACADQQJqIQEgACADLQABOgABIABBAmohAAsgAkEEcQRAIAAgAS0AADoAACAAIAEtAAE6AAEgAEECaiIAIAFBAmoiAy0AADoAACADQQJqIQEgACADLQABOgABIABBAmohAAsgAkECcQRAIAAgAS0AADoAACAAIgNBAmohACADIAEtAAE6AAEgAUECaiEBCyACQQFxBEAgACABLQAAOgAACwvSAgECfwJAIAIhAyAAIAFGDQAgASAAayADa0EAIANBAXRrTQRAIAAgASADEBYMAQsgACABSQRAIAFBB3EgAEEHcUYEQANAIABBB3EEQCADRQ0EIANBAWshAyAAIgJBAWohACABIQQgAUEBaiEBIAIgBC0AADoAAAwBCwsDQCADQQhPBEAgACABKQMANwMAIANBCGshAyAAQQhqIQAgAUEIaiEBDAELCwsDQCADBEAgACICQQFqIQAgASEEIAFBAWohASACIAQtAAA6AAAgA0EBayEDDAELCwUgAUEHcSAAQQdxRgRAA0AgACADakEHcQRAIANFDQQgA0EBayIDIABqIAEgA2otAAA6AAAMAQsLA0AgA0EITwRAIANBCGsiAyAAaiABIANqKQMANwMADAELCwsDQCADBEAgA0EBayIDIABqIAEgA2otAAA6AAAMAQsLCwsLvAIBA38jCEECRgRAIwkjCSgCAEEUazYCACMJKAIAIgQoAgAhACAEKAIIIQIgBCgCDCEDIAQoAhAhBSAEKAIEIQELAn8gBSAAIAF0IwgbIQUjCEECRgRAIwkjCSgCAEEEazYCACMJKAIAKAIAIQYLIAZBACMIG0UEQCAFQQAQDSEEQQAjCEEBRg0BGiAEIQELIwhBASADG0UEQCABIAMgBRAXCyAGQQFGQQEjCBsEQEEQIAIQDSEEQQEjCEEBRg0BGiAEIQILIwhFBEAgAiABNgIAIAIgATYCBCACIAU2AgggAiAANgIMIAIPCwALIQQjCSgCACAENgIAIwkjCSgCAEEE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ADEAOAAxADkAMQBhADEAYgAxAGMAMQBkADEAZQAxAGYAMgAwADIAMQAyADIAMgAzADIANAAyADUAMgA2ADIANwAyADgAMgA5ADIAYQAyAGIAMgBjADIAZAAyAGUAMgBmADMAMAAzADEAMwAyADMAMwAzADQAMwA1ADMANgAzADcAMwA4ADMAOQAzAGEAMwBiADMAYwAzAGQAMwBlADMAZgA0ADAANAAxADQAMgA0ADMANAA0ADQANQA0ADYANAA3ADQAOAA0ADkANABhADQAYgA0AGMANABkADQAZQA0AGYANQAwADUAMQA1ADIANQAzADUANAA1ADUANQA2ADUANwA1ADgANQA5ADUAYQA1AGIANQBjADUAZAA1AGUANQBmADYAMAA2ADEANgAyADYAMwA2ADQANgA1ADYANgA2ADcANgA4ADYAOQA2AGEANgBiADYAYwA2AGQANgBlADYAZgA3ADAANwAxADcAMgA3ADMANwA0ADcANQA3ADYANwA3ADcAOAA3ADkANwBhADcAYgA3AGMANwBkADcAZQA3AGYAOAAwADgAMQA4ADIAOAAzADgANAA4ADUAOAA2ADgANwA4ADgAOAA5ADgAYQA4AGIAOABjADgAZAA4AGUAOABmADkAMAA5ADEAOQAyADkAMwA5ADQAOQA1ADkANgA5ADcAOQA4ADkAOQA5AGEAOQBiADkAYwA5AGQAOQBlADkAZgBhADAAYQAxAGEAMgBhADMAYQA0AGEANQBhADYAYQA3AGEAOABhADkAYQBhAGEAYgBhAGMAYQBkAGEAZQBhAGYAYgAwAGIAMQBiADIAYgAzAGIANABiADUAYgA2AGIANwBiADgAYgA5AGIAYQBiAGIAYgBjAGIAZABiAGUAYgBmAGMAMABjADEAYwAyAGMAMwBjADQAYwA1AGMANgBjADcAYwA4AGMAOQBjAGEAYwBiAGMAYwBjAGQAYwBlAGMAZgBkADAAZAAxAGQAMgBkADMAZAA0AGQANQBkADYAZAA3AGQAOABkADkAZABhAGQAYgBkAGMAZABkAGQAZQBkAGYAZQAwAGUAMQBlADIAZQAzAGUANABlADUAZQA2AGUANwBlADgAZQA5AGUAYQBlAGIAZQBjAGUAZABlAGUAZQBmAGYAMABmADEAZgAyAGYAMwBmADQAZgA1AGYANgBmADcAZgA4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" -); - -const wrap_info = toUint8Array( - "hKd2ZXJzaW9uozAuMaRuYW1ls2lwZnMtaHR0cC1jbGllbnQtYXOkdHlwZaR3YXNto2FiaYandmVyc2lvbqMwLjGrb2JqZWN0VHlwZXOYg6R0eXBlqkNhdE9wdGlvbnOka2luZAGqcHJvcGVydGllc5KEpHR5cGWlSW50MzKkbmFtZaZvZmZzZXSka2luZCKmc2NhbGFyg6RuYW1lpm9mZnNldKR0eXBlpUludDMypGtpbmQEhKR0eXBlpUludDMypG5hbWWmbGVuZ3RopGtpbmQipnNjYWxhcoOkbmFtZaZsZW5ndGikdHlwZaVJbnQzMqRraW5kBIOkdHlwZapBZGRPcHRpb25zpGtpbmQBqnByb3BlcnRpZXOThKR0eXBlp0Jvb2xlYW6kbmFtZaNwaW6ka2luZCKmc2NhbGFyg6RuYW1lo3BpbqR0eXBlp0Jvb2xlYW6ka2luZASEpHR5cGWnQm9vbGVhbqRuYW1lqG9ubHlIYXNopGtpbmQipnNjYWxhcoOkbmFtZahvbmx5SGFzaKR0eXBlp0Jvb2xlYW6ka2luZASEpHR5cGWnQm9vbGVhbqRuYW1lsXdyYXBXaXRoRGlyZWN0b3J5pGtpbmQipnNjYWxhcoOkbmFtZbF3cmFwV2l0aERpcmVjdG9yeaR0eXBlp0Jvb2xlYW6ka2luZASDpHR5cGWuUmVzb2x2ZU9wdGlvbnOka2luZAGqcHJvcGVydGllc5OEpHR5cGWnQm9vbGVhbqRuYW1lqXJlY3Vyc2l2ZaRraW5kIqZzY2FsYXKDpG5hbWWpcmVjdXJzaXZlpHR5cGWnQm9vbGVhbqRraW5kBISkdHlwZaVJbnQzMqRuYW1lrmRodFJlY29yZENvdW50pGtpbmQipnNjYWxhcoOkbmFtZa5kaHRSZWNvcmRDb3VudKR0eXBlpUludDMypGtpbmQEhKR0eXBlplN0cmluZ6RuYW1lqmRodFRpbWVvdXSka2luZCKmc2NhbGFyg6RuYW1lqmRodFRpbWVvdXSkdHlwZaZTdHJpbmeka2luZASDpHR5cGWtUmVzb2x2ZVJlc3VsdKRraW5kAapwcm9wZXJ0aWVzkoWkdHlwZaZTdHJpbmekbmFtZaNjaWSocmVxdWlyZWTDpGtpbmQipnNjYWxhcoSkbmFtZaNjaWSkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEhaR0eXBlplN0cmluZ6RuYW1lqHByb3ZpZGVyqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWocHJvdmlkZXKkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEg6R0eXBlqUFkZFJlc3VsdKRraW5kAapwcm9wZXJ0aWVzk4WkdHlwZaZTdHJpbmekbmFtZaRuYW1lqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWkbmFtZaR0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASFpHR5cGWmU3RyaW5npG5hbWWkaGFzaKhyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lpGhhc2ikdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEhaR0eXBlplN0cmluZ6RuYW1lpHNpemWocmVxdWlyZWTDpGtpbmQipnNjYWxhcoSkbmFtZaRzaXplpHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBIOkdHlwZalGaWxlRW50cnmka2luZAGqcHJvcGVydGllc5KFpHR5cGWmU3RyaW5npG5hbWWkbmFtZahyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lpG5hbWWkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEhaR0eXBlpUJ5dGVzpG5hbWWkZGF0YahyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lpGRhdGGkdHlwZaVCeXRlc6hyZXF1aXJlZMOka2luZASDpHR5cGWuRGlyZWN0b3J5RW50cnmka2luZAGqcHJvcGVydGllc5OFpHR5cGWmU3RyaW5npG5hbWWkbmFtZahyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lpG5hbWWkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEhKR0eXBlsFtEaXJlY3RvcnlFbnRyeV2kbmFtZatkaXJlY3Rvcmllc6RraW5kIqVhcnJheYWkbmFtZatkaXJlY3Rvcmllc6R0eXBlsFtEaXJlY3RvcnlFbnRyeV2mb2JqZWN0hKRuYW1lq2RpcmVjdG9yaWVzqHJlcXVpcmVkw6R0eXBlrkRpcmVjdG9yeUVudHJ5pGtpbmTNIACka2luZBKkaXRlbYSkbmFtZatkaXJlY3Rvcmllc6hyZXF1aXJlZMOkdHlwZa5EaXJlY3RvcnlFbnRyeaRraW5kzSAAhKR0eXBlq1tGaWxlRW50cnldpG5hbWWlZmlsZXOka2luZCKlYXJyYXmFpG5hbWWlZmlsZXOkdHlwZatbRmlsZUVudHJ5XaZvYmplY3SEpG5hbWWlZmlsZXOocmVxdWlyZWTDpHR5cGWpRmlsZUVudHJ5pGtpbmTNIACka2luZBKkaXRlbYSkbmFtZaVmaWxlc6hyZXF1aXJlZMOkdHlwZalGaWxlRW50cnmka2luZM0gAIOkdHlwZaRCbG9ipGtpbmQBqnByb3BlcnRpZXOShKR0eXBlsFtEaXJlY3RvcnlFbnRyeV2kbmFtZatkaXJlY3Rvcmllc6RraW5kIqVhcnJheYWkbmFtZatkaXJlY3Rvcmllc6R0eXBlsFtEaXJlY3RvcnlFbnRyeV2mb2JqZWN0hKRuYW1lq2RpcmVjdG9yaWVzqHJlcXVpcmVkw6R0eXBlrkRpcmVjdG9yeUVudHJ5pGtpbmTNIACka2luZBKkaXRlbYSkbmFtZatkaXJlY3Rvcmllc6hyZXF1aXJlZMOkdHlwZa5EaXJlY3RvcnlFbnRyeaRraW5kzSAAhKR0eXBlq1tGaWxlRW50cnldpG5hbWWlZmlsZXOka2luZCKlYXJyYXmFpG5hbWWlZmlsZXOkdHlwZatbRmlsZUVudHJ5XaZvYmplY3SEpG5hbWWlZmlsZXOocmVxdWlyZWTDpHR5cGWpRmlsZUVudHJ5pGtpbmTNIACka2luZBKkaXRlbYSkbmFtZaVmaWxlc6hyZXF1aXJlZMOkdHlwZalGaWxlRW50cnmka2luZM0gAKptb2R1bGVUeXBlhKdpbXBvcnRzlYGkdHlwZatIdHRwX01vZHVsZYGkdHlwZaxIdHRwX1JlcXVlc3SBpHR5cGWxSHR0cF9SZXNwb25zZVR5cGWBpHR5cGWySHR0cF9Gb3JtRGF0YUVudHJ5gaR0eXBlrUh0dHBfUmVzcG9uc2WkdHlwZaZNb2R1bGWka2luZMyAp21ldGhvZHOVhqRuYW1lo2NhdKZyZXR1cm6FpHR5cGWlQnl0ZXOkbmFtZaNjYXSocmVxdWlyZWTDpGtpbmQipnNjYWxhcoSkbmFtZaNjYXSkdHlwZaVCeXRlc6hyZXF1aXJlZMOka2luZASkdHlwZaZNZXRob2Ska2luZECocmVxdWlyZWTDqWFyZ3VtZW50c5SFpHR5cGWmU3RyaW5npG5hbWWjY2lkqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWjY2lkpHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBIWkdHlwZaZTdHJpbmekbmFtZaxpcGZzUHJvdmlkZXKocmVxdWlyZWTDpGtpbmQipnNjYWxhcoSkbmFtZaxpcGZzUHJvdmlkZXKkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEhKR0eXBlplVJbnQzMqRuYW1lp3RpbWVvdXSka2luZCKmc2NhbGFyg6RuYW1lp3RpbWVvdXSkdHlwZaZVSW50MzKka2luZASEpHR5cGWqQ2F0T3B0aW9uc6RuYW1lqmNhdE9wdGlvbnOka2luZCKmb2JqZWN0g6RuYW1lqmNhdE9wdGlvbnOkdHlwZapDYXRPcHRpb25zpGtpbmTNIACGpG5hbWWncmVzb2x2ZaZyZXR1cm6FpHR5cGWtUmVzb2x2ZVJlc3VsdKRuYW1lp3Jlc29sdmWocmVxdWlyZWTDpGtpbmQipm9iamVjdISkbmFtZadyZXNvbHZlqHJlcXVpcmVkw6R0eXBlrVJlc29sdmVSZXN1bHSka2luZM0gAKR0eXBlpk1ldGhvZKRraW5kQKhyZXF1aXJlZMOpYXJndW1lbnRzlIWkdHlwZaZTdHJpbmekbmFtZaNjaWSocmVxdWlyZWTDpGtpbmQipnNjYWxhcoSkbmFtZaNjaWSkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEhaR0eXBlplN0cmluZ6RuYW1lrGlwZnNQcm92aWRlcqhyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lrGlwZnNQcm92aWRlcqR0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASEpHR5cGWmVUludDMypG5hbWWndGltZW91dKRraW5kIqZzY2FsYXKDpG5hbWWndGltZW91dKR0eXBlplVJbnQzMqRraW5kBISkdHlwZa5SZXNvbHZlT3B0aW9uc6RuYW1lrnJlc29sdmVPcHRpb25zpGtpbmQipm9iamVjdIOkbmFtZa5yZXNvbHZlT3B0aW9uc6R0eXBlrlJlc29sdmVPcHRpb25zpGtpbmTNIACGpG5hbWWnYWRkRmlsZaZyZXR1cm6FpHR5cGWpQWRkUmVzdWx0pG5hbWWnYWRkRmlsZahyZXF1aXJlZMOka2luZCKmb2JqZWN0hKRuYW1lp2FkZEZpbGWocmVxdWlyZWTDpHR5cGWpQWRkUmVzdWx0pGtpbmTNIACkdHlwZaZNZXRob2Ska2luZECocmVxdWlyZWTDqWFyZ3VtZW50c5SFpHR5cGWpRmlsZUVudHJ5pG5hbWWkZGF0YahyZXF1aXJlZMOka2luZCKmb2JqZWN0hKRuYW1lpGRhdGGocmVxdWlyZWTDpHR5cGWpRmlsZUVudHJ5pGtpbmTNIACFpHR5cGWmU3RyaW5npG5hbWWsaXBmc1Byb3ZpZGVyqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWsaXBmc1Byb3ZpZGVypHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBISkdHlwZaZVSW50MzKkbmFtZad0aW1lb3V0pGtpbmQipnNjYWxhcoOkbmFtZad0aW1lb3V0pHR5cGWmVUludDMypGtpbmQEhKR0eXBlqkFkZE9wdGlvbnOkbmFtZaphZGRPcHRpb25zpGtpbmQipm9iamVjdIOkbmFtZaphZGRPcHRpb25zpHR5cGWqQWRkT3B0aW9uc6RraW5kzSAAhqRuYW1lpmFkZERpcqZyZXR1cm6FpHR5cGWrW0FkZFJlc3VsdF2kbmFtZaZhZGREaXKocmVxdWlyZWTDpGtpbmQipWFycmF5hqR0eXBlq1tBZGRSZXN1bHRdpG5hbWWmYWRkRGlyqHJlcXVpcmVkw6ZvYmplY3SEpG5hbWWmYWRkRGlyqHJlcXVpcmVkw6R0eXBlqUFkZFJlc3VsdKRraW5kzSAApGtpbmQSpGl0ZW2EpG5hbWWmYWRkRGlyqHJlcXVpcmVkw6R0eXBlqUFkZFJlc3VsdKRraW5kzSAApHR5cGWmTWV0aG9kpGtpbmRAqHJlcXVpcmVkw6lhcmd1bWVudHOUhaR0eXBlrkRpcmVjdG9yeUVudHJ5pG5hbWWkZGF0YahyZXF1aXJlZMOka2luZCKmb2JqZWN0hKRuYW1lpGRhdGGocmVxdWlyZWTDpHR5cGWuRGlyZWN0b3J5RW50cnmka2luZM0gAIWkdHlwZaZTdHJpbmekbmFtZaxpcGZzUHJvdmlkZXKocmVxdWlyZWTDpGtpbmQipnNjYWxhcoSkbmFtZaxpcGZzUHJvdmlkZXKkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEhKR0eXBlplVJbnQzMqRuYW1lp3RpbWVvdXSka2luZCKmc2NhbGFyg6RuYW1lp3RpbWVvdXSkdHlwZaZVSW50MzKka2luZASEpHR5cGWqQWRkT3B0aW9uc6RuYW1lqmFkZE9wdGlvbnOka2luZCKmb2JqZWN0g6RuYW1lqmFkZE9wdGlvbnOkdHlwZapBZGRPcHRpb25zpGtpbmTNIACGpG5hbWWnYWRkQmxvYqZyZXR1cm6FpHR5cGWrW0FkZFJlc3VsdF2kbmFtZadhZGRCbG9iqHJlcXVpcmVkw6RraW5kIqVhcnJheYakdHlwZatbQWRkUmVzdWx0XaRuYW1lp2FkZEJsb2KocmVxdWlyZWTDpm9iamVjdISkbmFtZadhZGRCbG9iqHJlcXVpcmVkw6R0eXBlqUFkZFJlc3VsdKRraW5kzSAApGtpbmQSpGl0ZW2EpG5hbWWnYWRkQmxvYqhyZXF1aXJlZMOkdHlwZalBZGRSZXN1bHSka2luZM0gAKR0eXBlpk1ldGhvZKRraW5kQKhyZXF1aXJlZMOpYXJndW1lbnRzlIWkdHlwZaRCbG9ipG5hbWWkZGF0YahyZXF1aXJlZMOka2luZCKmb2JqZWN0hKRuYW1lpGRhdGGocmVxdWlyZWTDpHR5cGWkQmxvYqRraW5kzSAAhaR0eXBlplN0cmluZ6RuYW1lrGlwZnNQcm92aWRlcqhyZXF1aXJlZMOka2luZCKmc2NhbGFyhKRuYW1lrGlwZnNQcm92aWRlcqR0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASEpHR5cGWmVUludDMypG5hbWWndGltZW91dKRraW5kIqZzY2FsYXKDpG5hbWWndGltZW91dKR0eXBlplVJbnQzMqRraW5kBISkdHlwZapBZGRPcHRpb25zpG5hbWWqYWRkT3B0aW9uc6RraW5kIqZvYmplY3SDpG5hbWWqYWRkT3B0aW9uc6R0eXBlqkFkZE9wdGlvbnOka2luZM0gALNpbXBvcnRlZE9iamVjdFR5cGVzk4akdHlwZaxIdHRwX1JlcXVlc3SjdXJpv3dyYXA6Ly9lbnMvd3JhcHMuZXRoOmh0dHBAMS4xLjCpbmFtZXNwYWNlpEh0dHCqbmF0aXZlVHlwZadSZXF1ZXN0pGtpbmTNBAGqcHJvcGVydGllc5aEpHR5cGWzTWFwPFN0cmluZywgU3RyaW5nPqRuYW1lp2hlYWRlcnOjbWFwhqR0eXBls01hcDxTdHJpbmcsIFN0cmluZz6mc2NhbGFyhKRuYW1lp2hlYWRlcnOkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEpGtpbmTOAAQAAqRuYW1lp2hlYWRlcnOja2V5hKRuYW1lp2hlYWRlcnOkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEpXZhbHVlhKRuYW1lp2hlYWRlcnOkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEpGtpbmQihKR0eXBls01hcDxTdHJpbmcsIFN0cmluZz6kbmFtZal1cmxQYXJhbXOjbWFwhqR0eXBls01hcDxTdHJpbmcsIFN0cmluZz6mc2NhbGFyhKRuYW1lqXVybFBhcmFtc6R0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASka2luZM4ABAACpG5hbWWpdXJsUGFyYW1zo2tleYSkbmFtZal1cmxQYXJhbXOkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEpXZhbHVlhKRuYW1lqXVybFBhcmFtc6R0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASka2luZCKFpHR5cGWxSHR0cF9SZXNwb25zZVR5cGWkbmFtZaxyZXNwb25zZVR5cGWocmVxdWlyZWTDpGtpbmQipGVudW2EpG5hbWWscmVzcG9uc2VUeXBlqHJlcXVpcmVkw6R0eXBlsUh0dHBfUmVzcG9uc2VUeXBlpGtpbmTNQACFpHR5cGWmU3RyaW5npG5hbWWkYm9keadjb21tZW502U1UaGUgYm9keSBvZiB0aGUgcmVxdWVzdC4gSWYgcHJlc2VudCwgdGhlIGBmb3JtRGF0YWAgcHJvcGVydHkgd2lsbCBiZSBpZ25vcmVkLqRraW5kIqZzY2FsYXKDpG5hbWWkYm9keaR0eXBlplN0cmluZ6RraW5kBIWkdHlwZbRbSHR0cF9Gb3JtRGF0YUVudHJ5XaRuYW1lqGZvcm1EYXRhp2NvbW1lbnTaATUgIEFuIGFsdGVybmF0aXZlIHRvIHRoZSBzdGFuZGFyZCByZXF1ZXN0IGJvZHksICdmb3JtRGF0YScgaXMgZXhwZWN0ZWQgdG8gYmUgaW4gdGhlICdtdWx0aXBhcnQvZm9ybS1kYXRhJyBmb3JtYXQuCklmIHByZXNlbnQsIHRoZSBgYm9keWAgcHJvcGVydHkgaXMgbm90IG51bGwsIGBmb3JtRGF0YWAgd2lsbCBiZSBpZ25vcmVkLgpPdGhlcndpc2UsIGlmIGZvcm1EYXRhIGlzIG5vdCBudWxsLCB0aGUgZm9sbG93aW5nIGhlYWRlciB3aWxsIGJlIGFkZGVkIHRvIHRoZSByZXF1ZXN0OiAnQ29udGVudC1UeXBlOiBtdWx0aXBhcnQvZm9ybS1kYXRhJy6ka2luZCKlYXJyYXmFpG5hbWWoZm9ybURhdGGkdHlwZbRbSHR0cF9Gb3JtRGF0YUVudHJ5XaZvYmplY3SEpG5hbWWoZm9ybURhdGGocmVxdWlyZWTDpHR5cGWySHR0cF9Gb3JtRGF0YUVudHJ5pGtpbmTNIACka2luZBKkaXRlbYSkbmFtZahmb3JtRGF0YahyZXF1aXJlZMOkdHlwZbJIdHRwX0Zvcm1EYXRhRW50cnmka2luZM0gAISkdHlwZaZVSW50MzKkbmFtZad0aW1lb3V0pGtpbmQipnNjYWxhcoOkbmFtZad0aW1lb3V0pHR5cGWmVUludDMypGtpbmQEhqR0eXBlskh0dHBfRm9ybURhdGFFbnRyeaN1cmm/d3JhcDovL2Vucy93cmFwcy5ldGg6aHR0cEAxLjEuMKluYW1lc3BhY2WkSHR0cKpuYXRpdmVUeXBlrUZvcm1EYXRhRW50cnmka2luZM0EAapwcm9wZXJ0aWVzlIakdHlwZaZTdHJpbmekbmFtZaRuYW1lp2NvbW1lbnSyRm9ybURhdGEgZW50cnkga2V5qHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWkbmFtZaR0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASFpHR5cGWmU3RyaW5npG5hbWWldmFsdWWnY29tbWVudNk+SWYgJ3R5cGUnIGlzIGRlZmluZWQsIHZhbHVlIGlzIHRyZWF0ZWQgYXMgYSBiYXNlNjQgYnl0ZSBzdHJpbmeka2luZCKmc2NhbGFyg6RuYW1lpXZhbHVlpHR5cGWmU3RyaW5npGtpbmQEhaR0eXBlplN0cmluZ6RuYW1lqGZpbGVOYW1lp2NvbW1lbnTZIUZpbGUgbmFtZSB0byByZXBvcnQgdG8gdGhlIHNlcnZlcqRraW5kIqZzY2FsYXKDpG5hbWWoZmlsZU5hbWWkdHlwZaZTdHJpbmeka2luZASFpHR5cGWmU3RyaW5npG5hbWWkdHlwZadjb21tZW502XJNSU1FIHR5cGUgKGh0dHBzOi8vZGV2ZWxvcGVyLm1vemlsbGEub3JnL2VuLVVTL2RvY3MvV2ViL0hUVFAvQmFzaWNzX29mX0hUVFAvTUlNRV90eXBlcykuIERlZmF1bHRzIHRvIGVtcHR5IHN0cmluZy6ka2luZCKmc2NhbGFyg6RuYW1lpHR5cGWkdHlwZaZTdHJpbmeka2luZASGpHR5cGWtSHR0cF9SZXNwb25zZaN1cmm/d3JhcDovL2Vucy93cmFwcy5ldGg6aHR0cEAxLjEuMKluYW1lc3BhY2WkSHR0cKpuYXRpdmVUeXBlqFJlc3BvbnNlpGtpbmTNBAGqcHJvcGVydGllc5SFpHR5cGWjSW50pG5hbWWmc3RhdHVzqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWmc3RhdHVzpHR5cGWjSW50qHJlcXVpcmVkw6RraW5kBIWkdHlwZaZTdHJpbmekbmFtZapzdGF0dXNUZXh0qHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWqc3RhdHVzVGV4dKR0eXBlplN0cmluZ6hyZXF1aXJlZMOka2luZASEpHR5cGWzTWFwPFN0cmluZywgU3RyaW5nPqRuYW1lp2hlYWRlcnOjbWFwhqR0eXBls01hcDxTdHJpbmcsIFN0cmluZz6mc2NhbGFyhKRuYW1lp2hlYWRlcnOkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEpGtpbmTOAAQAAqRuYW1lp2hlYWRlcnOja2V5hKRuYW1lp2hlYWRlcnOkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEpXZhbHVlhKRuYW1lp2hlYWRlcnOkdHlwZaZTdHJpbmeocmVxdWlyZWTDpGtpbmQEpGtpbmQihKR0eXBlplN0cmluZ6RuYW1lpGJvZHmka2luZCKmc2NhbGFyg6RuYW1lpGJvZHmkdHlwZaZTdHJpbmeka2luZASzaW1wb3J0ZWRNb2R1bGVUeXBlc5GHo3Vyab93cmFwOi8vZW5zL3dyYXBzLmV0aDpodHRwQDEuMS4wqW5hbWVzcGFjZaRIdHRwqm5hdGl2ZVR5cGWmTW9kdWxlq2lzSW50ZXJmYWNlwqR0eXBlq0h0dHBfTW9kdWxlpGtpbmTNAQCnbWV0aG9kc5KGpG5hbWWjZ2V0pnJldHVyboSkdHlwZa1IdHRwX1Jlc3BvbnNlpG5hbWWjZ2V0pGtpbmQipm9iamVjdIOkbmFtZaNnZXSkdHlwZa1IdHRwX1Jlc3BvbnNlpGtpbmTNIACkdHlwZaZNZXRob2Ska2luZECocmVxdWlyZWTDqWFyZ3VtZW50c5KFpHR5cGWmU3RyaW5npG5hbWWjdXJsqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWjdXJspHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBISkdHlwZaxIdHRwX1JlcXVlc3SkbmFtZadyZXF1ZXN0pGtpbmQipm9iamVjdIOkbmFtZadyZXF1ZXN0pHR5cGWsSHR0cF9SZXF1ZXN0pGtpbmTNIACGpG5hbWWkcG9zdKZyZXR1cm6EpHR5cGWtSHR0cF9SZXNwb25zZaRuYW1lpHBvc3Ska2luZCKmb2JqZWN0g6RuYW1lpHBvc3SkdHlwZa1IdHRwX1Jlc3BvbnNlpGtpbmTNIACkdHlwZaZNZXRob2Ska2luZECocmVxdWlyZWTDqWFyZ3VtZW50c5KFpHR5cGWmU3RyaW5npG5hbWWjdXJsqHJlcXVpcmVkw6RraW5kIqZzY2FsYXKEpG5hbWWjdXJspHR5cGWmU3RyaW5nqHJlcXVpcmVkw6RraW5kBISkdHlwZaxIdHRwX1JlcXVlc3SkbmFtZadyZXF1ZXN0pGtpbmQipm9iamVjdIOkbmFtZadyZXF1ZXN0pHR5cGWsSHR0cF9SZXF1ZXN0pGtpbmTNIACxaW1wb3J0ZWRFbnVtVHlwZXORhqR0eXBlsUh0dHBfUmVzcG9uc2VUeXBlqWNvbnN0YW50c5KkVEVYVKZCSU5BUlmjdXJpv3dyYXA6Ly9lbnMvd3JhcHMuZXRoOmh0dHBAMS4xLjCpbmFtZXNwYWNlpEh0dHCqbmF0aXZlVHlwZaxSZXNwb25zZVR5cGWka2luZM0CCA==" -); - -export const wasmPackage = WasmPackage.from( - wrap_info, - wrap_wasm -); diff --git a/packages/js/client-config-builder/src/bundles/embeds/ipfs-http-client/wrap.wasm b/packages/js/client-config-builder/src/bundles/embeds/ipfs-http-client/wrap.wasm deleted file mode 100644 index ea5752edf07656a454d362d81317406f92cff322..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 150523 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 - }; diff --git a/packages/js/client-config-builder/src/types/IClientConfigBuilder.ts b/packages/js/client-config-builder/src/types/IClientConfigBuilder.ts deleted file mode 100644 index edc5f8fdf2..0000000000 --- a/packages/js/client-config-builder/src/types/IClientConfigBuilder.ts +++ /dev/null @@ -1,259 +0,0 @@ -import { BuilderConfig } from "./configs"; -import { BuildOptions } from "./BuildOptions"; - -import { CoreClientConfig, Wrapper, IWrapPackage } from "@polywrap/core-js"; -import { UriResolverLike } from "@polywrap/uri-resolvers-js"; - -export interface IClientConfigBuilder { - config: BuilderConfig; - - // $start: IClientConfigBuilder-build - /** - * Build a sanitized core client configuration that can be passed to the PolywrapClient or PolywrapCoreClient constructors - * - * @param options - Use a custom wrapper cache or resolver - * @returns CoreClientConfig that results from applying all the steps in the builder pipeline - */ - build(options?: BuildOptions): CoreClientConfig; - // $end - - // $start: IClientConfigBuilder-add - /** - * Add a partial BuilderConfig - * This is equivalent to calling each of the plural add functions: `addEnvs`, `addWrappers`, etc. - * - * @param config: a partial BuilderConfig - * @returns IClientConfigBuilder (mutated self) - */ - add(config: Partial): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-addDefaults - /** - * Add the default configuration bundle - * - * @returns IClientConfigBuilder (mutated self) - */ - addDefaults(): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-addWrapper - /** - * Add an embedded wrapper - * - * @param uri: uri of wrapper - * @param wrapper: wrapper to be added - * @returns IClientConfigBuilder (mutated self) - */ - addWrapper(uri: string, wrapper: Wrapper): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-addWrappers - /** - * Add one or more embedded wrappers. - * This is equivalent to calling addWrapper for each wrapper. - * - * @param uriWrappers: an object where keys are uris and wrappers are value - * @returns IClientConfigBuilder (mutated self) - */ - addWrappers(uriWrappers: Record): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-removeWrapper - /** - * Remove an embedded wrapper - * - * @param uri: the wrapper's URI - * @returns IClientConfigBuilder (mutated self) - */ - removeWrapper(uri: string): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-addPackage - /** - * Add an embedded wrap package - * - * @param uri: uri of wrapper - * @param wrapPackage: package to be added - * @returns IClientConfigBuilder (mutated self) - */ - addPackage(uri: string, wrapPackage: IWrapPackage): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-addPackages - /** - * Add one or more embedded wrap packages - * This is equivalent to calling addPackage for each package - * - * @param uriPackages: an object where keys are uris and packages are value - * @returns IClientConfigBuilder (mutated self) - */ - addPackages(uriPackages: Record): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-removePackage - /** - * Remove an embedded wrap package - * - * @param uri: the package's URI - * @returns IClientConfigBuilder (mutated self) - */ - removePackage(uri: string): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-addEnv - /** - * Add an Env. - * If an Env is already associated with the uri, it is modified. - * - * @param uri: the wrapper's URI to associate with the Env - * @param env: an object with the env variables for the uri - * @returns IClientConfigBuilder (mutated self) - */ - addEnv(uri: string, env: Record): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-addEnvs - /** - * Add one or more Envs - * This is equivalent to calling addEnv for each Env - * - * @param uriEnvs: and object where key is the uri and value is the another object with the env variables for the uri - * @returns IClientConfigBuilder (mutated self) - */ - addEnvs( - uriEnvs: Record> - ): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-removeEnv - /** - * Remove an Env - * - * @param uri: the URI associated with the Env - * @returns IClientConfigBuilder (mutated self) - */ - removeEnv(uri: string): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-setEnv - /** - * Add an Env. - * If an Env is already associated with the uri, it is replaced. - * - * @param uri: the wrapper's URI to associate with the Env - * @param env: an object with the environment variables for the uri - * @returns IClientConfigBuilder (mutated self) - */ - setEnv(uri: string, env: Record): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-addInterfaceImplementation - /** - * Register an implementation of a single interface - * - * @param interfaceUri: the URI of the interface - * @param implementationUri: the URI of the implementation - * @returns IClientConfigBuilder (mutated self) - */ - addInterfaceImplementation( - interfaceUri: string, - implementationUri: string - ): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-addInterfaceImplementations - /** - * Register one or more implementation of a single interface - * - * @param interfaceUri: the URI of the interface - * @param implementationUris: a list of URIs for the implementations - * @returns IClientConfigBuilder (mutated self) - */ - addInterfaceImplementations( - interfaceUri: string, - implementationUris: Array - ): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-removeInterfaceImplementation - /** - * Remove an implementation of a single interface - * - * @param interfaceUri: the URI of the interface - * @param implementationUri: the URI of the implementation - * @returns IClientConfigBuilder (mutated self) - */ - removeInterfaceImplementation( - interfaceUri: string, - implementationUri: string - ): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-addRedirect - /** - * Add a redirect from one URI to another - * - * @param from: the URI to redirect from - * @param to: the URI to redirect to - * @returns IClientConfigBuilder (mutated self) - */ - addRedirect(from: string, to: string): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-addRedirects - /** - * Add an array of URI redirects - * - * @param redirects: an object where key is from and value is to - * @returns IClientConfigBuilder (mutated self) - */ - addRedirects(redirects: Record): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-removeRedirect - /** - * Remove a URI redirect - * - * @param from: the URI that is being redirected - * @returns IClientConfigBuilder (mutated self) - */ - removeRedirect(from: string): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-addResolver - /** - * Add a URI Resolver, capable of resolving a URI to a wrapper - * - * @remarks - * A UriResolverLike can be any one of: - * IUriResolver - * | IUriRedirect - * | IUriPackage - * | IUriWrapper - * | UriResolverLike[]; - * - * @param resolver: A UriResolverLike - * @returns IClientConfigBuilder (mutated self) - */ - addResolver(resolver: UriResolverLike): IClientConfigBuilder; - // $end - - // $start: IClientConfigBuilder-addResolvers - /** - * Add one or more URI Resolvers, capable of resolving URIs to wrappers - * - * @remarks - * A UriResolverLike can be any one of: - * IUriResolver - * | IUriRedirect - * | IUriPackage - * | IUriWrapper - * | UriResolverLike[]; - * - * @param resolvers: A list of UriResolverLike - * @returns IClientConfigBuilder (mutated self) - */ - addResolvers(resolvers: UriResolverLike[]): IClientConfigBuilder; - // $end -} diff --git a/packages/js/client-config-builder/src/types/configs/BuilderConfig.ts b/packages/js/client-config-builder/src/types/configs/BuilderConfig.ts deleted file mode 100644 index cf40457877..0000000000 --- a/packages/js/client-config-builder/src/types/configs/BuilderConfig.ts +++ /dev/null @@ -1,11 +0,0 @@ -import { Wrapper, IWrapPackage } from "@polywrap/core-js"; -import { UriResolverLike } from "@polywrap/uri-resolvers-js"; - -export interface BuilderConfig { - envs: Record>; - interfaces: Record>; - redirects: Record; - wrappers: Record; - packages: Record; - resolvers: UriResolverLike[]; -} diff --git a/packages/js/client-config-builder/src/types/configs/index.ts b/packages/js/client-config-builder/src/types/configs/index.ts deleted file mode 100644 index 621970bfec..0000000000 --- a/packages/js/client-config-builder/src/types/configs/index.ts +++ /dev/null @@ -1 +0,0 @@ -export * from "./BuilderConfig"; diff --git a/packages/js/client-config-builder/src/types/index.ts b/packages/js/client-config-builder/src/types/index.ts deleted file mode 100644 index 2d1ce18b86..0000000000 --- a/packages/js/client-config-builder/src/types/index.ts +++ /dev/null @@ -1,3 +0,0 @@ -export * from "./configs"; -export * from "./IClientConfigBuilder"; -export * from "./BuildOptions"; diff --git a/packages/js/client-config-builder/tsconfig.build.json b/packages/js/client-config-builder/tsconfig.build.json deleted file mode 100644 index ccebf665da..0000000000 --- a/packages/js/client-config-builder/tsconfig.build.json +++ /dev/null @@ -1,12 +0,0 @@ -{ - "extends": "./tsconfig.json", - "compilerOptions": { - "outDir": "build" - }, - "include": [ - "./src/**/*.ts" - ], - "exclude": [ - "./src/**/__tests__", - ] -} \ No newline at end of file diff --git a/packages/js/client-config-builder/tsconfig.json b/packages/js/client-config-builder/tsconfig.json deleted file mode 100644 index 02827831c0..0000000000 --- a/packages/js/client-config-builder/tsconfig.json +++ /dev/null @@ -1,8 +0,0 @@ -{ - "extends": "../../../tsconfig", - "include": [ - "./src/**/*.ts", - "./examples/**/*.ts" - ], - "exclude": [] -} diff --git a/packages/js/client/.gitignore b/packages/js/client/.gitignore deleted file mode 100644 index dbb01bb64d..0000000000 --- a/packages/js/client/.gitignore +++ /dev/null @@ -1,3 +0,0 @@ -/examples/**/*.d.ts -/examples/**/*.js -/examples/**/*.js.map diff --git a/packages/js/client/README.md b/packages/js/client/README.md deleted file mode 100644 index 9d5ca0b146..0000000000 --- a/packages/js/client/README.md +++ /dev/null @@ -1,72 +0,0 @@ -# @polywrap/client-js - -npm - - -
-
-The Polywrap client extends the PolywrapCoreClient to provide UX features, such as an additional constructor and additional configuration options. - -## Installation - -```bash -npm install --save @polywrap/client-js -``` - -## Usage - -### Instantiate - -Use the PolywrapClient [constructor](#constructor) to instantiate the client with the default configuration bundle. - -```ts - import { PolywrapClient } from "@polywrap/client-js"; - - const client = new PolywrapClient(); -``` - -### Configure - -Use the `@polywrap/client-config-builder-js` package to build a custom configuration for your project. - -```ts - const config = new ClientConfigBuilder().addDefaults().build(); - - const client = new PolywrapClient(config); -``` - -### Invoke - -Invoke a wrapper. - -```ts - const result = await client.invoke({ - uri: "ens/helloworld.dev.polywrap.eth", - method: "logMessage", - args: { - message: "Hello World!" - } - }); - - if (!result.ok) throw result.error; - - const value = result.value; -``` - -# Reference - -## Configuration - -Below you will find a reference of object definitions which can be used to configure the Polywrap client. Please note that the intended way of configuring the client is to use the `ClientConfigBuilder`, as explained above. - -## PolywrapClient - -### Constructor -```ts - /** - * Instantiate a PolywrapClient - * - * @param config - a client configuration - */ - constructor(config?: CoreClientConfig) -``` \ No newline at end of file diff --git a/packages/js/client/examples/quickstart.ts b/packages/js/client/examples/quickstart.ts deleted file mode 100644 index 4872b7381b..0000000000 --- a/packages/js/client/examples/quickstart.ts +++ /dev/null @@ -1,38 +0,0 @@ -import { ClientConfigBuilder, PolywrapClient } from "../build"; - -export function instantiate(): PolywrapClient { - // /* $: quickstart-instantiate */ import { PolywrapClient } from "@polywrap/client-js"; - - const client = new PolywrapClient(); - // $end - - return client; -} - -export function configure(): PolywrapClient { - // $start: quickstart-configure - const config = new ClientConfigBuilder().addDefaults().build(); - - const client = new PolywrapClient(config); - // $end - - return client; -} - -export async function invoke(): Promise { - const client = new PolywrapClient(); - // $start: quickstart-invoke - const result = await client.invoke({ - uri: "ens/helloworld.dev.polywrap.eth", - method: "logMessage", - args: { - message: "Hello World!" - } - }); - - if (!result.ok) throw result.error; - - const value = result.value; - // $end - return value; -} diff --git a/packages/js/client/examples/tsconfig.examples.json b/packages/js/client/examples/tsconfig.examples.json deleted file mode 100644 index f37de53612..0000000000 --- a/packages/js/client/examples/tsconfig.examples.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "extends": "../tsconfig.json", - "include": [ - "./**/*.ts" - ], -} \ No newline at end of file diff --git a/packages/js/client/jest.config.js b/packages/js/client/jest.config.js deleted file mode 100644 index b99d42000f..0000000000 --- a/packages/js/client/jest.config.js +++ /dev/null @@ -1,12 +0,0 @@ -module.exports = { - collectCoverage: true, - preset: 'ts-jest', - testEnvironment: 'node', - testMatch: ["**/?(*.)+(spec|test).[jt]s?(x)"], - modulePathIgnorePatterns: ["./src/__tests__/e2e/helpers.ts", "\\.polywrap"], - globals: { - 'ts-jest': { - diagnostics: false - } - } -}; diff --git a/packages/js/client/package.json b/packages/js/client/package.json deleted file mode 100644 index 22f11453f4..0000000000 --- a/packages/js/client/package.json +++ /dev/null @@ -1,97 +0,0 @@ -{ - "name": "@polywrap/client-js", - "description": "Polywrap Javascript Client", - "version": "0.10.0", - "license": "MIT", - "repository": { - "type": "git", - "url": "https://github.com/polywrap/toolchain.git" - }, - "main": "build/index.js", - "files": [ - "build" - ], - "scripts": { - "build": "yarn build:fast", - "build:docs": "yarn build:snippets && yarn build:readme", - "build:fast": "rimraf ./build && tsc --project tsconfig.build.json", - "lint": "eslint --color -c ../../../.eslintrc.js src/", - "test": "jest --passWithNoTests --runInBand --verbose --detectOpenHandles --forceExit", - "test:rust": "jest --passWithNoTests --runInBand --verbose --detectOpenHandles --forceExit -t 'client <-> wrappers .* rs'", - "test:watch": "yarn test -- --watch", - "build:snippets": "tsc --project ./examples/tsconfig.examples.json", - "build:readme": "yarn doc-snippets combine" - }, - "dependencies": { - "@polywrap/client-config-builder-js": "0.10.0", - "@polywrap/core-client-js": "0.10.0", - "@polywrap/core-js": "0.10.0", - "@polywrap/msgpack-js": "0.10.0", - "@polywrap/plugin-js": "0.10.0", - "@polywrap/result": "0.10.0", - "@polywrap/tracing-js": "0.10.0", - "@polywrap/uri-resolver-extensions-js": "0.10.0", - "@polywrap/uri-resolvers-js": "0.10.0", - "@polywrap/wrap-manifest-types-js": "0.10.0" - }, - "devDependencies": { - "@polywrap/cli-js": "0.10.0", - "@polywrap/test-cases": "0.10.0", - "@types/jest": "26.0.8", - "@types/prettier": "2.6.0", - "@types/uuid": "8.3.0", - "bignumber.js": "9.0.2", - "doc-snippets": "~1.0.0", - "jest": "26.6.3", - "polywrap": "0.10.0", - "rimraf": "3.0.2", - "ts-jest": "26.5.4", - "ts-loader": "8.0.17", - "ts-node": "10.9.1", - "typescript": "4.9.5", - "yaml": "2.1.3" - }, - "gitHead": "7346adaf5adb7e6bbb70d9247583e995650d390a", - "publishConfig": { - "access": "public" - }, - "doc-snippets": { - "extract": { - "include": [ - "./src/**/*.{ts,tsx,json,yaml,txt,md,graphql,cue}", - "./examples/**/*.{ts,tsx,json,yaml,txt,md,graphql,cue}" - ], - "ignore": [ - "./**/node_modules/**", - "./**/.polywrap/**", - "./**/__tests__/**" - ], - "dir": "./" - }, - "inject": { - "dir": "./readme", - "include": "./README.md" - }, - "startTokens": [ - { - "pattern": "$start: ", - "inline": false - }, - { - "pattern": "/* $: {SNIPPET_NAME} */", - "inline": true - } - ], - "endTokens": [ - { - "pattern": "$end", - "inline": false - }, - { - "pattern": "/* $ */", - "inline": true - } - ], - "outputDir": "./" - } -} diff --git a/packages/js/client/readme/README.md b/packages/js/client/readme/README.md deleted file mode 100644 index 237221ea04..0000000000 --- a/packages/js/client/readme/README.md +++ /dev/null @@ -1,53 +0,0 @@ -# @polywrap/client-js - -npm - - -
-
-The Polywrap client extends the PolywrapCoreClient to provide UX features, such as an additional constructor and additional configuration options. - -## Installation - -```bash -npm install --save @polywrap/client-js -``` - -## Usage - -### Instantiate - -Use the PolywrapClient [constructor](#constructor) to instantiate the client with the default configuration bundle. - -```ts -$snippet: quickstart-instantiate -``` - -### Configure - -Use the `@polywrap/client-config-builder-js` package to build a custom configuration for your project. - -```ts -$snippet: quickstart-configure -``` - -### Invoke - -Invoke a wrapper. - -```ts -$snippet: quickstart-invoke -``` - -# Reference - -## Configuration - -Below you will find a reference of object definitions which can be used to configure the Polywrap client. Please note that the intended way of configuring the client is to use the `ClientConfigBuilder`, as explained above. - -## PolywrapClient - -### Constructor -```ts -$snippet: PolywrapClient-constructor -``` \ No newline at end of file diff --git a/packages/js/client/src/PolywrapClient.ts b/packages/js/client/src/PolywrapClient.ts deleted file mode 100644 index 978bb06868..0000000000 --- a/packages/js/client/src/PolywrapClient.ts +++ /dev/null @@ -1,239 +0,0 @@ -import { InvokerOptions, TryResolveUriOptions } from "./types"; - -import { PolywrapCoreClient } from "@polywrap/core-client-js"; -import { - CoreClientConfig, - GetFileOptions, - GetImplementationsOptions, - InvokeResult, - IUriResolutionContext, - IUriResolver, - ReadonlyUriMap, - Uri, - UriPackageOrWrapper, - ValidateOptions, - WrapError, - Wrapper, - WrapperEnv, -} from "@polywrap/core-js"; -import { Result, ResultErr, ResultOk } from "@polywrap/result"; -import { - compareSignature, - DeserializeManifestOptions, - ImportedModuleDefinition, - WrapManifest, -} from "@polywrap/wrap-manifest-types-js"; -import { Tracer, TracerConfig } from "@polywrap/tracing-js"; -import { ClientConfigBuilder } from "@polywrap/client-config-builder-js"; - -export class PolywrapClient extends PolywrapCoreClient { - // $start: PolywrapClient-constructor - /** - * Instantiate a PolywrapClient - * - * @param config - a client configuration - */ - constructor(config?: CoreClientConfig) /* $ */ { - super(config ?? new ClientConfigBuilder().addDefaults().build()); - } - - /** - * Enable tracing for intricate debugging - * - * @remarks - * Tracing uses the @polywrap/tracing-js package - * - * @param tracerConfig - configure options such as the tracing level - * @returns void - */ - public setTracingEnabled(tracerConfig?: Partial): void { - if (tracerConfig?.consoleEnabled || tracerConfig?.httpEnabled) { - Tracer.enableTracing("PolywrapClient", tracerConfig); - } else { - Tracer.disableTracing(); - } - } - - @Tracer.traceMethod("PolywrapClient: getConfig") - public getConfig(): CoreClientConfig { - return super.getConfig(); - } - - @Tracer.traceMethod("PolywrapClient: getInterfaces") - public getInterfaces(): ReadonlyUriMap | undefined { - return super.getInterfaces(); - } - - @Tracer.traceMethod("PolywrapClient: getEnvs") - public getEnvs(): ReadonlyUriMap | undefined { - return super.getEnvs(); - } - - @Tracer.traceMethod("PolywrapClient: getResolver") - public getResolver(): IUriResolver { - return super.getResolver(); - } - - @Tracer.traceMethod("PolywrapClient: getEnvByUri") - public getEnvByUri( - uri: TUri - ): WrapperEnv | undefined { - return super.getEnvByUri(Uri.from(uri)); - } - - @Tracer.traceMethod("PolywrapClient: getManifest") - public async getManifest( - uri: TUri - ): Promise> { - return super.getManifest(Uri.from(uri)); - } - - @Tracer.traceMethod("PolywrapClient: getFile") - public async getFile( - uri: TUri, - options: GetFileOptions - ): Promise> { - return super.getFile(Uri.from(uri), options); - } - - @Tracer.traceMethod("PolywrapClient: getImplementations") - public async getImplementations( - uri: TUri, - options?: GetImplementationsOptions - ): Promise> { - return super.getImplementations(Uri.from(uri), options); - } - - @Tracer.traceMethod("PolywrapClient: invokeWrapper") - public async invokeWrapper< - TData = unknown, - TUri extends Uri | string = string - >( - options: InvokerOptions & { wrapper: Wrapper } - ): Promise> { - return super.invokeWrapper({ - ...options, - uri: Uri.from(options.uri), - }); - } - - @Tracer.traceMethod("PolywrapClient: invoke") - public async invoke( - options: InvokerOptions - ): Promise> { - return super.invoke({ - ...options, - uri: Uri.from(options.uri), - }); - } - - @Tracer.traceMethod("PolywrapClient: tryResolveUri") - public async tryResolveUri( - options: TryResolveUriOptions - ): Promise> { - return super.tryResolveUri({ - ...options, - uri: Uri.from(options.uri), - }); - } - - @Tracer.traceMethod("PolywrapClient: loadWrapper") - loadWrapper( - uri: Uri, - resolutionContext?: IUriResolutionContext, - options?: DeserializeManifestOptions - ): Promise> { - return super.loadWrapper(Uri.from(uri), resolutionContext, options); - } - - // $start: PolywrapCoreClient-validate - /** - * Validate a wrapper, given a URI. - * Optionally, validate the full ABI and/or recursively validate imports. - * - * @param uri - the Uri to resolve - * @param options - { abi?: boolean; recursive?: boolean } - * @returns A Promise with a Result containing a boolean or Error - */ - @Tracer.traceMethod("PolywrapClient: validateConfig") - public async validate /* $ */( - uri: TUri, - options: ValidateOptions - ): Promise> { - const wrapper = await this.loadWrapper(Uri.from(uri)); - if (!wrapper.ok) { - return ResultErr(new Error(wrapper.error?.message)); - } - - const { abi } = await wrapper.value.getManifest(); - const importedModules: ImportedModuleDefinition[] = - abi.importedModuleTypes || []; - - const importUri = (importedModuleType: ImportedModuleDefinition) => { - return this.tryResolveUri({ uri: importedModuleType.uri }); - }; - const resolvedModules = await Promise.all(importedModules.map(importUri)); - const modulesNotFound = resolvedModules.filter(({ ok }) => !ok) as { - error: Error; - }[]; - - if (modulesNotFound.length) { - const missingModules = modulesNotFound.map(({ error }) => { - const uriIndex = error?.message.indexOf("\n"); - return error?.message.substring(0, uriIndex); - }); - const error = new Error(JSON.stringify(missingModules)); - return ResultErr(error); - } - - if (options.abi) { - for (const importedModule of importedModules) { - const importedModuleManifest = await this.getManifest( - importedModule.uri - ); - if (!importedModuleManifest.ok) { - return ResultErr(importedModuleManifest.error); - } - const importedMethods = - importedModuleManifest.value.abi.moduleType?.methods || []; - - const expectedMethods = importedModules.find( - ({ uri }) => importedModule.uri === uri - ); - - const errorMessage = `ABI from Uri: ${importedModule.uri} is not compatible with Uri: ${uri}`; - for (const [i, _] of Object.keys(importedMethods).entries()) { - const importedMethod = importedMethods[i]; - - if (expectedMethods?.methods && expectedMethods?.methods.length < i) { - const expectedMethod = expectedMethods?.methods[i]; - const areEqual = compareSignature(importedMethod, expectedMethod); - - if (!areEqual) return ResultErr(new Error(errorMessage)); - } else { - return ResultErr(new Error(errorMessage)); - } - } - } - } - - if (options.recursive) { - const validateImportedModules = importedModules.map(({ uri }) => - this.validate(uri, options) - ); - const resolverUris = await Promise.all(validateImportedModules); - const invalidUris = resolverUris.filter(({ ok }) => !ok) as { - error: Error; - }[]; - if (invalidUris.length) { - const missingUris = invalidUris.map(({ error }) => { - const uriIndex = error?.message.indexOf("\n"); - return error?.message.substring(0, uriIndex); - }); - const error = new Error(JSON.stringify(missingUris)); - return ResultErr(error); - } - } - return ResultOk(true); - } -} diff --git a/packages/js/client/src/__tests__/core/embedded-package.spec.ts b/packages/js/client/src/__tests__/core/embedded-package.spec.ts deleted file mode 100644 index 66b0f872d0..0000000000 --- a/packages/js/client/src/__tests__/core/embedded-package.spec.ts +++ /dev/null @@ -1,179 +0,0 @@ -import fs from "fs"; -import path from "path"; -import { GetPathToTestWrappers } from "@polywrap/test-cases"; -import { InMemoryFileReader, WasmPackage } from "@polywrap/wasm-js"; -import { IWrapPackage } from "@polywrap/core-js"; -import { Result, ResultErr, ResultOk } from "@polywrap/result"; -import { PolywrapClient } from "../../PolywrapClient"; -import { ClientConfigBuilder } from "@polywrap/client-config-builder-js"; - -jest.setTimeout(200000); - -const wrapperPath = `${GetPathToTestWrappers()}/subinvoke/00-subinvoke/implementations/as`; -const wrapperUri = `fs/${wrapperPath}`; - -describe("Embedded package", () => { - it("can invoke an embedded package", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")); - const wasmModuleBuffer = fs.readFileSync( - path.join(wrapperPath, "wrap.wasm") - ); - - let wrapPackage = WasmPackage.from(manifestBuffer, wasmModuleBuffer); - const config = new ClientConfigBuilder() - .addDefaults() - .addPackage(wrapperUri, wrapPackage) - .build(); - const client = new PolywrapClient(config); - - const result = await client.invoke({ - uri: wrapperUri, - method: "add", - args: { - a: 1, - b: 1, - }, - }); - - if (!result.ok) fail(result.error); - expect(result.value).toBeTruthy(); - expect(typeof result.value).toBe("number"); - expect(result.value).toEqual(2); - }); - - it("can get a file from wrapper", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")); - const wasmModuleBuffer = fs.readFileSync( - path.join(wrapperPath, "wrap.wasm") - ); - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapPackage = WasmPackage.from(manifestBuffer, wasmModuleBuffer, { - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - }, - }); - - await testEmbeddedPackageWithFile(wrapPackage, testFilePath, testFileText); - }); - - it("can add embedded wrapper through file reader", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")); - const wasmModuleBuffer = fs.readFileSync( - path.join(wrapperPath, "wrap.wasm") - ); - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapPackage = WasmPackage.from({ - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else if (filePath === "wrap.info") { - return ResultOk(manifestBuffer); - } else if (filePath === "wrap.wasm") { - return ResultOk(wasmModuleBuffer); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - }, - }); - - await testEmbeddedPackageWithFile(wrapPackage, testFilePath, testFileText); - }); - - it("can add embedded wrapper with async wrap manifest", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")); - const wasmModuleBuffer = fs.readFileSync( - path.join(wrapperPath, "wrap.wasm") - ); - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapPackage = WasmPackage.from( - InMemoryFileReader.fromWasmModule(wasmModuleBuffer, { - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else if (filePath === "wrap.info") { - return ResultOk(manifestBuffer); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - }, - }) - ); - - await testEmbeddedPackageWithFile(wrapPackage, testFilePath, testFileText); - }); - - it("can add embedded wrapper with async wasm module", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")); - const wasmModuleBuffer = fs.readFileSync( - path.join(wrapperPath, "wrap.wasm") - ); - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapPackage = WasmPackage.from(manifestBuffer, { - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else if (filePath === "wrap.wasm") { - return ResultOk(wasmModuleBuffer); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - }, - }); - - await testEmbeddedPackageWithFile(wrapPackage, testFilePath, testFileText); - }); -}); - -const testEmbeddedPackageWithFile = async ( - wrapPackage: IWrapPackage, - filePath: string, - fileText: string -) => { - const config = new ClientConfigBuilder() - .addDefaults() - .addPackage(wrapperUri, wrapPackage) - .build(); - - const client = new PolywrapClient(config); - - const expectedManifest = await fs.promises.readFile( - `${wrapperPath}/wrap.info` - ); - const receivedManifestResult = await client.getFile(wrapperUri, { - path: "wrap.info", - }); - if (!receivedManifestResult.ok) fail(receivedManifestResult.error); - const receivedManifest = receivedManifestResult.value as Uint8Array; - expect(receivedManifest).toEqual(expectedManifest); - - const expectedWasmModule = await fs.promises.readFile( - `${wrapperPath}/wrap.wasm` - ); - const receivedWasmModuleResult = await client.getFile(wrapperUri, { - path: "wrap.wasm", - }); - if (!receivedWasmModuleResult.ok) fail(receivedWasmModuleResult.error); - const receivedWasmModule = receivedWasmModuleResult.value as Uint8Array; - expect(receivedWasmModule).toEqual(expectedWasmModule); - - const receivedHelloFileResult = await client.getFile(wrapperUri, { - path: filePath, - encoding: "utf-8", - }); - if (!receivedHelloFileResult.ok) fail(receivedHelloFileResult.error); - const receivedHelloFile = receivedHelloFileResult.value as Uint8Array; - - expect(receivedHelloFile).toEqual(fileText); -}; diff --git a/packages/js/client/src/__tests__/core/embedded-wrapper.spec.ts b/packages/js/client/src/__tests__/core/embedded-wrapper.spec.ts deleted file mode 100644 index 915e734464..0000000000 --- a/packages/js/client/src/__tests__/core/embedded-wrapper.spec.ts +++ /dev/null @@ -1,173 +0,0 @@ -import fs from "fs"; -import path from "path"; -import { GetPathToTestWrappers } from "@polywrap/test-cases"; -import { WasmWrapper, InMemoryFileReader } from "@polywrap/wasm-js"; -import { Wrapper } from "@polywrap/core-js"; -import { Result, ResultErr, ResultOk } from "@polywrap/result"; -import { PolywrapClient } from "../../PolywrapClient"; -import { ClientConfigBuilder } from "@polywrap/client-config-builder-js"; - -jest.setTimeout(200000); - -const wrapperPath = `${GetPathToTestWrappers()}/subinvoke/00-subinvoke/implementations/as`; -const simpleWrapperUri = `fs/${wrapperPath}`; - -describe("Embedded wrapper", () => { - it("can invoke an embedded wrapper", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")) - const wasmModuleBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.wasm")) - - let wrapper: Wrapper = await WasmWrapper.from( - manifestBuffer, - wasmModuleBuffer - ); - - const config = new ClientConfigBuilder() - .addDefaults() - .addWrapper(simpleWrapperUri, wrapper) - .build(); - - const client = new PolywrapClient(config); - - const result = await client.invoke({ - uri: simpleWrapperUri, - method: "add", - args: { - a: 1, - b: 1 - }, - }); - - if (!result.ok) fail(result.error); - expect(result.value).toBeTruthy(); - expect(typeof result.value).toBe("number"); - expect(result.value).toEqual(2); - }); - - it("can get a file from wrapper", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")) - const wasmModuleBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.wasm")) - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapper = await WasmWrapper.from(manifestBuffer, wasmModuleBuffer, { - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - }, - }); - - await testEmbeddedWrapperWithFile(wrapper, testFilePath, testFileText); - }); - - it("can add embedded wrapper through file reader", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")) - const wasmModuleBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.wasm")) - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapper = await WasmWrapper.from({ - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else if (filePath === "wrap.info") { - return ResultOk(manifestBuffer); - } else if (filePath === "wrap.wasm") { - return ResultOk(wasmModuleBuffer); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - }, - }); - - await testEmbeddedWrapperWithFile(wrapper, testFilePath, testFileText); - }); - - it("can add embedded wrapper with async wrap manifest", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")) - const wasmModuleBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.wasm")) - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapper = await WasmWrapper.from( - InMemoryFileReader.fromWasmModule(wasmModuleBuffer, { - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else if (filePath === "wrap.info") { - return ResultOk(manifestBuffer); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - }, - }) - ); - - await testEmbeddedWrapperWithFile(wrapper, testFilePath, testFileText); - }); - - it("can add embedded wrapper with async wasm module", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")) - const wasmModuleBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.wasm")) - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapper = await WasmWrapper.from(manifestBuffer, { - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else if (filePath === "wrap.wasm") { - return ResultOk(wasmModuleBuffer); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - }, - }); - - await testEmbeddedWrapperWithFile(wrapper, testFilePath, testFileText); - }); -}); - -const testEmbeddedWrapperWithFile = async ( - wrapper: WasmWrapper, - filePath: string, - fileText: string -) => { - const config = new ClientConfigBuilder() - .addDefaults() - .addWrapper(simpleWrapperUri, wrapper) - .build(); - - const client = new PolywrapClient(config); - - const expectedManifest = await fs.promises.readFile( - `${wrapperPath}/wrap.info` - ); - const receivedManifestResult = await client.getFile(simpleWrapperUri, { - path: "wrap.info", - }); - if (!receivedManifestResult.ok) fail(receivedManifestResult.error); - const receivedManifest = receivedManifestResult.value as Uint8Array; - expect(receivedManifest).toEqual(expectedManifest); - - const expectedWasmModule = - await fs.promises.readFile(`${wrapperPath}/wrap.wasm`); - const receivedWasmModuleResult = await client.getFile(simpleWrapperUri, { - path: "wrap.wasm", - }); - if (!receivedWasmModuleResult.ok) fail(receivedWasmModuleResult.error); - const receivedWasmModule = receivedWasmModuleResult.value as Uint8Array; - expect(receivedWasmModule).toEqual(expectedWasmModule); - - const receivedHelloFileResult = await client.getFile(simpleWrapperUri, { - path: filePath, - encoding: "utf-8", - }); - if (!receivedHelloFileResult.ok) fail(receivedHelloFileResult.error); - const receivedHelloFile = receivedHelloFileResult.value as Uint8Array; - - expect(receivedHelloFile).toEqual(fileText); -}; diff --git a/packages/js/client/src/__tests__/core/error-structure.spec.ts b/packages/js/client/src/__tests__/core/error-structure.spec.ts deleted file mode 100644 index 83c3aedb39..0000000000 --- a/packages/js/client/src/__tests__/core/error-structure.spec.ts +++ /dev/null @@ -1,533 +0,0 @@ -import fs from "fs"; -import path from "path"; -import { Uri } from "@polywrap/core-js"; - -import { GetPathToTestWrappers } from "@polywrap/test-cases"; -import { PolywrapClient } from "../.."; -import { WrapError, WrapErrorCode } from "@polywrap/core-js"; -import { incompatiblePlugin, mockPluginRegistration } from "../helpers"; -import { msgpackDecode, msgpackEncode } from "@polywrap/msgpack-js"; -import { - ClientConfigBuilder, - DefaultBundle, -} from "@polywrap/client-config-builder-js"; - -jest.setTimeout(660000); - -const asSubinvokeWrapperPath = `${GetPathToTestWrappers()}/subinvoke/00-subinvoke/implementations/as`; -const asSubinvokeWrapperUri = new Uri(`fs/${asSubinvokeWrapperPath}`); - -const asInvokeWrapperPath = `${GetPathToTestWrappers()}/subinvoke/01-invoke/implementations/as`; -const asInvokeWrapperUri = new Uri(`fs/${asInvokeWrapperPath}`); - -const asConsumerWrapperPath = `${GetPathToTestWrappers()}/subinvoke/02-consumer/implementations/as`; -const asConsumerWrapperUri = new Uri(`fs/${asConsumerWrapperPath}`); - -const rsSubinvokeWrapperPath = `${GetPathToTestWrappers()}/subinvoke/00-subinvoke/implementations/rs`; -const rsSubinvokeWrapperUri = new Uri(`fs/${rsSubinvokeWrapperPath}`); - -const rsInvokeWrapperPath = `${GetPathToTestWrappers()}/subinvoke/01-invoke/implementations/rs`; -const rsInvokeWrapperUri = new Uri(`fs/${rsInvokeWrapperPath}`); - -const rsConsumerWrapperPath = `${GetPathToTestWrappers()}/subinvoke/02-consumer/implementations/rs`; -const rsConsumerWrapperUri = new Uri(`fs/${rsConsumerWrapperPath}`); - -describe("Error structure", () => { - describe("URI resolution", () => { - let client = new PolywrapClient(); - test("Invoke a wrapper that is not found", async () => { - const result = await client.invoke({ - uri: asSubinvokeWrapperUri.uri + "-not-found", - method: "simpleMethod", - args: { - arg: "test", - }, - }); - - expect(result.ok).toBeFalsy(); - if (result.ok) throw Error("should never happen"); - - expect(result.error?.name).toEqual("WrapError"); - expect(result.error?.code).toEqual(WrapErrorCode.URI_RESOLVER_ERROR); - expect(result.error?.reason).toContain("A URI Resolver returned an error."); - expect( - result.error?.uri.endsWith( - "packages/test-cases/cases/wrappers/subinvoke/00-subinvoke/implementations/as-not-found" - ) - ).toBeTruthy(); - expect(result.error?.resolutionStack).toBeTruthy(); - }); - - test("Subinvoke a wrapper that is not found", async () => { - const result = await client.invoke({ - uri: asConsumerWrapperUri.uri, - method: "throwError", - args: { - a: "Hey", - }, - }); - - expect(result.ok).toBeFalsy(); - if (result.ok) throw Error("should never happen"); - - expect(result.error?.name).toEqual("WrapError"); - expect(result.error?.code).toEqual(WrapErrorCode.WRAPPER_INVOKE_ABORTED); - expect(result.error?.reason).toContain("SubInvocation exception encountered"); - expect( - result.error?.uri.endsWith( - "packages/test-cases/cases/wrappers/subinvoke/02-consumer/implementations/as" - ) - ).toBeTruthy(); - expect(result.error?.method).toEqual("throwError"); - expect(result.error?.args).toEqual('{\n "a": "Hey"\n}'); - expect(result.error?.source?.file).toEqual( - "~lib/@polywrap/wasm-as/containers/Result.ts" - ); - - expect(result.error?.innerError instanceof WrapError).toBeTruthy(); - const prev = result.error?.innerError as WrapError; - expect(prev.name).toEqual("WrapError"); - expect(prev.code).toEqual(WrapErrorCode.WRAPPER_INVOKE_ABORTED); - expect(prev.reason).toContain( - "A URI Resolver returned an error." - ); - expect(prev.uri).toEqual("wrap://ens/wraps.eth:ens-uri-resolver-ext@1.0.1"); - }); - - describe("Wasm wrapper - Assemblyscript", () => { - let client = new PolywrapClient(); - test("Invoke a wrapper with malformed arguments", async () => { - const result = await client.invoke({ - uri: asSubinvokeWrapperUri.uri, - method: "add", - args: { - a: "1", - b: 1, - }, - }); - - expect(result.ok).toBeFalsy(); - if (result.ok) throw Error("should never happen"); - - expect(result.error?.name).toEqual("WrapError"); - expect(result.error?.code).toEqual( - WrapErrorCode.WRAPPER_INVOKE_ABORTED - ); - expect(result.error?.reason.startsWith("__wrap_abort:")).toBeTruthy(); - expect( - result.error?.uri.endsWith( - "packages/test-cases/cases/wrappers/subinvoke/00-subinvoke/implementations/as" - ) - ).toBeTruthy(); - expect(result.error?.method).toEqual("add"); - expect(result.error?.args).toEqual('{\n "a": "1",\n "b": 1\n}'); - expect(result.error?.source?.file).toEqual( - "~lib/@polywrap/wasm-as/msgpack/ReadDecoder.ts" - ); - }); - - test("Invoke a wrapper method that doesn't exist", async () => { - const result = await client.invoke({ - uri: asSubinvokeWrapperUri.uri, - method: "notExistingMethod", - args: { - arg: "test", - }, - }); - - expect(result.ok).toBeFalsy(); - if (result.ok) throw Error("should never happen"); - - expect(result.error?.name).toEqual("WrapError"); - expect(result.error?.code).toEqual(WrapErrorCode.WRAPPER_INVOKE_FAIL); - expect( - result.error?.reason.startsWith("Could not find invoke function") - ).toBeTruthy(); - expect( - result.error?.uri.endsWith( - "packages/test-cases/cases/wrappers/subinvoke/00-subinvoke/implementations/as" - ) - ).toBeTruthy(); - expect(result.error?.method).toEqual("notExistingMethod"); - expect(result.error?.args).toEqual('{\n "arg": "test"\n}'); - expect( - result.error - ?.toString() - .split(WrapErrorCode.WRAPPER_INVOKE_FAIL.valueOf().toString()) - .length - ).toEqual(2); - expect(result.error?.innerError).toBeUndefined(); - }); - - test("Subinvoke error two layers deep", async () => { - const config = new ClientConfigBuilder() - .addDefaults() - .addRedirects({ - "ens/imported-invoke.eth": asInvokeWrapperUri.uri, - "ens/imported-subinvoke.eth": asSubinvokeWrapperUri.uri, - }); - - client = new PolywrapClient(config.build()); - const result = await client.invoke({ - uri: asConsumerWrapperUri.uri, - method: "throwError", - args: { - a: "Hey", - }, - }); - - expect(result.ok).toBeFalsy(); - if (result.ok) throw Error("should never happen"); - - expect(result.error?.name).toEqual("WrapError"); - expect(result.error?.code).toEqual( - WrapErrorCode.WRAPPER_INVOKE_ABORTED - ); - expect( - result.error?.reason.startsWith("SubInvocation exception encountered") - ).toBeTruthy(); - expect( - result.error?.uri.endsWith( - "packages/test-cases/cases/wrappers/subinvoke/02-consumer/implementations/as" - ) - ).toBeTruthy(); - expect(result.error?.method).toEqual("throwError"); - expect(result.error?.args).toEqual('{\n "a": "Hey"\n}'); - expect(result.error?.source?.file).toEqual( - "~lib/@polywrap/wasm-as/containers/Result.ts" - ); - - expect(result.error?.innerError instanceof WrapError).toBeTruthy(); - const prev = result.error?.innerError as WrapError; - expect(prev.name).toEqual("WrapError"); - expect(prev.code).toEqual(WrapErrorCode.WRAPPER_INVOKE_ABORTED); - expect( - prev.reason.startsWith("SubInvocation exception encountered") - ).toBeTruthy(); - expect(prev.uri).toEqual("wrap://ens/imported-invoke.eth"); - expect(prev.method).toEqual("invokeThrowError"); - expect(prev.args).toEqual('{\n "a": "Hey"\n}' ); - expect(prev.source?.file).toEqual( - "~lib/@polywrap/wasm-as/containers/Result.ts" - ); - - expect(prev.innerError instanceof WrapError).toBeTruthy(); - const prevOfPrev = prev.innerError as WrapError; - expect(prevOfPrev.name).toEqual("WrapError"); - expect(prevOfPrev.code).toEqual(WrapErrorCode.WRAPPER_INVOKE_ABORTED); - expect(prevOfPrev.reason).toEqual("__wrap_abort: Hey"); - expect( - prevOfPrev.uri.endsWith("wrap://ens/imported-subinvoke.eth") - ).toBeTruthy(); - expect(prevOfPrev.method).toEqual("subinvokeThrowError"); - expect(prev.args).toEqual('{\n "a": "Hey"\n}'); - expect(prevOfPrev.source?.file).toEqual( - "src/index.ts" - ); - }); - - describe("Incompatible version invocation", () => { - beforeAll(async () => { - const wrapperPath = `${GetPathToTestWrappers()}/subinvoke/00-subinvoke/implementations/as`; - const manifestBuffer = fs.readFileSync( - path.join(wrapperPath, "wrap.info") - ); - const wasmModuleBuffer = fs.readFileSync( - path.join(wrapperPath, "wrap.wasm") - ); - - fs.mkdirSync("tmp"); - const manifest: Record = (await msgpackDecode( - manifestBuffer - )) as Record; - manifest.version = "0.0.0.5" as any; - const modifiedManifestBuffer = msgpackEncode(manifest, false); - fs.writeFileSync("tmp/wrap.info", modifiedManifestBuffer); - fs.writeFileSync("tmp/wrap.wasm", wasmModuleBuffer); - }); - test("Invoke a wrapper with incompatible version", async () => { - const client = new PolywrapClient(); - const result = await client.invoke({ - uri: "wrap://fs/tmp", - method: "simpleMethod", - }); - - expect(result.ok).toBeFalsy(); - if (result.ok) throw Error("should never happen"); - - expect(result.error?.name).toEqual("WrapError"); - expect(result.error?.code).toEqual(WrapErrorCode.URI_RESOLVER_ERROR); - expect(result.error?.uri.endsWith("tmp")).toBeTruthy(); - expect(result.error?.resolutionStack).toBeDefined(); - expect(`${result.error?.cause}`).toContain( - `Unrecognized WrapManifest schema version "0.0.0.5"` - ); - }); - - test.skip("Invoke a plugin with incompatible version", async () => { - const builder = new ClientConfigBuilder(); - const config = builder - .addPackage("wrap://ens/plugin.eth", incompatiblePlugin()) - .build(); - const client = new PolywrapClient(config); - const result = await client.invoke({ - uri: "wrap://ens/plugin.eth", - method: "getData", - }); - - expect(result.ok).toBeFalsy(); - if (result.ok) throw Error("should never happen"); - - expect(result.error?.name).toEqual("WrapError"); - expect(result.error?.code).toEqual(WrapErrorCode.URI_RESOLVER_ERROR); - expect(result.error?.uri.endsWith("plugin.eth")).toBeTruthy(); - expect(result.error?.resolutionStack).toBeDefined(); - expect(`${result.error?.cause}`).toContain( - `Unrecognized WrapManifest schema version "0.0.0.5"` - ); - }); - - afterAll(() => { - fs.rmdirSync("tmp", { recursive: true }); - }); - }); - }); - - describe("Wasm wrapper - Rust", () => { - let client = new PolywrapClient(); - test("Invoke a wrapper with malformed arguments", async () => { - const result = await client.invoke({ - uri: rsSubinvokeWrapperUri.uri, - method: "add", - args: { - a: "1", - b: 1, - }, - }); - - expect(result.ok).toBeFalsy(); - if (result.ok) throw Error("should never happen"); - - expect(result.error?.name).toEqual("WrapError"); - expect(result.error?.code).toEqual( - WrapErrorCode.WRAPPER_INVOKE_ABORTED - ); - expect(result.error?.reason.startsWith("__wrap_abort:")).toBeTruthy(); - expect( - result.error?.uri.endsWith( - "packages/test-cases/cases/wrappers/subinvoke/00-subinvoke/implementations/rs" - ) - ).toBeTruthy(); - expect(result.error?.method).toEqual("add"); - expect(result.error?.args).toEqual('{\n "a": "1",\n "b": 1\n}'); - expect(result.error?.source?.file).toEqual( - "src/wrap/module/wrapped.rs" - ); - }); - - test("Invoke a wrapper method that doesn't exist", async () => { - const result = await client.invoke({ - uri: rsSubinvokeWrapperUri.uri, - method: "notExistingMethod", - args: { - arg: "test", - }, - }); - - expect(result.ok).toBeFalsy(); - if (result.ok) throw Error("should never happen"); - - expect(result.error?.name).toEqual("WrapError"); - expect(result.error?.code).toEqual(WrapErrorCode.WRAPPER_INVOKE_FAIL); - expect( - result.error?.reason.startsWith("Could not find invoke function") - ).toBeTruthy(); - expect( - result.error?.uri.endsWith( - "packages/test-cases/cases/wrappers/subinvoke/00-subinvoke/implementations/rs" - ) - ).toBeTruthy(); - expect(result.error?.method).toEqual("notExistingMethod"); - expect(result.error?.args).toEqual('{\n "arg": "test"\n}'); - expect( - result.error - ?.toString() - .split(WrapErrorCode.WRAPPER_INVOKE_FAIL.valueOf().toString()) - .length - ).toEqual(2); - expect(result.error?.innerError).toBeUndefined(); - }); - - test("Subinvoke error two layers deep", async () => { - const config = new ClientConfigBuilder() - .addDefaults() - .addRedirects({ - "ens/imported-invoke.eth": rsInvokeWrapperUri.uri, - "ens/imported-subinvoke.eth": rsSubinvokeWrapperUri.uri, - }); - - client = new PolywrapClient(config.build()); - const result = await client.invoke({ - uri: rsConsumerWrapperUri.uri, - method: "throwError", - args: { - a: "Hey", - }, - }); - - expect(result.ok).toBeFalsy(); - if (result.ok) throw Error("should never happen"); - - expect(result.error?.name).toEqual("WrapError"); - expect(result.error?.code).toEqual( - WrapErrorCode.WRAPPER_INVOKE_ABORTED - ); - expect( - result.error?.reason.startsWith("SubInvocation exception encountered") - ).toBeTruthy(); - expect( - result.error?.uri.endsWith( - "packages/test-cases/cases/wrappers/subinvoke/02-consumer/implementations/rs" - ) - ).toBeTruthy(); - expect(result.error?.method).toEqual("throwError"); - expect(result.error?.args).toEqual('{\n "a": "Hey"\n}'); - expect(result.error?.source?.file).toEqual("src/lib.rs"); - - expect(result.error?.innerError instanceof WrapError).toBeTruthy(); - const prev = result.error?.innerError as WrapError; - expect(prev.name).toEqual("WrapError"); - expect(prev.code).toEqual(WrapErrorCode.WRAPPER_INVOKE_ABORTED); - expect( - prev.reason.startsWith("SubInvocation exception encountered") - ).toBeTruthy(); - expect(prev.uri).toEqual("wrap://ens/imported-invoke.eth"); - expect(prev.method).toEqual("invokeThrowError"); - expect(prev.args).toEqual('{\n "a": "Hey"\n}'); - expect(prev.source?.file).toEqual("src/lib.rs"); - - expect(prev.innerError instanceof WrapError).toBeTruthy(); - const prevOfPrev = prev.innerError as WrapError; - expect(prevOfPrev.name).toEqual("WrapError"); - expect(prevOfPrev.code).toEqual(WrapErrorCode.WRAPPER_INVOKE_ABORTED); - expect(prevOfPrev.reason).toEqual("__wrap_abort: Hey"); - expect( - prevOfPrev.uri.endsWith("wrap://ens/imported-subinvoke.eth") - ).toBeTruthy(); - expect(prevOfPrev.method).toEqual("subinvokeThrowError"); - expect(prevOfPrev.args).toEqual('{\n "a": "Hey"\n}'); - expect(prevOfPrev.source?.file).toEqual( - "src/lib.rs" - ); - }); - }); - - describe("Plugin wrapper", () => { - const mockPlugin = mockPluginRegistration("plugin/mock") - const config = new ClientConfigBuilder() - .addDefaults().addPackage(mockPlugin.uri.uri, mockPlugin.package) - const client = new PolywrapClient(config.build()); - test("Invoke a plugin wrapper with malformed args", async () => { - const result = await client.invoke({ - uri: DefaultBundle.plugins.fileSystem.uri.uri, - method: "readFile", - args: { - pathh: "packages/js/client/src/__tests__/core/index.ts", - }, - }); - - expect(result.ok).toBeFalsy(); - if (result.ok) throw Error("should never happen"); - - expect(result.error?.name).toEqual("WrapError"); - expect(result.error?.code).toEqual( - WrapErrorCode.WRAPPER_INVOKE_ABORTED - ); - expect(result.error?.reason).toEqual( - 'The "path" argument must be of type string or an instance of Buffer or URL. Received undefined' - ); - expect(result.error?.uri).toEqual(DefaultBundle.plugins.fileSystem.uri.uri); - expect(result.error?.method).toEqual("readFile"); - expect(result.error?.args).toContain( - '{\n "pathh": "packages/js/client/src/__tests__/core/index.ts"\n}' - ); - expect(result.error?.source?.file).toEqual( - "node:internal/fs/promises" - ); - }); - - test("Invoke a plugin wrapper with a method that doesn't exist", async () => { - const result = await client.invoke({ - uri: DefaultBundle.plugins.fileSystem.uri.uri, - method: "readFileNotFound", - args: { - path: __dirname + "/index.ts", - }, - }); - - expect(result.ok).toBeFalsy(); - if (result.ok) throw Error("should never happen"); - - expect(result.error?.name).toEqual("WrapError"); - expect(result.error?.code).toEqual( - WrapErrorCode.WRAPPER_METHOD_NOT_FOUND - ); - expect( - result.error?.reason.startsWith("Plugin missing method ") - ).toBeTruthy(); - expect(result.error?.uri).toEqual(DefaultBundle.plugins.fileSystem.uri.uri); - expect(result.error?.method).toEqual("readFileNotFound"); - }); - - test("Invoke a plugin wrapper that throws explicitly", async () => { - const result = await client.invoke({ - uri: "wrap://plugin/mock", - method: "methodThatThrows", - }); - - expect(result.ok).toBeFalsy(); - if (result.ok) throw Error("should never happen"); - - expect(result.error?.name).toEqual("WrapError"); - expect(result.error?.code).toEqual( - WrapErrorCode.WRAPPER_INVOKE_ABORTED - ); - expect(result.error?.reason).toEqual("I'm throwing!"); - expect(result.error?.uri).toEqual("wrap://plugin/mock"); - expect( - result.error?.source?.file?.endsWith( - "packages/js/client/src/__tests__/helpers.ts" - ) - ).toBeTruthy(); - expect(result.error?.source?.row).toEqual(47); - expect(result.error?.source?.col).toEqual(15); - }); - - test("Invoke a plugin wrapper that throws unexpectedly", async () => { - const result = await client.invoke({ - uri: DefaultBundle.plugins.fileSystem.uri.uri, - method: "readFile", - args: { - path: "./this/path/does/not/exist.ts", - }, - }); - - expect(result.ok).toBeFalsy(); - if (result.ok) throw Error("should never happen"); - - expect(result.error?.name).toEqual("WrapError"); - expect(result.error?.code).toEqual( - WrapErrorCode.WRAPPER_INVOKE_ABORTED - ); - expect( - result.error?.reason.startsWith("ENOENT: no such file or directory") - ).toBeTruthy(); - expect(result.error?.uri).toEqual(DefaultBundle.plugins.fileSystem.uri.uri); - expect(result.error?.method).toEqual("readFile"); - expect(result.error?.args).toEqual( - '{\n "path": "./this/path/does/not/exist.ts"\n}' - ); - }); - }); - }); -}); diff --git a/packages/js/client/src/__tests__/core/plugin-wrapper.spec.ts b/packages/js/client/src/__tests__/core/plugin-wrapper.spec.ts deleted file mode 100644 index 94ceb90edf..0000000000 --- a/packages/js/client/src/__tests__/core/plugin-wrapper.spec.ts +++ /dev/null @@ -1,93 +0,0 @@ -import { PolywrapClient } from "../.."; -import { Uri } from "@polywrap/core-js"; -import { WrapManifest } from "@polywrap/wrap-manifest-types-js"; -import { PluginPackage, PluginModule } from "@polywrap/plugin-js"; -import { UriResolver } from "@polywrap/uri-resolvers-js"; -import { DefaultBundle } from "@polywrap/client-config-builder-js"; - -jest.setTimeout(200000); - -describe("plugin-wrapper", () => { - const mockMapPlugin = () => { - interface Config extends Record { - map: Map; - } - - class MockMapPlugin extends PluginModule { - async getMap(_: unknown) { - return this.config.map; - } - - updateMap(args: { map: Map }): Map { - for (const key of args.map.keys()) { - this.config.map.set( - key, - (this.config.map.get(key) || 0) + (args.map.get(key) || 0) - ); - } - return this.config.map; - } - } - - return new PluginPackage( - new MockMapPlugin({ - map: new Map().set("a", 1).set("b", 2), - }), - {} as WrapManifest - ); - }; - - test("plugin map types", async () => { - const implementationUri = Uri.from("wrap://ens/some-implementation.eth"); - const mockPlugin = mockMapPlugin(); - const client = new PolywrapClient( - { - resolver: UriResolver.from([ - { - uri: implementationUri, - package: mockPlugin, - }, - ]), - } - ); - - const getResult = await client.invoke({ - uri: implementationUri, - method: "getMap", - }); - - if (!getResult.ok) fail(getResult.error); - expect(getResult.value).toBeTruthy(); - expect(getResult.value).toMatchObject( - new Map().set("a", 1).set("b", 2) - ); - - const updateResult = await client.invoke({ - uri: implementationUri, - method: "updateMap", - args: { - map: new Map().set("b", 1).set("c", 5), - }, - }); - - if (!updateResult.ok) fail(updateResult.error); - expect(updateResult.value).toBeTruthy(); - expect(updateResult.value).toMatchObject( - new Map().set("a", 1).set("b", 3).set("c", 5) - ); - }); - - test("get manifest should fetch wrap manifest from plugin", async () => { - const client = new PolywrapClient( - { - resolver: UriResolver.from([ - { uri: DefaultBundle.plugins.http.uri, package: DefaultBundle.plugins.http.plugin }, - ]), - } - ); - const manifest = await client.getManifest(DefaultBundle.plugins.http.uri); - if (!manifest.ok) fail(manifest.error); - expect(manifest.value.type).toEqual("plugin"); - expect(manifest.value.name).toEqual("Http"); - }); -}); diff --git a/packages/js/client/src/__tests__/core/sanity.spec.ts b/packages/js/client/src/__tests__/core/sanity.spec.ts deleted file mode 100644 index 98b6218c24..0000000000 --- a/packages/js/client/src/__tests__/core/sanity.spec.ts +++ /dev/null @@ -1,126 +0,0 @@ -import { Uri, PolywrapClient } from "../.."; -import fs from "fs"; - -import { GetPathToTestWrappers } from "@polywrap/test-cases"; -import { IUriPackage, IUriRedirect } from "@polywrap/core-js"; -import { ResultErr } from "@polywrap/result"; -import { StaticResolver, UriResolverLike } from "@polywrap/uri-resolvers-js"; -import { WasmPackage } from "@polywrap/wasm-js"; -import { ClientConfigBuilder, DefaultBundle } from "@polywrap/client-config-builder-js"; -import { CoreClientConfig } from "@polywrap/core-js"; - -jest.setTimeout(200000); - -describe("sanity", () => { - test("default client config", () => { - const clientConfig = new PolywrapClient().getConfig(); - const expectedConfig = new ClientConfigBuilder().add(DefaultBundle.getConfig()).build(); - - expect( - JSON.stringify(clientConfig, null, 2) - ).toMatch( - JSON.stringify(expectedConfig, null, 2) - ); - }); - - test("validate requested uri is available", async () => { - const subinvokeUri = Uri.from("ens/imported-subinvoke.eth"); - const invokeUri = Uri.from("ens/imported-invoke.eth"); - const consumerUri = Uri.from("ens/consumer.eth"); - - const getPackage = async (name: string) => { - const manifest = await fs.promises.readFile( - `${GetPathToTestWrappers()}/subinvoke/${name}/implementations/as/wrap.info` - ); - - const wasmModule = await fs.promises.readFile( - `${GetPathToTestWrappers()}/subinvoke/${name}/implementations/as/wrap.wasm` - ); - return WasmPackage.from(manifest, wasmModule); - }; - - let config: CoreClientConfig = { - resolver: { - tryResolveUri: (_a: unknown, _b: unknown, _c: unknown) => { - return Promise.resolve(ResultErr()); - }, - }, - interfaces: undefined, - envs: undefined, - }; - - let client = new PolywrapClient(config); - let result = await client.validate(subinvokeUri, {}); - expect(result.ok).toBeFalsy(); - let resultError = (result as { error: Error }).error; - expect(resultError).toBeTruthy(); - expect(resultError.message).toContain("Error resolving URI"); - - let fooPackage: IUriPackage = { - uri: subinvokeUri, - package: await getPackage("00-subinvoke"), - }; - - let resolvers: UriResolverLike[] = [fooPackage]; - let staticResolver = StaticResolver.from(resolvers); - - config = { - resolver: staticResolver, - }; - - client = new PolywrapClient(config); - result = await client.validate(subinvokeUri, {}); - - expect(result.ok).toBeTruthy(); - - result = await client.validate(invokeUri, { - recursive: true, - }); - resultError = (result as { error: Error }).error; - expect(result.ok).toBeFalsy(); - expect(resultError).toBeTruthy(); - expect(resultError.message).toContain("Unable to find URI"); - - let modifiedFooWrapper: IUriPackage = { - uri: invokeUri, - package: await getPackage("01-invoke"), - }; - resolvers.push(modifiedFooWrapper); - staticResolver = StaticResolver.from(resolvers); - - const newConfig1: CoreClientConfig = { - resolver: staticResolver, - envs: config.envs, - interfaces: config.interfaces, - }; - client = new PolywrapClient(newConfig1); - - result = await client.validate(invokeUri, { - recursive: true, - }); - - expect(result.ok).toBeTruthy(); - - let redirectUri: IUriRedirect = { - from: subinvokeUri, - to: consumerUri, - }; - resolvers.push(redirectUri); - - staticResolver = StaticResolver.from(resolvers); - - const newConfig2: CoreClientConfig = { - resolver: staticResolver, - envs: newConfig1.envs, - interfaces: newConfig1.interfaces, - }; - - client = new PolywrapClient(newConfig2); - - result = await client.validate(invokeUri, { - abi: true, - }); - - expect(result.ok).toBeFalsy(); - }); -}); diff --git a/packages/js/client/src/__tests__/core/type-test-cases.ts b/packages/js/client/src/__tests__/core/type-test-cases.ts deleted file mode 100644 index ba2c28b021..0000000000 --- a/packages/js/client/src/__tests__/core/type-test-cases.ts +++ /dev/null @@ -1,811 +0,0 @@ -import { memoryStoragePlugin, ErrResult } from "../helpers"; -import { PolywrapClient } from "../../PolywrapClient"; - -import BigNumber from "bignumber.js"; -import { ClientConfigBuilder } from "@polywrap/client-config-builder-js"; -import { GetPathToTestWrappers } from "@polywrap/test-cases"; - -export const typeTestCases = (implementation: string) => { - describe("types test cases", () => { - test(`asyncify ${implementation}`, async () => { - const builder = new ClientConfigBuilder(); - builder.addDefaults().addPackage( - "wrap://ens/memory-storage.polywrap.eth", - memoryStoragePlugin() - ); - const client = new PolywrapClient(builder.build()); - - const uri = `fs/${GetPathToTestWrappers()}/asyncify/implementations/${implementation}`; - const subsequentInvokes = await client.invoke({ - uri: uri, - method: "subsequentInvokes", - args: { - numberOfTimes: 40, - }, - }); - - const expected = Array.from(new Array(40), (_, index) => - index.toString() - ); - - if (!subsequentInvokes.ok) fail(subsequentInvokes.error); - expect(subsequentInvokes.value).toBeTruthy(); - expect(subsequentInvokes.value).toEqual(expected); - - const localVarMethod = await client.invoke({ - uri, - method: "localVarMethod", - }); - - if (!localVarMethod.ok) fail(localVarMethod.error); - expect(localVarMethod.value).toBeTruthy(); - expect(localVarMethod.value).toEqual(true); - - const globalVarMethod = await client.invoke({ - uri, - method: "globalVarMethod", - }); - - if (!globalVarMethod.ok) fail(globalVarMethod.error); - expect(globalVarMethod.value).toBeTruthy(); - expect(globalVarMethod.value).toEqual(true); - - const largeStr = new Array(10000).join("polywrap "); - const setDataWithLargeArgs = await client.invoke({ - uri, - method: "setDataWithLargeArgs", - args: { - value: largeStr, - }, - }); - - if (!setDataWithLargeArgs.ok) fail(setDataWithLargeArgs.error); - expect(setDataWithLargeArgs.value).toBeTruthy(); - expect(setDataWithLargeArgs.value).toEqual(largeStr); - - const setDataWithManyArgs = await client.invoke({ - uri, - method: "setDataWithManyArgs", - args: { - valueA: "polywrap a", - valueB: "polywrap b", - valueC: "polywrap c", - valueD: "polywrap d", - valueE: "polywrap e", - valueF: "polywrap f", - valueG: "polywrap g", - valueH: "polywrap h", - valueI: "polywrap i", - valueJ: "polywrap j", - valueK: "polywrap k", - valueL: "polywrap l", - }, - }); - - if (!setDataWithManyArgs.ok) fail(setDataWithManyArgs.error); - expect(setDataWithManyArgs.value).toBeTruthy(); - expect(setDataWithManyArgs.value).toEqual( - "polywrap apolywrap bpolywrap cpolywrap dpolywrap epolywrap fpolywrap gpolywrap hpolywrap ipolywrap jpolywrap kpolywrap l" - ); - - const createObj = (i: number) => { - return { - propA: `a-${i}`, - propB: `b-${i}`, - propC: `c-${i}`, - propD: `d-${i}`, - propE: `e-${i}`, - propF: `f-${i}`, - propG: `g-${i}`, - propH: `h-${i}`, - propI: `i-${i}`, - propJ: `j-${i}`, - propK: `k-${i}`, - propL: `l-${i}`, - }; - }; - - const setDataWithManyStructuredArgs = await client.invoke({ - uri, - method: "setDataWithManyStructuredArgs", - args: { - valueA: createObj(1), - valueB: createObj(2), - valueC: createObj(3), - valueD: createObj(4), - valueE: createObj(5), - valueF: createObj(6), - valueG: createObj(7), - valueH: createObj(8), - valueI: createObj(9), - valueJ: createObj(10), - valueK: createObj(11), - valueL: createObj(12), - }, - }); - - if (!setDataWithManyStructuredArgs.ok) - fail(setDataWithManyStructuredArgs.error); - expect(setDataWithManyStructuredArgs.value).toBeTruthy(); - expect(setDataWithManyStructuredArgs.value).toBe(true); - }); - - test(`bigint-type ${implementation}`, async () => { - const uri = `fs/${GetPathToTestWrappers()}/bigint-type/implementations/${implementation}`; - const client = new PolywrapClient(); - let response = await client.invoke({ - uri, - method: "method", - args: { - arg1: "123456789123456789", - obj: { - prop1: "987654321987654321", - }, - }, - }); - let result = BigInt("123456789123456789") * BigInt("987654321987654321"); - if (!response.ok) fail(response.error); - expect(response.value).toBeTruthy(); - expect(response.value).toEqual(result.toString()); - - response = await client.invoke({ - uri, - method: "method", - args: { - arg1: "123456789123456789", - arg2: "123456789123456789123456789123456789", - obj: { - prop1: "987654321987654321", - prop2: "987654321987654321987654321987654321", - }, - }, - }); - - result = - BigInt("123456789123456789") * - BigInt("123456789123456789123456789123456789") * - BigInt("987654321987654321") * - BigInt("987654321987654321987654321987654321"); - - if (!response.ok) fail(response.error); - expect(response.value).toBeTruthy(); - expect(response.value).toEqual(result.toString()); - }); - - test(`bignumber-type ${implementation}`, async () => { - const uri = `fs/${GetPathToTestWrappers()}/bignumber-type/implementations/${implementation}`; - const client = new PolywrapClient(); - let response = await client.invoke({ - uri, - method: "method", - args: { - arg1: "1234.56789123456789", - obj: { - prop1: "98.7654321987654321", - }, - }, - }); - - let arg1 = new BigNumber("1234.56789123456789"); - let prop1 = new BigNumber("98.7654321987654321"); - let result = arg1.times(prop1); - - if (!response.ok) fail(response.error); - expect(response.value).toBeTruthy(); - expect(response.value).toEqual(result.toFixed()); - - response = await client.invoke({ - uri, - method: "method", - args: { - arg1: "1234567.89123456789", - arg2: "123456789123.456789123456789123456789", - obj: { - prop1: "987654.321987654321", - prop2: "987.654321987654321987654321987654321", - }, - }, - }); - - arg1 = new BigNumber("1234567.89123456789"); - const arg2 = new BigNumber("123456789123.456789123456789123456789"); - prop1 = new BigNumber("987654.321987654321"); - const prop2 = new BigNumber("987.654321987654321987654321987654321"); - result = arg1.times(arg2).times(prop1).times(prop2); - - if (!response.ok) fail(response.error); - expect(response.value).toBeTruthy(); - expect(response.value).toEqual(result.toFixed()); - }); - - test(`bytes-type ${implementation}`, async () => { - const uri = `fs/${GetPathToTestWrappers()}/bytes-type/implementations/${implementation}`; - const client = new PolywrapClient(); - const response = await client.invoke({ - uri, - method: "bytesMethod", - args: { - arg: { - prop: Buffer.from("Argument Value"), - }, - }, - }); - - if (!response.ok) fail(response.error); - expect(response.value).toBeTruthy(); - expect(response.value).toEqual( - new TextEncoder().encode("Argument Value Sanity!") - ); - }); - - test(`enum-type ${implementation}`, async () => { - const uri = `fs/${GetPathToTestWrappers()}/enum-type/implementations/${implementation}`; - const client = new PolywrapClient(); - - let method1a = await client.invoke({ - uri, - method: "method1", - args: { - en: 5, - }, - }); - - method1a = method1a as ErrResult; - expect(method1a.error).toBeTruthy(); - expect(method1a.error?.message).toMatch( - /__wrap_abort: Invalid value for enum 'SanityEnum': 5/gm - ); - - const method1b = await client.invoke({ - uri, - method: "method1", - args: { - en: 2, - optEnum: 1, - }, - }); - - if (!method1b.ok) fail(method1b.error); - expect(method1b.value).toBeTruthy(); - expect(method1b.value).toEqual(2); - - let method1c = await client.invoke({ - uri, - method: "method1", - args: { - en: 1, - optEnum: "INVALID", - }, - }); - - method1c = method1c as ErrResult; - expect(method1c.error).toBeTruthy(); - expect(method1c.error?.message).toMatch( - /__wrap_abort: Invalid key for enum 'SanityEnum': INVALID/gm - ); - - const method2a = await client.invoke({ - uri, - method: "method2", - args: { - enumArray: ["OPTION1", 0, "OPTION3"], - }, - }); - - if (!method2a.ok) fail(method2a.error); - expect(method2a.value).toBeTruthy(); - expect(method2a.value).toEqual([0, 0, 2]); - }); - - test(`invalid-types ${implementation}`, async () => { - const uri = `fs/${GetPathToTestWrappers()}/invalid-type/implementations/${implementation}`; - const client = new PolywrapClient(); - let invalidBoolIntSent = await client.invoke({ - uri, - method: "boolMethod", - args: { - arg: 10, - }, - }); - invalidBoolIntSent = invalidBoolIntSent as ErrResult; - expect(invalidBoolIntSent.error).toBeTruthy(); - expect(invalidBoolIntSent.error?.message).toMatch( - /Property must be of type 'bool'. Found 'int'./ - ); - - let invalidIntBoolSent = await client.invoke({ - uri, - method: "intMethod", - args: { - arg: true, - }, - }); - invalidIntBoolSent = invalidIntBoolSent as ErrResult; - expect(invalidIntBoolSent.error).toBeTruthy(); - expect(invalidIntBoolSent.error?.message).toMatch( - /Property must be of type 'int'. Found 'bool'./ - ); - - let invalidUIntArraySent = await client.invoke({ - uri, - method: "uIntMethod", - args: { - arg: [10], - }, - }); - invalidUIntArraySent = invalidUIntArraySent as ErrResult; - expect(invalidUIntArraySent.error).toBeTruthy(); - expect(invalidUIntArraySent.error?.message).toMatch( - /Property must be of type 'uint'. Found 'array'./ - ); - - let invalidBytesFloatSent = await client.invoke({ - uri, - method: "bytesMethod", - args: { - arg: 10.15, - }, - }); - - invalidBytesFloatSent = invalidBytesFloatSent as ErrResult; - expect(invalidBytesFloatSent.error).toBeTruthy(); - expect(invalidBytesFloatSent.error?.message).toMatch( - /Property must be of type 'bytes'. Found 'float64'./ - ); - - let invalidArrayMapSent = await client.invoke({ - uri, - method: "arrayMethod", - args: { - arg: { - prop: "prop", - }, - }, - }); - - invalidArrayMapSent = invalidArrayMapSent as ErrResult; - expect(invalidArrayMapSent.error).toBeTruthy(); - expect(invalidArrayMapSent.error?.message).toMatch( - /Property must be of type 'array'. Found 'map'./ - ); - }); - - test(`json-type ${implementation}`, async () => { - const uri = `fs/${GetPathToTestWrappers()}/json-type/implementations/${implementation}`; - const client = new PolywrapClient(); - type Json = string; - const value = JSON.stringify({ foo: "bar", bar: "bar" }); - const parseResponse = await client.invoke({ - uri, - method: "parse", - args: { - value, - }, - }); - - if (!parseResponse.ok) fail(parseResponse.error); - expect(parseResponse.value).toEqual(value); - - const values = [ - JSON.stringify({ bar: "foo" }), - JSON.stringify({ baz: "fuz" }), - ]; - - const stringifyResponse = await client.invoke({ - uri, - method: "stringify", - args: { - values, - }, - }); - - if (!stringifyResponse.ok) fail(stringifyResponse.error); - expect(stringifyResponse.value).toEqual(values.join("")); - - const object = { - jsonA: JSON.stringify({ foo: "bar" }), - jsonB: JSON.stringify({ fuz: "baz" }), - }; - - const stringifyObjectResponse = await client.invoke({ - uri, - method: "stringifyObject", - args: { - object, - }, - }); - - if (!stringifyObjectResponse.ok) fail(stringifyObjectResponse.error); - expect(stringifyObjectResponse.value).toEqual( - object.jsonA + object.jsonB - ); - - const json = { - valueA: 5, - valueB: "foo", - valueC: true, - }; - - const methodJSONResponse = await client.invoke({ - uri, - method: "methodJSON", - args: json, - }); - - if (!methodJSONResponse.ok) fail(methodJSONResponse.error); - const methodJSONResult = JSON.stringify(json); - expect(methodJSONResponse.value).toEqual(methodJSONResult); - - // @TODO: Remove this once https://github.com/polywrap/toolchain/issues/633 is implemented & tested - if (implementation === "rs") { - const reserved = { const: "hello", if: true }; - const parseReservedResponse = await client.invoke<{ - const: string; - if: boolean; - }>({ - uri, - method: "parseReserved", - args: { - json: JSON.stringify(reserved), - }, - }); - - if (!parseReservedResponse.ok) fail(parseReservedResponse.error); - expect(parseReservedResponse.value).toEqual(reserved); - - const stringifyReservedResponse = await client.invoke({ - uri, - method: "stringifyReserved", - args: { - reserved, - }, - }); - - if (!stringifyReservedResponse.ok) - fail(stringifyReservedResponse.error); - expect(stringifyReservedResponse.value).toEqual( - JSON.stringify(reserved) - ); - } - }); - - test(`numbers-type ${implementation}`, async () => { - const uri = `fs/${GetPathToTestWrappers()}/numbers-type/implementations/${implementation}`; - const client = new PolywrapClient(); - let i8Underflow = await client.invoke({ - uri, - method: "i8Method", - args: { - first: -129, // min i8 = -128 - second: 10, - }, - }); - - i8Underflow = i8Underflow as ErrResult; - expect(i8Underflow.error).toBeTruthy(); - expect(i8Underflow.error?.message).toMatch( - /integer overflow: value = -129; bits = 8/ - ); - - let u8Overflow = await client.invoke({ - uri, - method: "u8Method", - args: { - first: 256, // max u8 = 255 - second: 10, - }, - }); - u8Overflow = u8Overflow as ErrResult; - expect(u8Overflow.error).toBeTruthy(); - expect(u8Overflow.error?.message).toMatch( - /unsigned integer overflow: value = 256; bits = 8/ - ); - - let i16Underflow = await client.invoke({ - uri, - method: "i16Method", - args: { - first: -32769, // min i16 = -32768 - second: 10, - }, - }); - i16Underflow = i16Underflow as ErrResult; - expect(i16Underflow.error).toBeTruthy(); - expect(i16Underflow.error?.message).toMatch( - /integer overflow: value = -32769; bits = 16/ - ); - - let u16Overflow = await client.invoke({ - uri, - method: "u16Method", - args: { - first: 65536, // max u16 = 65535 - second: 10, - }, - }); - u16Overflow = u16Overflow as ErrResult; - expect(u16Overflow.error).toBeTruthy(); - expect(u16Overflow.error?.message).toMatch( - /unsigned integer overflow: value = 65536; bits = 16/ - ); - - let i32Underflow = await client.invoke({ - uri, - method: "i32Method", - args: { - first: -2147483649, // min i32 = -2147483648 - second: 10, - }, - }); - i32Underflow = i32Underflow as ErrResult; - expect(i32Underflow.error).toBeTruthy(); - expect(i32Underflow.error?.message).toMatch( - /integer overflow: value = -2147483649; bits = 32/ - ); - - let u32Overflow = await client.invoke({ - uri, - method: "u32Method", - args: { - first: 4294967296, // max u32 = 4294967295 - second: 10, - }, - }); - u32Overflow = u32Overflow as ErrResult; - expect(u32Overflow.error).toBeTruthy(); - expect(u32Overflow.error?.message).toMatch( - /unsigned integer overflow: value = 4294967296; bits = 32/ - ); - }); - - test(`object-type ${implementation}`, async () => { - const uri = `fs/${GetPathToTestWrappers()}/object-type/implementations/${implementation}`; - const client = new PolywrapClient(); - const method1a = await client.invoke({ - uri, - method: "method1", - args: { - arg1: { - prop: "arg1 prop", - nested: { - prop: "arg1 nested prop", - }, - }, - }, - }); - - if (!method1a.ok) fail(method1a.error); - expect(method1a.value).toBeTruthy(); - expect(method1a.value).toEqual([ - { - prop: "arg1 prop", - nested: { - prop: "arg1 nested prop", - }, - }, - { - prop: "", - nested: { - prop: "", - }, - }, - ]); - - const method1b = await client.invoke({ - uri, - method: "method1", - args: { - arg1: { - prop: "arg1 prop", - nested: { - prop: "arg1 nested prop", - }, - }, - arg2: { - prop: "arg2 prop", - circular: { - prop: "arg2 circular prop", - }, - }, - }, - }); - - if (!method1b.ok) fail(method1b.error); - expect(method1b.value).toBeTruthy(); - expect(method1b.value).toEqual([ - { - prop: "arg1 prop", - nested: { - prop: "arg1 nested prop", - }, - }, - { - prop: "arg2 prop", - nested: { - prop: "arg2 circular prop", - }, - }, - ]); - - const method2a = await client.invoke({ - uri, - method: "method2", - args: { - arg: { - prop: "arg prop", - nested: { - prop: "arg nested prop", - }, - }, - }, - }); - - if (!method2a.ok) fail(method2a.error); - expect(method2a.value).toBeTruthy(); - expect(method2a.value).toEqual({ - prop: "arg prop", - nested: { - prop: "arg nested prop", - }, - }); - - const method2b = await client.invoke({ - uri, - method: "method2", - args: { - arg: { - prop: "null", - nested: { - prop: "arg nested prop", - }, - }, - }, - }); - - if (!method2b.ok) fail(method2b.error); - expect(method2b.value).toEqual(null); - - const method3 = await client.invoke({ - uri, - method: "method3", - args: { - arg: { - prop: "arg prop", - nested: { - prop: "arg nested prop", - }, - }, - }, - }); - - if (!method3.ok) fail(method3.error); - expect(method3.value).toBeTruthy(); - expect(method3.value).toEqual([ - null, - { - prop: "arg prop", - nested: { - prop: "arg nested prop", - }, - }, - ]); - - const method4 = await client.invoke({ - uri, - method: "method4", - args: { - arg: { - prop: [49, 50, 51, 52], - }, - }, - }); - - if (!method4.ok) fail(method4.error); - expect(method4.value).toBeTruthy(); - expect(method4.value).toEqual({ - prop: "1234", - nested: { - prop: "nested prop", - }, - }); - }); - - test(`map-type ${implementation}`, async () => { - const uri = `fs/${GetPathToTestWrappers()}/map-type/implementations/${implementation}`; - const client = new PolywrapClient(); - const mapClass = new Map() - .set("Hello", 1) - .set("Heyo", 50); - const nestedMapClass = new Map>().set( - "Nested", - mapClass - ); - const mapRecord: Record = { - Hello: 1, - Heyo: 50, - }; - const nestedMapRecord: Record> = { - Nested: mapRecord, - }; - - const returnMapResponse1 = await client.invoke>({ - uri, - method: "returnMap", - args: { - map: mapClass, - }, - }); - if (!returnMapResponse1.ok) fail(returnMapResponse1.error); - expect(returnMapResponse1.value).toEqual(mapClass); - - const returnMapResponse2 = await client.invoke>({ - uri, - method: "returnMap", - args: { - map: mapRecord, - }, - }); - if (!returnMapResponse2.ok) fail(returnMapResponse2.error); - expect(returnMapResponse2.value).toEqual(mapClass); - - const getKeyResponse1 = await client.invoke({ - uri, - method: "getKey", - args: { - foo: { - map: mapClass, - nestedMap: nestedMapClass, - }, - key: "Hello", - }, - }); - if (!getKeyResponse1.ok) fail(getKeyResponse1.error); - expect(getKeyResponse1.value).toEqual(mapClass.get("Hello")); - - const getKeyResponse2 = await client.invoke({ - uri, - method: "getKey", - args: { - foo: { - map: mapRecord, - nestedMap: nestedMapRecord, - }, - key: "Heyo", - }, - }); - if (!getKeyResponse2.ok) fail(getKeyResponse2.error); - expect(getKeyResponse2.value).toEqual(mapRecord.Heyo); - - const returnCustomMap = await client.invoke<{ - map: Map; - nestedMap: Map>; - }>({ - uri, - method: "returnCustomMap", - args: { - foo: { - map: mapRecord, - nestedMap: nestedMapClass, - }, - }, - }); - if (!returnCustomMap.ok) fail(returnCustomMap.error); - expect(returnCustomMap.value).toEqual({ - map: mapClass, - nestedMap: nestedMapClass, - }); - - const returnNestedMap = await client.invoke< - Map> - >({ - uri, - method: "returnNestedMap", - args: { - foo: nestedMapClass, - }, - }); - if (!returnNestedMap.ok) fail(returnNestedMap.error); - expect(returnNestedMap.value).toEqual(nestedMapClass); - }); - }); -}; diff --git a/packages/js/client/src/__tests__/core/uri-resolution/histories/sanity.json b/packages/js/client/src/__tests__/core/uri-resolution/histories/sanity.json deleted file mode 100644 index 4b29e4c5bc..0000000000 --- a/packages/js/client/src/__tests__/core/uri-resolution/histories/sanity.json +++ /dev/null @@ -1,109 +0,0 @@ -[ - "wrap://ens/wraps.eth:uri-resolver-ext@1.1.0 => RequestSynchronizerResolver => uri (wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm)", - [ - "wrap://ens/wraps.eth:uri-resolver-ext@1.1.0 => ResolutionResultCacheResolver => uri (wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm)", - [ - "wrap://ens/wraps.eth:uri-resolver-ext@1.1.0 => PackageToWrapperResolver => uri (wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm)", - [ - "wrap://ens/wraps.eth:uri-resolver-ext@1.1.0 => UriResolverAggregator => uri (wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm)", - [ - "wrap://ens/wraps.eth:uri-resolver-ext@1.1.0 => StaticResolver - Miss", - "wrap://ens/wraps.eth:uri-resolver-ext@1.1.0 => ExtendableUriResolver => uri (wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm)", - [ - "wrap://ens/wraps.eth:async-ipfs-uri-resolver-ext@1.0.1 => RequestSynchronizerResolver => uri (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)", - [ - "wrap://ens/wraps.eth:async-ipfs-uri-resolver-ext@1.0.1 => ResolutionResultCacheResolver => uri (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)", - [ - "wrap://ens/wraps.eth:async-ipfs-uri-resolver-ext@1.0.1 => PackageToWrapperResolver => uri (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)", - [ - "wrap://ens/wraps.eth:async-ipfs-uri-resolver-ext@1.0.1 => UriResolverAggregator => uri (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)", - [ - "wrap://ens/wraps.eth:async-ipfs-uri-resolver-ext@1.0.1 => StaticResolver - Redirect (wrap://ens/wraps.eth:async-ipfs-uri-resolver-ext@1.0.1 - wrap://embed/async-ipfs-uri-resolver-ext@1.0.1) => uri (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)" - ] - ] - ] - ], - "wrap://embed/async-ipfs-uri-resolver-ext@1.0.1 => RequestSynchronizerResolver => wrapper (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)", - [ - "wrap://embed/async-ipfs-uri-resolver-ext@1.0.1 => ResolutionResultCacheResolver => wrapper (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)", - [ - "wrap://embed/async-ipfs-uri-resolver-ext@1.0.1 => PackageToWrapperResolver => wrapper (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)", - [ - "wrap://embed/async-ipfs-uri-resolver-ext@1.0.1 => UriResolverAggregator => package (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)", - [ - "wrap://embed/async-ipfs-uri-resolver-ext@1.0.1 => StaticResolver - Package (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1) => package (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)" - ] - ] - ] - ], - "wrap://ens/wraps.eth:uri-resolver-ext@1.1.0 => ResolverExtension (wrap://ens/wraps.eth:async-ipfs-uri-resolver-ext@1.0.1)", - "wrap://ens/wraps.eth:ens-text-record-uri-resolver-ext@1.0.1 => RequestSynchronizerResolver => uri (wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs)", - [ - "wrap://ens/wraps.eth:ens-text-record-uri-resolver-ext@1.0.1 => ResolutionResultCacheResolver => uri (wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs)", - [ - "wrap://ens/wraps.eth:ens-text-record-uri-resolver-ext@1.0.1 => PackageToWrapperResolver => uri (wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs)", - [ - "wrap://ens/wraps.eth:ens-text-record-uri-resolver-ext@1.0.1 => UriResolverAggregator => uri (wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs)", - [ - "wrap://ens/wraps.eth:ens-text-record-uri-resolver-ext@1.0.1 => StaticResolver - Redirect (wrap://ens/wraps.eth:ens-text-record-uri-resolver-ext@1.0.1 - wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs) => uri (wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs)" - ] - ] - ] - ], - "wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs => RequestSynchronizerResolver => wrapper (wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs)", - [ - "wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs => ResolutionResultCacheResolver => wrapper (wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs)", - [ - "wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs => PackageToWrapperResolver => wrapper (wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs)", - [ - "wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs => UriResolverAggregator => package (wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs)", - [ - "wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs => StaticResolver - Miss", - "wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs => ExtendableUriResolver => package (wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs)", - [ - "wrap://ens/wraps.eth:async-ipfs-uri-resolver-ext@1.0.1 => RequestSynchronizerResolver => uri (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)", - [ - "wrap://ens/wraps.eth:async-ipfs-uri-resolver-ext@1.0.1 => ResolutionResultCacheResolver (Cache) => uri (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)" - ], - "wrap://embed/async-ipfs-uri-resolver-ext@1.0.1 => RequestSynchronizerResolver => wrapper (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)", - [ - "wrap://embed/async-ipfs-uri-resolver-ext@1.0.1 => ResolutionResultCacheResolver (Cache) => wrapper (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)" - ], - "wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs => ResolverExtension (wrap://ens/wraps.eth:async-ipfs-uri-resolver-ext@1.0.1) => package (wrap://ipfs/QmXcHWtKkfrFmcczdMSXH7udsSyV3UJeoWzkaUqGBm1oYs)" - ] - ] - ] - ] - ], - "wrap://ens/wraps.eth:uri-resolver-ext@1.1.0 => ResolverExtension (wrap://ens/wraps.eth:ens-text-record-uri-resolver-ext@1.0.1) => uri (wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm)" - ] - ] - ] - ] - ], - "wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm => RequestSynchronizerResolver => wrapper (wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm)", - [ - "wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm => ResolutionResultCacheResolver => wrapper (wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm)", - [ - "wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm => PackageToWrapperResolver => wrapper (wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm)", - [ - "wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm => UriResolverAggregator => package (wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm)", - [ - "wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm => StaticResolver - Miss", - "wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm => ExtendableUriResolver => package (wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm)", - [ - "wrap://ens/wraps.eth:async-ipfs-uri-resolver-ext@1.0.1 => RequestSynchronizerResolver => uri (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)", - [ - "wrap://ens/wraps.eth:async-ipfs-uri-resolver-ext@1.0.1 => ResolutionResultCacheResolver (Cache) => uri (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)" - ], - "wrap://embed/async-ipfs-uri-resolver-ext@1.0.1 => RequestSynchronizerResolver => wrapper (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)", - [ - "wrap://embed/async-ipfs-uri-resolver-ext@1.0.1 => ResolutionResultCacheResolver (Cache) => wrapper (wrap://embed/async-ipfs-uri-resolver-ext@1.0.1)" - ], - "wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm => ResolverExtension (wrap://ens/wraps.eth:async-ipfs-uri-resolver-ext@1.0.1) => package (wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm)" - ] - ] - ] - ] - ] -] \ No newline at end of file diff --git a/packages/js/client/src/__tests__/core/uri-resolution/uri-resolution.spec.ts b/packages/js/client/src/__tests__/core/uri-resolution/uri-resolution.spec.ts deleted file mode 100644 index 1336e03970..0000000000 --- a/packages/js/client/src/__tests__/core/uri-resolution/uri-resolution.spec.ts +++ /dev/null @@ -1,117 +0,0 @@ -import { GetPathToTestWrappers } from "@polywrap/test-cases"; -import { - Uri, - IUriResolutionStep, - UriPackageOrWrapper, - UriResolutionContext, - buildCleanUriHistory, -} from "@polywrap/core-js"; -import { UriResolutionResult } from "@polywrap/uri-resolvers-js"; -import fs from "fs"; -import { Result } from "@polywrap/result"; -import { PolywrapClient, ClientConfigBuilder } from "../../../"; - -jest.setTimeout(200000); - -const expectResultWithHistory = async ( - receivedResult: Result, - expectedResult: Result, - uriHistory: IUriResolutionStep[], - historyFileName: string -): Promise => { - if (historyFileName && uriHistory) { - await expectHistory(uriHistory, historyFileName); - } - - expect(expectedResult.ok).toEqual(receivedResult.ok); - - if (expectedResult.ok) { - expect((receivedResult as { value: UriPackageOrWrapper }).value).toEqual( - expect.objectContaining(expectedResult.value) - ); - } else { - expect(expectedResult.error).toEqual( - (receivedResult as { error: unknown }).error - ); - } -}; - -const expectHistory = async ( - receivedHistory: IUriResolutionStep[] | undefined, - historyFileName: string -): Promise => { - if (!receivedHistory) { - fail("History is not defined"); - } - - let expectedCleanHistory = await fs.promises.readFile( - `${__dirname}/histories/${historyFileName}.json`, - "utf-8" - ); - - const receivedCleanHistory = replaceAll( - JSON.stringify(buildCleanUriHistory(receivedHistory), null, 2), - `${GetPathToTestWrappers()}`, - "$root-wrapper-dir" - ); - - expect(receivedCleanHistory).toEqual( - JSON.stringify(JSON.parse(expectedCleanHistory), null, 2) - ); -}; - -function replaceAll(str: string, strToReplace: string, replaceStr: string) { - return str.replace(new RegExp(strToReplace, "g"), replaceStr); -} - -describe("URI resolution", () => { - it("sanity", async () => { - const uri = new Uri("ens/wraps.eth:uri-resolver-ext@1.1.0"); - - const client = new PolywrapClient(); - - const resolutionContext = new UriResolutionContext(); - const result = await client.tryResolveUri({ uri, resolutionContext }); - - const expectResult = UriResolutionResult.ok( - Uri.from("wrap://ipfs/QmSAXrSLcmGUkQRrApAtG5qTPmuRMMX2Zf1wihpguDQfbm") - ); - - if (expectResult.ok) { - expectResult.value.type = "wrapper" - } - - await expectResultWithHistory( - result, - expectResult, - resolutionContext.getHistory(), - "sanity" - ); - }); - - it("can resolve uri with custom resolver", async () => { - const fromUri = new Uri(`test/from.eth`); - const redirectUri = new Uri(`test/to.eth`); - - const config = new ClientConfigBuilder() - .addDefaults() - .addResolver({ - tryResolveUri: async (uri: Uri) => { - if (uri.uri === fromUri.uri) { - return UriResolutionResult.ok(redirectUri); - } - - return UriResolutionResult.ok(uri); - }, - }) - .build(); - - const client = new PolywrapClient(config); - - const result = await client.tryResolveUri({ - uri: fromUri, - }); - - expect(result).toEqual(UriResolutionResult.ok(redirectUri)); - }); -}); diff --git a/packages/js/client/src/__tests__/core/wasm-wrapper.spec.ts b/packages/js/client/src/__tests__/core/wasm-wrapper.spec.ts deleted file mode 100644 index e98170ff9c..0000000000 --- a/packages/js/client/src/__tests__/core/wasm-wrapper.spec.ts +++ /dev/null @@ -1,208 +0,0 @@ -import { msgpackDecode } from "@polywrap/msgpack-js"; -import { GetPathToTestWrappers } from "@polywrap/test-cases"; -import fs from "fs"; -import { Uri, PolywrapClient, IWrapPackage } from "../.."; -import { WrapManifest } from "@polywrap/wrap-manifest-types-js"; -import { PluginModule, PluginPackage } from "@polywrap/plugin-js"; -import { UriResolver } from "@polywrap/uri-resolvers-js"; -import { ClientConfigBuilder } from "@polywrap/client-config-builder-js"; -import { mockPluginRegistration, ErrResult } from "../helpers"; - -jest.setTimeout(200000); - -const wrapperPath = `${GetPathToTestWrappers()}/subinvoke/00-subinvoke/implementations/rs`; -const wrapperUri = new Uri(`fs/${wrapperPath}`); - -describe("wasm-wrapper", () => { - const mockPlugin = (): IWrapPackage => { - class MockPlugin extends PluginModule<{}> { - add(_: unknown): string { - return "plugin response"; - } - } - - return new PluginPackage(new MockPlugin({}), {} as WrapManifest); - }; - - test("can invoke with string URI", async () => { - const client = new PolywrapClient(); - const result = await client.invoke({ - uri: wrapperUri.uri, - method: "add", - args: { - a: 1, - b: 1 - }, - }); - - if (!result.ok) fail(result.error); - expect(result.value).toBeTruthy(); - expect(typeof result.value).toBe("number"); - expect(result.value).toEqual(2); - }); - - test("can invoke with typed URI", async () => { - const client = new PolywrapClient(); - const result = await client.invoke({ - uri: wrapperUri, - method: "add", - args: { - a: 1, - b: 1 - }, - }); - - if (!result.ok) fail(result.error); - expect(result.value).toBeTruthy(); - expect(typeof result.value).toBe("number"); - expect(result.value).toEqual(2); - }); - - test("invoke with decode defaulted to true works as expected", async () => { - const client = new PolywrapClient(); - const result = await client.invoke({ - uri: wrapperUri.uri, - method: "add", - args: { - a: 1, - b: 1 - }, - }); - - if (!result.ok) fail(result.error); - expect(result.value).toBeTruthy(); - expect(typeof result.value).toBe("number"); - expect(result.value).toEqual(2); - }); - - test("invoke with decode set to false works as expected", async () => { - const client = new PolywrapClient(); - const result = await client.invoke({ - uri: wrapperUri, - method: "add", - args: { - a: 1, - b: 1 - }, - encodeResult: true, - }); - - if (!result.ok) fail(result.error); - expect(result.value).toBeTruthy(); - expect(result.value instanceof Uint8Array).toBeTruthy(); - expect(msgpackDecode(result.value as Uint8Array)).toEqual(2); - }); - - it("should invoke wrapper with custom redirects", async () => { - const config = new ClientConfigBuilder() - .addDefaults() - .addRedirect(wrapperUri.uri, "wrap://ens/mock.polywrap.eth") - .addPackage("wrap://ens/mock.polywrap.eth", mockPlugin()) - .build(); - - const client = new PolywrapClient(config); - - const result = await client.invoke({ - uri: wrapperUri, - method: "add", - args: { - a: 1, - b: 1 - }, - }); - - if (!result.ok) fail(result.error); - expect(result.value).toBeTruthy(); - expect(result.value).toEqual("plugin response"); - }); - - it("should allow clone + reconfigure of redirects", async () => { - let builder = new ClientConfigBuilder() - .add({ - packages: { "wrap://ens/mock.polywrap.eth": mockPlugin() }, - }) - .addDefaults(); - - const client = new PolywrapClient(builder.build()); - - const clientResult = await client.invoke({ - uri: wrapperUri.uri, - method: "add", - args: { - a: 1, - b: 1 - }, - }); - - if (!clientResult.ok) fail(clientResult.error); - expect(clientResult.value).toBeTruthy(); - expect(clientResult.value).toEqual(2); - - const redirects = { - [wrapperUri.uri]: "wrap://ens/mock.polywrap.eth", - }; - - builder = builder.add({ redirects }); - - const newClient = new PolywrapClient(builder.build()); - - const newClientResult = await newClient.invoke({ - uri: wrapperUri.uri, - method: "add", - args: { - a: 1, - b: 1 - }, - }); - - if (!newClientResult.ok) fail(newClientResult.error); - expect(newClientResult.value).toBeTruthy(); - expect(newClientResult.value).toEqual("plugin response"); - }); - - test("get file from wrapper", async () => { - const client = new PolywrapClient(); - - const expectedManifest = new Uint8Array( - await fs.promises.readFile(`${wrapperPath}/wrap.info`) - ); - - const receivedManifestResult = await client.getFile(wrapperUri, { - path: "./wrap.info", - }); - if (!receivedManifestResult.ok) fail(receivedManifestResult.error); - const receivedManifest = receivedManifestResult.value as Uint8Array; - - expect(receivedManifest).toEqual(expectedManifest); - - const expectedWasmModule = new Uint8Array( - await fs.promises.readFile(`${wrapperPath}/wrap.wasm`) - ); - - const receivedWasmModuleResult = await client.getFile(wrapperUri, { - path: "./wrap.wasm", - }); - if (!receivedWasmModuleResult.ok) fail(receivedWasmModuleResult.error); - const receivedWasmModule = receivedWasmModuleResult.value as Uint8Array; - - expect(receivedWasmModule).toEqual(expectedWasmModule); - - const pluginClient = new PolywrapClient({ - resolver: UriResolver.from([ - mockPluginRegistration("ens/mock-plugin.eth"), - ]), - }); - - let pluginGetFileResult = await pluginClient.getFile( - "ens/mock-plugin.eth", - { - path: "./index.js", - } - ); - - pluginGetFileResult = pluginGetFileResult as ErrResult; - expect(pluginGetFileResult.error?.message).toContain( - "client.getFile(...) is not implemented for Plugins." - ); - }); -}); diff --git a/packages/js/client/src/__tests__/core/wrap-features/env-case.ts b/packages/js/client/src/__tests__/core/wrap-features/env-case.ts deleted file mode 100644 index d55d0f0318..0000000000 --- a/packages/js/client/src/__tests__/core/wrap-features/env-case.ts +++ /dev/null @@ -1,221 +0,0 @@ -import { PluginPackage } from "@polywrap/plugin-js"; -import { RecursiveResolver } from "@polywrap/uri-resolvers-js"; -import { GetPathToTestWrappers } from "@polywrap/test-cases"; -import { PolywrapClient } from "../../../PolywrapClient"; -import { mockPluginRegistration } from "../../helpers"; -import { ClientConfigBuilder } from "@polywrap/client-config-builder-js"; -import { Uri, UriMap } from "@polywrap/core-js"; - -jest.setTimeout(200000); - -export const envTestCases = (implementation: string) => { - describe("env", () => { - test(implementation, async () => { - const externalWrapperPath = `${GetPathToTestWrappers()}/env-type/00-external/implementations/${implementation}`; - const { uri: externalWrapperUri } = Uri.from( - `file/${externalWrapperPath}` - ); - - const wrapperPath = `${GetPathToTestWrappers()}/env-type/01-main/implementations/${implementation}`; - const { uri: wrapperUri } = Uri.from(`file/${wrapperPath}`); - - const envs = { - [wrapperUri]: { - object: { - prop: "object string", - }, - str: "string", - optFilledStr: "optional string", - number: 10, - bool: true, - en: "FIRST", - array: [32, 23], - }, - [externalWrapperUri]: { - externalArray: [1, 2, 3], - externalString: "iamexternal", - }, - }; - - const builder = new ClientConfigBuilder(); - builder - .addDefaults() - .addEnvs(envs) - .addRedirect("ens/external-env.polywrap.eth", externalWrapperUri); - const client = new PolywrapClient(builder.build()); - const methodRequireEnvResult = await client.invoke({ - uri: wrapperUri, - method: "methodRequireEnv", - args: { - arg: "string", - }, - }); - if (!methodRequireEnvResult.ok) fail(methodRequireEnvResult.error); - expect(methodRequireEnvResult.value).toEqual({ - str: "string", - optFilledStr: "optional string", - optStr: null, - number: 10, - optNumber: null, - bool: true, - optBool: null, - object: { - prop: "object string", - }, - optObject: null, - en: 0, - optEnum: null, - array: [32, 23], - }); - - const subinvokeEnvMethodResult = await client.invoke({ - uri: wrapperUri, - method: "subinvokeEnvMethod", - args: { - arg: "string", - }, - }); - if (!subinvokeEnvMethodResult.ok) fail(subinvokeEnvMethodResult.error); - expect(subinvokeEnvMethodResult.value).toEqual({ - local: { - str: "string", - optFilledStr: "optional string", - optStr: null, - number: 10, - optNumber: null, - bool: true, - optBool: null, - object: { - prop: "object string", - }, - optObject: null, - en: 0, - optEnum: null, - array: [32, 23], - }, - external: { - externalArray: [1, 2, 3], - externalString: "iamexternal", - }, - }); - - const methodRequireEnvModuleTimeResult = await client.invoke({ - uri: wrapperUri, - method: "methodRequireEnv", - args: { - arg: "string", - }, - }); - if (!methodRequireEnvModuleTimeResult.ok) - fail(methodRequireEnvModuleTimeResult.error); - expect(methodRequireEnvModuleTimeResult.value).toEqual({ - str: "string", - optFilledStr: "optional string", - optStr: null, - number: 10, - optNumber: null, - bool: true, - optBool: null, - object: { - prop: "object string", - }, - optObject: null, - en: 0, - optEnum: null, - array: [32, 23], - }); - - const mockUpdatedEnvResult = await client.invoke({ - uri: wrapperUri, - method: "methodRequireEnv", - args: { - arg: "string", - }, - env: { - object: { - prop: "object another string", - }, - str: "another string", - optFilledStr: "optional string", - number: 10, - bool: true, - en: "FIRST", - array: [32, 23], - }, - }); - if (!mockUpdatedEnvResult.ok) fail(mockUpdatedEnvResult.error); - expect(mockUpdatedEnvResult.value).toEqual({ - str: "another string", - optFilledStr: "optional string", - optStr: null, - number: 10, - optNumber: null, - bool: true, - optBool: null, - object: { - prop: "object another string", - }, - optObject: null, - en: 0, - optEnum: null, - array: [32, 23], - }); - }); - }); - - describe("env client types", () => { - test("plugin env types", async () => { - const implementationUri = Uri.from("wrap://ens/some-implementation.eth"); - const envPlugin = mockPluginRegistration("ens/hello.eth"); - const client = new PolywrapClient({ - resolver: RecursiveResolver.from([ - { - uri: envPlugin.uri, - package: envPlugin.package, - }, - { from: Uri.from("ens/hello.eth"), to: implementationUri }, - ]), - envs: new UriMap([[Uri.from("wrap://ens/hello.eth"), { arg1: "10" }]]), - }); - - const mockEnv = await client.invoke({ - uri: Uri.from("ens/hello.eth"), - method: "mockEnv", - }); - - if (!mockEnv.ok) fail(mockEnv.error); - expect(mockEnv.value).toBeTruthy(); - expect(mockEnv.value).toMatchObject({ arg1: "10" }); - }); - - test("inline plugin env types", async () => { - const implementationUri = "wrap://ens/some-implementation.eth"; - interface MockEnv extends Record { - arg1: number; - } - - const client = new PolywrapClient({ - resolver: RecursiveResolver.from([ - { - uri: Uri.from(implementationUri), - package: PluginPackage.from((module) => ({ - mockEnv: (_, __, env: MockEnv): MockEnv => { - return env; - }, - })), - }, - ]), - envs: new UriMap([[Uri.from(implementationUri), { arg1: "10" }]]), - }); - - const mockEnv = await client.invoke({ - uri: Uri.from(implementationUri), - method: "mockEnv", - }); - - if (!mockEnv.ok) fail(mockEnv.error); - expect(mockEnv.value).toBeTruthy(); - expect(mockEnv.value).toMatchObject({ arg1: "10" }); - }); - }); -}; diff --git a/packages/js/client/src/__tests__/core/wrap-features/interface-implementation-case.ts b/packages/js/client/src/__tests__/core/wrap-features/interface-implementation-case.ts deleted file mode 100644 index 03ecdebced..0000000000 --- a/packages/js/client/src/__tests__/core/wrap-features/interface-implementation-case.ts +++ /dev/null @@ -1,310 +0,0 @@ -import { - ExtendableUriResolver, - Uri, - PolywrapClient, - UriMap, -} from "../../../index"; -import { ClientConfigBuilder } from "@polywrap/client-config-builder-js"; -import { UriResolver } from "@polywrap/uri-resolvers-js"; -import { mockPluginRegistration } from "../../helpers"; -import { GetPathToTestWrappers } from "@polywrap/test-cases"; - -jest.setTimeout(200000); - -export const interfaceInvokeCase = (implementation: string) => { - describe("interface invoke", () => { - test(`invoke wrappers ${implementation}`, async () => { - const interfaceUri = "wrap://ens/interface.eth"; - const implementationPath = `${GetPathToTestWrappers()}/interface-invoke/01-implementation/implementations/${implementation}`; - const implementationUri = `fs/${implementationPath}`; - - const config = new ClientConfigBuilder() - .addDefaults() - .addInterfaceImplementation(interfaceUri, implementationUri); - const client = new PolywrapClient(config.build()); - - const wrapperPath = `${GetPathToTestWrappers()}/interface-invoke/02-wrapper/implementations/${implementation}`; - const wrapperUri = `fs/${wrapperPath}`; - - const result = await client.invoke({ - uri: wrapperUri, - method: "moduleMethod", - args: { - arg: { - uint8: 1, - str: "Test String 1", - }, - }, - }); - - if (!result.ok) fail(result.error); - expect(result.value).toBeTruthy(); - expect(result.value).toEqual({ - uint8: 1, - str: "Test String 1", - }); - }); - }); - - describe("interface-implementations", () => { - it("should register interface implementations successfully", async () => { - const interfaceUri = Uri.from("wrap://ens/some-interface1.eth"); - const implementation1Uri = Uri.from( - "wrap://ens/some-implementation1.eth" - ); - const implementation2Uri = Uri.from( - "wrap://ens/some-implementation2.eth" - ); - - const client = new PolywrapClient({ - interfaces: new UriMap([ - [interfaceUri, [implementation1Uri, implementation2Uri]], - ]), - resolver: UriResolver.from({ - from: Uri.from("uri/foo"), - to: Uri.from("uri/bar"), - }), - }); - - const interfaces = client.getInterfaces(); - - expect(interfaces).toEqual(new UriMap([ - [interfaceUri, [implementation1Uri, implementation2Uri]], - ])); - - const implementations = await client.getImplementations(interfaceUri, { - applyResolution: false, - }); - - if (!implementations.ok) fail(implementations.error); - expect(implementations.value).toEqual([ - implementation1Uri, - implementation2Uri, - ]); - }); - - it("should get all implementations of interface", async () => { - const interface1Uri = Uri.from("wrap://ens/some-interface1.eth"); - const interface2Uri = Uri.from("wrap://ens/some-interface2.eth"); - const interface3Uri = Uri.from("wrap://ens/some-interface3.eth"); - - const implementation1Uri = Uri.from("wrap://ens/some-implementation.eth"); - const implementation2Uri = Uri.from( - "wrap://ens/some-implementation2.eth" - ); - const implementation3Uri = Uri.from( - "wrap://ens/some-implementation3.eth" - ); - const implementation4Uri = Uri.from( - "wrap://ens/some-implementation4.eth" - ); - - const client = new PolywrapClient({ - resolver: UriResolver.from([ - { - from: interface1Uri, - to: interface2Uri, - }, - { - from: implementation1Uri, - to: implementation2Uri, - }, - { - from: implementation2Uri, - to: implementation3Uri, - }, - mockPluginRegistration(implementation4Uri), - ]), - interfaces: new UriMap([ - [interface1Uri, [implementation1Uri, implementation2Uri]], - [interface2Uri, [implementation3Uri]], - [interface3Uri, [implementation3Uri, implementation4Uri]], - ]), - }); - - const implementations1 = await client.getImplementations(interface1Uri, { - applyResolution: true, - }); - const implementations2 = await client.getImplementations(interface2Uri, { - applyResolution: true, - }); - const implementations3 = await client.getImplementations(interface3Uri, { - applyResolution: true, - }); - - if (!implementations1.ok) fail(implementations1.error); - expect(implementations1.value).toEqual([ - implementation1Uri, - implementation2Uri, - implementation3Uri, - ]); - - if (!implementations2.ok) fail(implementations2.error); - expect(implementations2.value).toEqual([ - implementation1Uri, - implementation2Uri, - implementation3Uri, - ]); - - if (!implementations3.ok) fail(implementations3.error); - expect(implementations3.value).toEqual([ - implementation3Uri, - implementation4Uri, - ]); - }); - - it("should merge user-defined interface implementations with each other", async () => { - const interfaceUri = Uri.from("wrap://ens/interface.eth"); - const implementationUri1 = Uri.from("wrap://ens/implementation1.eth"); - const implementationUri2 = Uri.from("wrap://ens/implementation2.eth"); - - const config = new ClientConfigBuilder() - .addDefaults() - .addInterfaceImplementations(interfaceUri.uri, [ - implementationUri1.uri, - implementationUri2.uri, - ]) - .build(); - - const client = new PolywrapClient(config); - - const implementationUris = (client.getInterfaces() || new UriMap).get(interfaceUri); - - expect(implementationUris).toEqual([ - implementationUri1, - implementationUri2, - ]); - }); - - it("should merge user-defined interface implementations with defaults", async () => { - const interfaceUri = ExtendableUriResolver.defaultExtInterfaceUris[0]; - const implementationUri1 = Uri.from("wrap://ens/implementation1.eth"); - const implementationUri2 = Uri.from("wrap://ens/implementation2.eth"); - - const config = new ClientConfigBuilder() - .addDefaults() - .addInterfaceImplementations(interfaceUri.uri, [ - implementationUri1.uri, - implementationUri2.uri, - ]) - .build(); - - const client = new PolywrapClient(config); - - const implementationUris = (client.getInterfaces() ?? new UriMap).get(interfaceUri); - - const builder = new ClientConfigBuilder(); - const defaultClientConfig = builder.addDefaults().build(); - - expect(implementationUris).toEqual([ - ...((defaultClientConfig.interfaces ?? new UriMap).get(interfaceUri) || []), - implementationUri1, - implementationUri2, - ]); - }); - - test("get implementations - do not return plugins that are not explicitly registered", async () => { - const interfaceUri = Uri.from("wrap://ens/some-interface.eth"); - - const implementation1Uri = Uri.from( - "wrap://ens/some-implementation1.eth" - ); - const implementation2Uri = Uri.from( - "wrap://ens/some-implementation2.eth" - ); - - const client = new PolywrapClient({ - resolver: UriResolver.from([ - mockPluginRegistration(implementation1Uri), - ]), - interfaces: new UriMap([ - [interfaceUri, [implementation2Uri]], - ]), - }); - - const getImplementationsResult = await client.getImplementations( - interfaceUri, - { applyResolution: true } - ); - - if (!getImplementationsResult.ok) fail(getImplementationsResult.error); - expect(getImplementationsResult.value).toEqual([implementation2Uri]); - }); - - test("get implementations - return implementations for plugins which don't have interface stated in manifest", async () => { - const interfaceUri = Uri.from("wrap://ens/some-interface.eth"); - - const implementation1Uri = Uri.from( - "wrap://ens/some-implementation1.eth" - ); - const implementation2Uri = Uri.from( - "wrap://ens/some-implementation2.eth" - ); - - const client = new PolywrapClient({ - resolver: UriResolver.from([ - mockPluginRegistration(implementation1Uri), - ]), - interfaces: new UriMap([ - [interfaceUri, [implementation1Uri, implementation2Uri]], - ]), - }); - - const getImplementationsResult = await client.getImplementations( - interfaceUri, - { applyResolution: true } - ); - - if (!getImplementationsResult.ok) fail(getImplementationsResult.error); - expect(getImplementationsResult.value).toEqual([ - implementation1Uri, - implementation2Uri, - ]); - }); - - test("getImplementations - pass string or Uri", async () => { - const oldInterfaceUri = Uri.from("mock/old"); - const newInterfaceUri = Uri.from("mock/new"); - - const implementation1Uri = Uri.from( - "wrap://mock/some-implementation1" - ); - const implementation2Uri = Uri.from( - "wrap://mock/some-implementation2" - ); - - const config = new ClientConfigBuilder() - .addDefaults() - .addRedirect(oldInterfaceUri.uri, newInterfaceUri.uri) - .addInterfaceImplementation(oldInterfaceUri.uri, implementation1Uri.uri) - .addInterfaceImplementation(newInterfaceUri.uri, implementation2Uri.uri) - .build(); - - const client = new PolywrapClient(config); - - let result = await client.getImplementations(oldInterfaceUri, { - applyResolution: false, - }); - if (!result.ok) fail(result.error); - expect(result.value).toEqual([implementation1Uri]); - - result = await client.getImplementations(oldInterfaceUri, { - applyResolution: true, - }); - if (!result.ok) fail(result.error); - expect(result.value).toEqual([implementation1Uri, implementation2Uri]); - - let result2 = await client.getImplementations(oldInterfaceUri, { - applyResolution: false, - }); - if (!result2.ok) fail(result2.error); - expect(result2.value).toEqual([implementation1Uri]); - - result2 = await client.getImplementations(oldInterfaceUri, { - applyResolution: true, - }); - if (!result2.ok) fail(result2.error); - expect(result2.value).toEqual([implementation1Uri, implementation2Uri]); - }); - }); -}; diff --git a/packages/js/client/src/__tests__/core/wrap-features/subinvoke-case.ts b/packages/js/client/src/__tests__/core/wrap-features/subinvoke-case.ts deleted file mode 100644 index 6c994ddb01..0000000000 --- a/packages/js/client/src/__tests__/core/wrap-features/subinvoke-case.ts +++ /dev/null @@ -1,32 +0,0 @@ -import { GetPathToTestWrappers } from "@polywrap/test-cases"; -import { ClientConfigBuilder } from "@polywrap/client-config-builder-js"; -import { PolywrapClient } from "../../../PolywrapClient"; - -export const subinvokeCase = (implementation: string) => { - describe("wrapper subinvocation", () => { - test(implementation, async () => { - const subinvokeUri = `file/${GetPathToTestWrappers()}/subinvoke/00-subinvoke/implementations/${implementation}`; - const wrapperUri = `file/${GetPathToTestWrappers()}/subinvoke/01-invoke/implementations/${implementation}`; - - const builder = new ClientConfigBuilder(); - builder - .addDefaults() - .addRedirect("ens/imported-subinvoke.eth", subinvokeUri); - - const client = new PolywrapClient(builder.build()); - - const response = await client.invoke({ - uri: wrapperUri, - method: "addAndIncrement", - args: { - a: 1, - b: 1, - }, - }); - - if (!response.ok) fail(response.error); - expect(response.value).toBeTruthy(); - expect(response.value).toEqual(3); - }); - }); -}; diff --git a/packages/js/client/src/__tests__/e2e.spec.ts b/packages/js/client/src/__tests__/e2e.spec.ts deleted file mode 100644 index 09d21a5f02..0000000000 --- a/packages/js/client/src/__tests__/e2e.spec.ts +++ /dev/null @@ -1,15 +0,0 @@ -import { typeTestCases } from "./core/type-test-cases"; -import { subinvokeCase } from "./core/wrap-features/subinvoke-case"; -import { envTestCases } from "./core/wrap-features/env-case"; -import { interfaceInvokeCase } from "./core/wrap-features/interface-implementation-case"; - -export const supportedImplementations = ["as", "rs"]; -describe.each(supportedImplementations)( - "client <-> wrappers end to end", - (i) => { - typeTestCases(i); - subinvokeCase(i); - envTestCases(i); - interfaceInvokeCase(i); - } -); diff --git a/packages/js/client/src/__tests__/helpers.ts b/packages/js/client/src/__tests__/helpers.ts deleted file mode 100644 index 74a1a0b003..0000000000 --- a/packages/js/client/src/__tests__/helpers.ts +++ /dev/null @@ -1,74 +0,0 @@ -import { PluginModule, PluginPackage } from "@polywrap/plugin-js"; -import { latestWrapManifestVersion } from "@polywrap/wrap-manifest-types-js"; -import { parseSchema } from "@polywrap/schema-parse"; -import { Uri } from "@polywrap/core-js"; - -class MemoryStoragePlugin extends PluginModule> { - private _value: number; - - async getData(_: {}): Promise { - await this.sleep(50); - return this._value; - } - - async setData(args: { value: number }): Promise { - await this.sleep(50); - this._value = args.value; - return true; - } - - private sleep(ms: number) { - return new Promise((resolve) => setTimeout(resolve, ms)); - } -} - -export const memoryStoragePlugin = () => { - return PluginPackage.from(new MemoryStoragePlugin({}), { - name: "memoryStorage", - type: "plugin", - version: latestWrapManifestVersion, - abi: parseSchema(` - type Module { - getData: Int32! - setData(value: Int32!): Boolean! - } - `), - }); -}; - -export const mockPluginRegistration = (uri: string | Uri) => { - return { - uri: Uri.from(uri), - package: PluginPackage.from(() => ({ - simpleMethod: (_: unknown): string => { - return "plugin response"; - }, - methodThatThrows: (_: unknown): string => { - throw Error("I'm throwing!"); - }, - mockEnv(_, __, env): { a: number } & Record { - return env as unknown as { a: number } & Record; - }, - })), - }; -}; - -export type ErrResult = { ok: false; error: E | undefined }; - -export const incompatiblePlugin = () => { - class IncompatiblePlugin extends PluginModule> { - async getData(_: {}): Promise { - return 0; - } - } - return PluginPackage.from(new IncompatiblePlugin({}), { - name: "incompatiblePlugin", - type: "plugin", - version: "0.0.0.5" as any, - abi: parseSchema(` - type Module { - getData: Int32! - } - `), - }); -}; diff --git a/packages/js/client/src/index.ts b/packages/js/client/src/index.ts deleted file mode 100644 index e4aa0a3f44..0000000000 --- a/packages/js/client/src/index.ts +++ /dev/null @@ -1,6 +0,0 @@ -export * from "./PolywrapClient"; -export * from "@polywrap/core-js"; -export * from "@polywrap/core-client-js"; -export * from "@polywrap/uri-resolvers-js"; -export * from "@polywrap/uri-resolver-extensions-js"; -export * from "@polywrap/client-config-builder-js"; diff --git a/packages/js/client/src/types/InvokerOptions.ts b/packages/js/client/src/types/InvokerOptions.ts deleted file mode 100644 index ca34900bca..0000000000 --- a/packages/js/client/src/types/InvokerOptions.ts +++ /dev/null @@ -1,23 +0,0 @@ -import { IUriResolutionContext, Uri } from "@polywrap/core-js"; - -export interface InvokerOptions { - /** The Wrapper's URI */ - uri: TUri; - - /** Method to be executed. */ - method: string; - - /** - * Arguments for the method, structured as a map, - * removing the chance of incorrectly ordering arguments. - */ - args?: Record | Uint8Array; - - /** - * Env variables for the wrapper invocation. - */ - env?: Record; - - resolutionContext?: IUriResolutionContext; - encodeResult?: boolean; -} diff --git a/packages/js/client/src/types/TryResolveUriOptions.ts b/packages/js/client/src/types/TryResolveUriOptions.ts deleted file mode 100644 index 9f3aeac0f5..0000000000 --- a/packages/js/client/src/types/TryResolveUriOptions.ts +++ /dev/null @@ -1,7 +0,0 @@ -import { IUriResolutionContext, Uri } from "@polywrap/core-js"; - -export interface TryResolveUriOptions { - /** The Wrapper's URI */ - uri: TUri; - resolutionContext?: IUriResolutionContext; -} diff --git a/packages/js/client/src/types/index.ts b/packages/js/client/src/types/index.ts deleted file mode 100644 index 5bc0467005..0000000000 --- a/packages/js/client/src/types/index.ts +++ /dev/null @@ -1,2 +0,0 @@ -export * from "./InvokerOptions"; -export * from "./TryResolveUriOptions"; diff --git a/packages/js/client/tsconfig.build.json b/packages/js/client/tsconfig.build.json deleted file mode 100644 index ec6eea7b58..0000000000 --- a/packages/js/client/tsconfig.build.json +++ /dev/null @@ -1,12 +0,0 @@ -{ - "extends": "./tsconfig.json", - "compilerOptions": { - "outDir": "build" - }, - "include": [ - "./src/**/*.ts" - ], - "exclude": [ - "./src/**/__tests__" - ] -} diff --git a/packages/js/client/tsconfig.json b/packages/js/client/tsconfig.json deleted file mode 100644 index 61edd1723e..0000000000 --- a/packages/js/client/tsconfig.json +++ /dev/null @@ -1,16 +0,0 @@ -{ - "extends": "../../../tsconfig", - "compilerOptions": { - "lib": [ - "es2020", - "es2015", - "es5", - "dom" - ], - }, - "include": [ - "./src/**/*.ts", - "./examples/**/*.ts" - ], - "exclude": [] -} diff --git a/packages/js/core-client/.gitignore b/packages/js/core-client/.gitignore deleted file mode 100644 index dbb01bb64d..0000000000 --- a/packages/js/core-client/.gitignore +++ /dev/null @@ -1,3 +0,0 @@ -/examples/**/*.d.ts -/examples/**/*.js -/examples/**/*.js.map diff --git a/packages/js/core-client/README.md b/packages/js/core-client/README.md deleted file mode 100644 index 0f64b7e764..0000000000 --- a/packages/js/core-client/README.md +++ /dev/null @@ -1,270 +0,0 @@ -# @polywrap/core-client-js - -npm - - -
-
-The Polywrap JavaScript core client invokes wrapper functions. It's designed to run in any environment that can execute JavaScript (think websites, node scripts, etc.). It has TypeScript support. - -## Installation - -```bash -npm install --save @polywrap/core-client-js -``` - -## Usage - -### Instantiate - -Use the `@polywrap/client-config-builder-js` package to build a CoreClientConfig for your project, then use the PolywrapCoreClient [constructor](#constructor) to instantiate the client with your config. - -```ts - const config = new ClientConfigBuilder().addDefaults().build(); - - const client = new PolywrapCoreClient(config); -``` - -### Invoke - -Invoke a wrapper. - -```ts - const result = await client.invoke({ - uri: Uri.from("ens/helloworld.dev.polywrap.eth"), - method: "logMessage", - args: { - message: "Hello World!" - } - }); - - if (!result.ok) throw result.error; - - const value = result.value; -``` - -# Reference - -## PolywrapCoreClient - -### Constructor -```ts - /** - * Instantiate a PolywrapClient - * - * @param config - a core client configuration - */ - constructor(private _config: CoreClientConfig) -``` - -### getConfig -```ts - /** - * Returns the configuration used to instantiate the client - * - * @returns an immutable Polywrap client config - */ - public getConfig(): CoreClientConfig -``` - -### getInterfaces -```ts - /** - * returns all interfaces from the configuration used to instantiate the client - * - * @returns an array of interfaces and their registered implementations - */ - public getInterfaces(): ReadonlyUriMap | undefined -``` - -### getEnvs -```ts - /** - * returns all env registrations from the configuration used to instantiate the client - * - * @returns an array of env objects containing wrapper environmental variables - */ - public getEnvs(): ReadonlyUriMap | undefined -``` - -### getResolver -```ts - /** - * returns the URI resolver from the configuration used to instantiate the client - * - * @returns an object that implements the IUriResolver interface - */ - public getResolver(): IUriResolver -``` - -### getEnvByUri -```ts - /** - * returns an env (a set of environmental variables) from the configuration used to instantiate the client - * - * @param uri - the URI used to register the env - * @returns an env, or undefined if an env is not found at the given URI - */ - public getEnvByUri(uri: Uri): WrapperEnv | undefined -``` - -### getManifest -```ts - /** - * returns a package's wrap manifest - * - * @param uri - a wrap URI - * @returns a Result containing the WrapManifest if the request was successful - */ - public async getManifest( - uri: Uri - ): Promise> -``` - -### getFile -```ts - /** - * returns a file contained in a wrap package - * - * @param uri - a wrap URI - * @param options - { path: string; encoding?: "utf-8" | string } - * @returns a Promise of a Result containing a file if the request was successful - */ - public async getFile( - uri: Uri, - options: GetFileOptions - ): Promise> -``` - -### getImplementations -```ts - /** - * returns the interface implementations associated with an interface URI - * from the configuration used to instantiate the client - * - * @param uri - a wrap URI - * @param options - { applyResolution?: boolean; resolutionContext?: IUriResolutionContext } - * @returns a Result containing URI array if the request was successful - */ - public async getImplementations( - uri: Uri, - options: GetImplementationsOptions = {} - ): Promise> -``` - -### invokeWrapper -```ts - /** - * Invoke a wrapper using an instance of the wrapper. - * - * @param options - { - * // The Wrapper's URI - * uri: TUri; - * - * // Method to be executed. - * method: string; - * - * //Arguments for the method, structured as a map, removing the chance of incorrectly ordered arguments. - * args?: Record | Uint8Array; - * - * // Env variables for the wrapper invocation. - * env?: Record; - * - * // A Uri resolution context - * resolutionContext?: IUriResolutionContext; - * - * // if true, return value is a msgpack-encoded byte array - * encodeResult?: boolean; - * - * // The wrapper to invoke - * wrapper: Wrapper - * } - * @returns A Promise with a Result containing the return value or an error - */ - public async invokeWrapper( - options: InvokerOptions & { wrapper: Wrapper } - ): Promise> -``` - -### invoke -```ts - /** - * Invoke a wrapper. - * - * @remarks - * Unlike `invokeWrapper`, this method automatically retrieves and caches the wrapper. - * - * @param options - { - * // The Wrapper's URI - * uri: TUri; - * - * // Method to be executed. - * method: string; - * - * //Arguments for the method, structured as a map, removing the chance of incorrectly ordered arguments. - * args?: Record | Uint8Array; - * - * // Env variables for the wrapper invocation. - * env?: Record; - * - * // A Uri resolution context - * resolutionContext?: IUriResolutionContext; - * - * // if true, return value is a msgpack-encoded byte array - * encodeResult?: boolean; - * } - * @returns A Promise with a Result containing the return value or an error - */ - public async invoke( - options: InvokerOptions - ): Promise> -``` - -### tryResolveUri -```ts - /** - * Resolve a URI to a wrap package, a wrapper, or a uri - * - * @param options - { uri: TUri; resolutionContext?: IUriResolutionContext } - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - public async tryResolveUri( - options: TryResolveUriOptions - ): Promise> -``` - -### loadWrapper -```ts - /** - * Resolve a URI to a wrap package or wrapper. - * If the URI resolves to wrap package, load the wrapper. - * - * @remarks - * Unlike other methods, `loadWrapper` does not accept a string URI. - * You can create a Uri (from the `@polywrap/core-js` package) using `Uri.from("wrap://...")` - * - * @param uri - the Uri to resolve - * @param resolutionContext? - a resolution context - * @param options - { noValidate?: boolean } - * @returns A Promise with a Result containing a Wrapper or Error - */ - public async loadWrapper( - uri: Uri, - resolutionContext?: IUriResolutionContext, - options?: DeserializeManifestOptions - ): Promise> -``` - -## Development - -The Polywrap JavaScript client is open-source. It lives within the [Polywrap toolchain monorepo](https://github.com/polywrap/toolchain/tree/origin/packages/js/client). Contributions from the community are welcomed! - -### Build -```bash -nvm use && yarn install && yarn build -``` - -### Test -```bash -yarn test -`` \ No newline at end of file diff --git a/packages/js/core-client/examples/quickstart.ts b/packages/js/core-client/examples/quickstart.ts deleted file mode 100644 index c55ca0d4eb..0000000000 --- a/packages/js/core-client/examples/quickstart.ts +++ /dev/null @@ -1,34 +0,0 @@ -import { PolywrapCoreClient } from "../build"; -import { ClientConfigBuilder } from "@polywrap/client-config-builder-js"; -import { Uri } from "@polywrap/core-js"; - -export function instantiate(): PolywrapCoreClient { - // $start: quickstart-instantiate - const config = new ClientConfigBuilder().addDefaults().build(); - - const client = new PolywrapCoreClient(config); - // $end - - return client; -} - -export async function invoke(): Promise { - const config = new ClientConfigBuilder().addDefaults().build(); - - const client = new PolywrapCoreClient(config); - - // $start: quickstart-invoke - const result = await client.invoke({ - uri: Uri.from("ens/helloworld.dev.polywrap.eth"), - method: "logMessage", - args: { - message: "Hello World!" - } - }); - - if (!result.ok) throw result.error; - - const value = result.value; - // $end - return value; -} diff --git a/packages/js/core-client/examples/tsconfig.examples.json b/packages/js/core-client/examples/tsconfig.examples.json deleted file mode 100644 index f37de53612..0000000000 --- a/packages/js/core-client/examples/tsconfig.examples.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "extends": "../tsconfig.json", - "include": [ - "./**/*.ts" - ], -} \ No newline at end of file diff --git a/packages/js/core-client/jest.config.js b/packages/js/core-client/jest.config.js deleted file mode 100644 index a5ca876a5a..0000000000 --- a/packages/js/core-client/jest.config.js +++ /dev/null @@ -1,11 +0,0 @@ -module.exports = { - collectCoverage: true, - preset: 'ts-jest', - testEnvironment: 'node', - testMatch: ["**/?(*.)+(spec|test).[jt]s?(x)"], - globals: { - 'ts-jest': { - diagnostics: false - } - } -}; diff --git a/packages/js/core-client/package.json b/packages/js/core-client/package.json deleted file mode 100644 index 51f40bcb45..0000000000 --- a/packages/js/core-client/package.json +++ /dev/null @@ -1,85 +0,0 @@ -{ - "name": "@polywrap/core-client-js", - "description": "Polywrap Javascript Core Client", - "version": "0.10.0", - "license": "MIT", - "repository": { - "type": "git", - "url": "https://github.com/polywrap/toolchain.git" - }, - "main": "build/index.js", - "files": [ - "build" - ], - "scripts": { - "build": "yarn build:fast", - "build:docs": "yarn build:snippets && yarn build:readme", - "build:fast": "rimraf ./build && tsc --project tsconfig.build.json", - "lint": "eslint --color -c ../../../.eslintrc.js src/", - "test": "jest --passWithNoTests --runInBand --verbose=true --detectOpenHandles --forceExit", - "build:snippets": "tsc --project ./examples/tsconfig.examples.json", - "build:readme": "yarn doc-snippets combine" - }, - "dependencies": { - "@polywrap/core-js": "0.10.0", - "@polywrap/msgpack-js": "0.10.0", - "@polywrap/result": "0.10.0", - "@polywrap/tracing-js": "0.10.0", - "@polywrap/wrap-manifest-types-js": "0.10.0" - }, - "devDependencies": { - "@polywrap/uri-resolvers-js": "0.10.0", - "@types/jest": "26.0.8", - "@types/uuid": "8.3.0", - "doc-snippets": "~1.0.0", - "jest": "26.6.3", - "rimraf": "3.0.2", - "ts-jest": "26.5.4", - "ts-loader": "8.0.17", - "ts-node": "10.9.1", - "typescript": "4.9.5" - }, - "gitHead": "7346adaf5adb7e6bbb70d9247583e995650d390a", - "publishConfig": { - "access": "public" - }, - "doc-snippets": { - "extract": { - "include": [ - "./src/**/*.{ts,tsx,json,yaml,txt,md,graphql,cue}", - "./examples/**/*.{ts,tsx,json,yaml,txt,md,graphql,cue}" - ], - "ignore": [ - "./**/node_modules/**", - "./**/.polywrap/**", - "./**/__tests__/**" - ], - "dir": "./" - }, - "inject": { - "dir": "./readme", - "include": "./README.md" - }, - "startTokens": [ - { - "pattern": "$start: ", - "inline": false - }, - { - "pattern": "/* $: {SNIPPET_NAME} */", - "inline": true - } - ], - "endTokens": [ - { - "pattern": "$end", - "inline": false - }, - { - "pattern": "/* $ */", - "inline": true - } - ], - "outputDir": "./" - } -} diff --git a/packages/js/core-client/readme/README.md b/packages/js/core-client/readme/README.md deleted file mode 100644 index 6ca5ff65a8..0000000000 --- a/packages/js/core-client/readme/README.md +++ /dev/null @@ -1,115 +0,0 @@ -# @polywrap/core-client-js - -npm - - -
-
-The Polywrap JavaScript core client invokes wrapper functions. It's designed to run in any environment that can execute JavaScript (think websites, node scripts, etc.). It has TypeScript support. - -## Installation - -```bash -npm install --save @polywrap/core-client-js -``` - -## Usage - -### Instantiate - -Use the `@polywrap/client-config-builder-js` package to build a CoreClientConfig for your project, then use the PolywrapCoreClient [constructor](#constructor) to instantiate the client with your config. - -```ts -$snippet: quickstart-instantiate -``` - -### Invoke - -Invoke a wrapper. - -```ts -$snippet: quickstart-invoke -``` - -# Reference - -## PolywrapCoreClient - -### Constructor -```ts -$snippet: PolywrapCoreClient-constructor -``` - -### getConfig -```ts -$snippet: PolywrapCoreClient-getConfig -``` - -### getInterfaces -```ts -$snippet: PolywrapCoreClient-getInterfaces -``` - -### getEnvs -```ts -$snippet: PolywrapCoreClient-getEnvs -``` - -### getResolver -```ts -$snippet: PolywrapCoreClient-getResolver -``` - -### getEnvByUri -```ts -$snippet: PolywrapCoreClient-getEnvByUri -``` - -### getManifest -```ts -$snippet: PolywrapCoreClient-getManifest -``` - -### getFile -```ts -$snippet: PolywrapCoreClient-getFile -``` - -### getImplementations -```ts -$snippet: PolywrapCoreClient-getImplementations -``` - -### invokeWrapper -```ts -$snippet: PolywrapCoreClient-invokeWrapper -``` - -### invoke -```ts -$snippet: PolywrapCoreClient-invoke -``` - -### tryResolveUri -```ts -$snippet: PolywrapCoreClient-tryResolveUri -``` - -### loadWrapper -```ts -$snippet: PolywrapCoreClient-loadWrapper -``` - -## Development - -The Polywrap JavaScript client is open-source. It lives within the [Polywrap toolchain monorepo](https://github.com/polywrap/toolchain/tree/origin/packages/js/client). Contributions from the community are welcomed! - -### Build -```bash -nvm use && yarn install && yarn build -``` - -### Test -```bash -yarn test -`` \ No newline at end of file diff --git a/packages/js/core-client/src/PolywrapCoreClient.ts b/packages/js/core-client/src/PolywrapCoreClient.ts deleted file mode 100644 index 90324b11ea..0000000000 --- a/packages/js/core-client/src/PolywrapCoreClient.ts +++ /dev/null @@ -1,416 +0,0 @@ -import { - Wrapper, - CoreClient, - GetFileOptions, - GetImplementationsOptions, - InvokeOptions, - InvokerOptions, - Uri, - getImplementations, - TryResolveUriOptions, - IUriResolver, - IUriResolutionContext, - UriPackageOrWrapper, - UriResolutionContext, - getEnvFromUriHistory, - InvokeResult, - buildCleanUriHistory, - CoreClientConfig, - WrapError, - WrapErrorCode, - WrapperEnv, - ReadonlyUriMap, - UriMap, -} from "@polywrap/core-js"; -import { msgpackEncode, msgpackDecode } from "@polywrap/msgpack-js"; -import { - DeserializeManifestOptions, - WrapManifest, -} from "@polywrap/wrap-manifest-types-js"; -import { Result, ResultErr, ResultOk } from "@polywrap/result"; - -export class PolywrapCoreClient implements CoreClient { - // $start: PolywrapCoreClient-constructor - /** - * Instantiate a PolywrapClient - * - * @param config - a core client configuration - */ - constructor(private _config: CoreClientConfig) /* $ */ {} - - // $start: PolywrapCoreClient-getConfig - /** - * Returns the configuration used to instantiate the client - * - * @returns an immutable Polywrap client config - */ - public getConfig(): CoreClientConfig /* $ */ { - return this._config; - } - - // $start: PolywrapCoreClient-getInterfaces - /** - * returns all interfaces from the configuration used to instantiate the client - * - * @returns an array of interfaces and their registered implementations - */ - public getInterfaces(): ReadonlyUriMap | undefined /* $ */ { - return this._config.interfaces; - } - - // $start: PolywrapCoreClient-getEnvs - /** - * returns all env registrations from the configuration used to instantiate the client - * - * @returns an array of env objects containing wrapper environmental variables - */ - public getEnvs(): ReadonlyUriMap | undefined /* $ */ { - return this._config.envs; - } - - // $start: PolywrapCoreClient-getResolver - /** - * returns the URI resolver from the configuration used to instantiate the client - * - * @returns an object that implements the IUriResolver interface - */ - public getResolver(): IUriResolver /* $ */ { - return this._config.resolver; - } - - // $start: PolywrapCoreClient-getEnvByUri - /** - * returns an env (a set of environmental variables) from the configuration used to instantiate the client - * - * @param uri - the URI used to register the env - * @returns an env, or undefined if an env is not found at the given URI - */ - public getEnvByUri(uri: Uri): WrapperEnv | undefined /* $ */ { - const envs = this.getEnvs(); - if (!envs) { - return undefined; - } - - return envs.get(uri); - } - - // $start: PolywrapCoreClient-getManifest - /** - * returns a package's wrap manifest - * - * @param uri - a wrap URI - * @returns a Result containing the WrapManifest if the request was successful - */ - public async getManifest( - uri: Uri - ): Promise> /* $ */ { - const load = await this.loadWrapper(Uri.from(uri), undefined); - if (!load.ok) { - return load; - } - const wrapper = load.value; - const manifest = wrapper.getManifest(); - - return ResultOk(manifest); - } - - // $start: PolywrapCoreClient-getFile - /** - * returns a file contained in a wrap package - * - * @param uri - a wrap URI - * @param options - { path: string; encoding?: "utf-8" | string } - * @returns a Promise of a Result containing a file if the request was successful - */ - public async getFile( - uri: Uri, - options: GetFileOptions - ): Promise> /* $ */ { - const load = await this.loadWrapper(Uri.from(uri), undefined); - if (!load.ok) { - return load; - } - const wrapper = load.value; - - const result = await wrapper.getFile(options); - if (!result.ok) { - const error = new WrapError(result.error?.message, { - code: WrapErrorCode.CLIENT_GET_FILE_ERROR, - uri: uri.toString(), - }); - return ResultErr(error); - } - return ResultOk(result.value); - } - - // $start: PolywrapCoreClient-getImplementations - /** - * returns the interface implementations associated with an interface URI - * from the configuration used to instantiate the client - * - * @param uri - a wrap URI - * @param options - { applyResolution?: boolean; resolutionContext?: IUriResolutionContext } - * @returns a Result containing URI array if the request was successful - */ - public async getImplementations( - uri: Uri, - options: GetImplementationsOptions = {} - ): Promise> /* $ */ { - const applyResolution = !!options.applyResolution; - - const getImplResult = await getImplementations( - Uri.from(uri), - this.getInterfaces() ?? new UriMap(), - applyResolution ? this : undefined, - applyResolution ? options.resolutionContext : undefined - ); - - if (!getImplResult.ok) { - return getImplResult; - } - - const uris = getImplResult.value; - - return ResultOk(uris); - } - - // $start: PolywrapCoreClient-invokeWrapper - /** - * Invoke a wrapper using an instance of the wrapper. - * - * @param options - { - * // The Wrapper's URI - * uri: TUri; - * - * // Method to be executed. - * method: string; - * - * //Arguments for the method, structured as a map, removing the chance of incorrectly ordered arguments. - * args?: Record | Uint8Array; - * - * // Env variables for the wrapper invocation. - * env?: Record; - * - * // A Uri resolution context - * resolutionContext?: IUriResolutionContext; - * - * // if true, return value is a msgpack-encoded byte array - * encodeResult?: boolean; - * - * // The wrapper to invoke - * wrapper: Wrapper - * } - * @returns A Promise with a Result containing the return value or an error - */ - public async invokeWrapper( - options: InvokerOptions & { wrapper: Wrapper } - ): Promise> /* $ */ { - try { - const typedOptions: InvokeOptions = { - ...options, - uri: Uri.from(options.uri), - }; - - const wrapper = options.wrapper; - const invocableResult = await wrapper.invoke(typedOptions, this); - - if (!invocableResult.ok) { - return ResultErr(invocableResult.error); - } - - const value = invocableResult.value; - - if (options.encodeResult && !invocableResult.encoded) { - const encoded = msgpackEncode(value); - return ResultOk((encoded as unknown) as TData); - } else if (invocableResult.encoded && !options.encodeResult) { - const decoded = msgpackDecode(value as Uint8Array); - return ResultOk(decoded as TData); - } else { - return ResultOk(value as TData); - } - } catch (error) { - return ResultErr(error); - } - } - - // $start: PolywrapCoreClient-invoke - /** - * Invoke a wrapper. - * - * @remarks - * Unlike `invokeWrapper`, this method automatically retrieves and caches the wrapper. - * - * @param options - { - * // The Wrapper's URI - * uri: TUri; - * - * // Method to be executed. - * method: string; - * - * //Arguments for the method, structured as a map, removing the chance of incorrectly ordered arguments. - * args?: Record | Uint8Array; - * - * // Env variables for the wrapper invocation. - * env?: Record; - * - * // A Uri resolution context - * resolutionContext?: IUriResolutionContext; - * - * // if true, return value is a msgpack-encoded byte array - * encodeResult?: boolean; - * } - * @returns A Promise with a Result containing the return value or an error - */ - public async invoke( - options: InvokerOptions - ): Promise> /* $ */ { - try { - const typedOptions: InvokeOptions = { - ...options, - uri: Uri.from(options.uri), - }; - - const resolutionContext = - options.resolutionContext ?? new UriResolutionContext(); - - const loadWrapperResult = await this.loadWrapper( - typedOptions.uri, - resolutionContext - ); - - if (!loadWrapperResult.ok) { - return loadWrapperResult; - } - const wrapper = loadWrapperResult.value; - - const resolutionPath = resolutionContext.getResolutionPath(); - - const env = getEnvFromUriHistory( - resolutionPath.length > 0 ? resolutionPath : [typedOptions.uri], - this - ); - - const invokeResult = await this.invokeWrapper({ - env: env, - ...typedOptions, - wrapper, - }); - - if (!invokeResult.ok) { - return invokeResult; - } - - return invokeResult; - } catch (error) { - return ResultErr(error); - } - } - - // $start: PolywrapCoreClient-tryResolveUri - /** - * Resolve a URI to a wrap package, a wrapper, or a uri - * - * @param options - { uri: TUri; resolutionContext?: IUriResolutionContext } - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - public async tryResolveUri( - options: TryResolveUriOptions - ): Promise> /* $ */ { - const uri = Uri.from(options.uri); - - const uriResolver = this.getResolver(); - - const resolutionContext = - options.resolutionContext ?? new UriResolutionContext(); - - const response = await uriResolver.tryResolveUri( - uri, - this, - resolutionContext - ); - - return response; - } - - // $start: PolywrapCoreClient-loadWrapper - /** - * Resolve a URI to a wrap package or wrapper. - * If the URI resolves to wrap package, load the wrapper. - * - * @remarks - * Unlike other methods, `loadWrapper` does not accept a string URI. - * You can create a Uri (from the `@polywrap/core-js` package) using `Uri.from("wrap://...")` - * - * @param uri - the Uri to resolve - * @param resolutionContext? - a resolution context - * @param options - { noValidate?: boolean } - * @returns A Promise with a Result containing a Wrapper or Error - */ - public async loadWrapper( - uri: Uri, - resolutionContext?: IUriResolutionContext, - options?: DeserializeManifestOptions - ): Promise> /* $ */ { - if (!resolutionContext) { - resolutionContext = new UriResolutionContext(); - } - - const result = await this.tryResolveUri({ - uri, - resolutionContext, - }); - - if (!result.ok) { - const history = buildCleanUriHistory(resolutionContext.getHistory()); - - let error: WrapError; - if (result.error) { - error = new WrapError("A URI Resolver returned an error.", { - code: WrapErrorCode.URI_RESOLVER_ERROR, - uri: uri.uri, - resolutionStack: history, - cause: result.error, - }); - } else { - error = new WrapError("Error resolving URI", { - code: WrapErrorCode.URI_RESOLUTION_ERROR, - uri: uri.uri, - resolutionStack: history, - }); - } - - return ResultErr(error); - } - - const uriPackageOrWrapper = result.value; - - if (uriPackageOrWrapper.type === "uri") { - const message = `Unable to find URI ${uriPackageOrWrapper.uri.uri}.`; - const history = buildCleanUriHistory(resolutionContext.getHistory()); - const error = new WrapError(message, { - code: WrapErrorCode.URI_NOT_FOUND, - uri: uri.uri, - resolutionStack: history, - }); - return ResultErr(error); - } - - if (uriPackageOrWrapper.type === "package") { - const result = await uriPackageOrWrapper.package.createWrapper(options); - - if (!result.ok) { - const error = new WrapError(result.error?.message, { - code: WrapErrorCode.CLIENT_LOAD_WRAPPER_ERROR, - uri: uri.uri, - cause: result.error, - }); - return ResultErr(error); - } - - return ResultOk(result.value); - } else { - return ResultOk(uriPackageOrWrapper.wrapper); - } - } -} diff --git a/packages/js/core-client/src/__tests__/embedded-package.spec.ts b/packages/js/core-client/src/__tests__/embedded-package.spec.ts deleted file mode 100644 index 70e660b510..0000000000 --- a/packages/js/core-client/src/__tests__/embedded-package.spec.ts +++ /dev/null @@ -1,169 +0,0 @@ -import fs from "fs"; -import path from "path"; -import { GetPathToTestWrappers } from "@polywrap/test-cases"; -import { UriResolver } from "@polywrap/uri-resolvers-js"; -import { InMemoryFileReader, WasmPackage } from "@polywrap/wasm-js"; -import { IWrapPackage, Uri } from "@polywrap/core-js"; -import { PolywrapCoreClient } from "../PolywrapCoreClient"; -import { Result, ResultErr, ResultOk } from "@polywrap/result"; - -jest.setTimeout(200000); - -const wrapperPath = `${GetPathToTestWrappers()}/subinvoke/00-subinvoke/implementations/as`; -const wrapperUri = new Uri(`fs/${wrapperPath}`); - -describe("Embedded package", () => { - it("can invoke an embedded package", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")) - const wasmModuleBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.wasm")) - - let wrapPackage = WasmPackage.from(manifestBuffer, wasmModuleBuffer); - - const client = new PolywrapCoreClient({ - resolver: UriResolver.from([ - { - uri: wrapperUri, - package: wrapPackage - } - ]) - }); - - const result = await client.invoke({ - uri: wrapperUri, - method: "add", - args: { - a: 1, - b: 1 - }, - }); - - if (!result.ok) fail(result.error); - expect(result.value).toBeTruthy(); - expect(typeof result.value).toBe("number"); - expect(result.value).toEqual(2); - }); - - it("can get a file from wrapper", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")) - const wasmModuleBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.wasm")) - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapPackage = WasmPackage.from(manifestBuffer, wasmModuleBuffer, { - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - } - }); - - await testEmbeddedPackageWithFile(wrapPackage, testFilePath, testFileText); - }); - - it("can add embedded wrapper through file reader", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")) - const wasmModuleBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.wasm")) - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapPackage = WasmPackage.from({ - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else if (filePath === "wrap.info") { - return ResultOk(manifestBuffer); - } else if (filePath === "wrap.wasm") { - return ResultOk(wasmModuleBuffer); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - } - }); - - await testEmbeddedPackageWithFile(wrapPackage, testFilePath, testFileText); - }); - - it("can add embedded wrapper with async wrap manifest", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")) - const wasmModuleBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.wasm")) - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapPackage = WasmPackage.from( - InMemoryFileReader.fromWasmModule(wasmModuleBuffer, { - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else if (filePath === "wrap.info") { - return ResultOk(manifestBuffer); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - } - }) - ); - - await testEmbeddedPackageWithFile(wrapPackage, testFilePath, testFileText); - }); - - it("can add embedded wrapper with async wasm module", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")) - const wasmModuleBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.wasm")) - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapPackage = WasmPackage.from(manifestBuffer, { - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else if (filePath === "wrap.wasm") { - return ResultOk(wasmModuleBuffer); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - } - }); - - await testEmbeddedPackageWithFile(wrapPackage, testFilePath, testFileText); - }); -}); - -const testEmbeddedPackageWithFile = async (wrapPackage: IWrapPackage, filePath: string, fileText: string) => { - const client = new PolywrapCoreClient({ - resolver: UriResolver.from([ - { - uri: wrapperUri, - package: wrapPackage - } - ]) - }); - - const expectedManifest = - await fs.promises.readFile(`${wrapperPath}/wrap.info`); - const receivedManifestResult = await client.getFile(wrapperUri, { - path: "wrap.info", - }); - if (!receivedManifestResult.ok) fail(receivedManifestResult.error); - const receivedManifest = receivedManifestResult.value as Uint8Array; - expect(receivedManifest).toEqual(expectedManifest); - - const expectedWasmModule = - await fs.promises.readFile(`${wrapperPath}/wrap.wasm`); - const receivedWasmModuleResult = await client.getFile(wrapperUri, { - path: "wrap.wasm", - }); - if (!receivedWasmModuleResult.ok) fail(receivedWasmModuleResult.error); - const receivedWasmModule = receivedWasmModuleResult.value as Uint8Array; - expect(receivedWasmModule).toEqual(expectedWasmModule); - - const receivedHelloFileResult = await client.getFile(wrapperUri, { - path: filePath, - encoding: "utf-8", - }); - if (!receivedHelloFileResult.ok) fail(receivedHelloFileResult.error); - const receivedHelloFile = receivedHelloFileResult.value as Uint8Array; - - expect(receivedHelloFile).toEqual(fileText); -}; diff --git a/packages/js/core-client/src/__tests__/embedded-wrapper.spec.ts b/packages/js/core-client/src/__tests__/embedded-wrapper.spec.ts deleted file mode 100644 index 6a0815edd8..0000000000 --- a/packages/js/core-client/src/__tests__/embedded-wrapper.spec.ts +++ /dev/null @@ -1,169 +0,0 @@ -import fs from "fs"; -import path from "path"; -import { GetPathToTestWrappers } from "@polywrap/test-cases"; -import { UriResolver } from "@polywrap/uri-resolvers-js"; -import { WasmWrapper, InMemoryFileReader } from "@polywrap/wasm-js"; -import { Uri, Wrapper } from "@polywrap/core-js"; -import { PolywrapCoreClient } from "../PolywrapCoreClient"; -import { Result, ResultErr, ResultOk } from "@polywrap/result"; - -jest.setTimeout(200000); - -const wrapperPath = `${GetPathToTestWrappers()}/subinvoke/00-subinvoke/implementations/as`; -const wrapperUri = new Uri(`fs/${wrapperPath}`); - -describe("Embedded wrapper", () => { - it("can invoke an embedded wrapper", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")) - const wasmModuleBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.wasm")) - - let wrapper: Wrapper = await WasmWrapper.from(manifestBuffer, wasmModuleBuffer); - - const client = new PolywrapCoreClient({ - resolver: UriResolver.from([ - { - uri: wrapperUri, - wrapper - } - ]) - }); - - const result = await client.invoke({ - uri: wrapperUri, - method: "add", - args: { - a: 1, - b: 1 - }, - }); - - if (!result.ok) fail(result.error); - expect(result.value).toBeTruthy(); - expect(typeof result.value).toBe("number"); - expect(result.value).toEqual(2); - }); - - it("can get a file from wrapper", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")) - const wasmModuleBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.wasm")) - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapper = await WasmWrapper.from(manifestBuffer, wasmModuleBuffer, { - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - } - }); - - await testEmbeddedWrapperWithFile(wrapper, testFilePath, testFileText); - }); - - it("can add embedded wrapper through file reader", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")) - const wasmModuleBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.wasm")) - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapper = await WasmWrapper.from({ - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else if (filePath === "wrap.info") { - return ResultOk(manifestBuffer); - } else if (filePath === "wrap.wasm") { - return ResultOk(wasmModuleBuffer); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - } - }); - - await testEmbeddedWrapperWithFile(wrapper, testFilePath, testFileText); - }); - - it("can add embedded wrapper with async wrap manifest", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")) - const wasmModuleBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.wasm")) - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapper = await WasmWrapper.from( - InMemoryFileReader.fromWasmModule(wasmModuleBuffer, { - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else if (filePath === "wrap.info") { - return ResultOk(manifestBuffer); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - } - }) - ); - - await testEmbeddedWrapperWithFile(wrapper, testFilePath, testFileText); - }); - - it("can add embedded wrapper with async wasm module", async () => { - const manifestBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.info")) - const wasmModuleBuffer = fs.readFileSync(path.join(wrapperPath, "wrap.wasm")) - const testFilePath = "hello.txt"; - const testFileText = "Hello Test!"; - - const wrapper = await WasmWrapper.from(manifestBuffer, { - readFile: async (filePath): Promise> => { - if (filePath === testFilePath) { - return ResultOk(Buffer.from(testFileText, "utf-8")); - } else if (filePath === "wrap.wasm") { - return ResultOk(wasmModuleBuffer); - } else { - return ResultErr(new Error(`File not found: ${filePath}`)); - } - } - }); - - await testEmbeddedWrapperWithFile(wrapper, testFilePath, testFileText); - }); -}); - -const testEmbeddedWrapperWithFile = async (wrapper: WasmWrapper, filePath: string, fileText: string) => { - const client = new PolywrapCoreClient({ - resolver: UriResolver.from([ - { - uri: wrapperUri, - wrapper - } - ]) - }); - - const expectedManifest = - await fs.promises.readFile(`${wrapperPath}/wrap.info`); - const receivedManifestResult = await client.getFile(wrapperUri, { - path: "wrap.info", - }); - if (!receivedManifestResult.ok) fail(receivedManifestResult.error); - const receivedManifest = receivedManifestResult.value as Uint8Array; - expect(receivedManifest).toEqual(expectedManifest); - - const expectedWasmModule = - await fs.promises.readFile(`${wrapperPath}/wrap.wasm`); - const receivedWasmModuleResult = await client.getFile(wrapperUri, { - path: "wrap.wasm", - }); - if (!receivedWasmModuleResult.ok) fail(receivedWasmModuleResult.error); - const receivedWasmModule = receivedWasmModuleResult.value as Uint8Array; - expect(receivedWasmModule).toEqual(expectedWasmModule); - - const receivedHelloFileResult = await client.getFile(wrapperUri, { - path: filePath, - encoding: "utf-8", - }); - if (!receivedHelloFileResult.ok) fail(receivedHelloFileResult.error); - const receivedHelloFile = receivedHelloFileResult.value as Uint8Array; - - expect(receivedHelloFile).toEqual(fileText); -}; diff --git a/packages/js/core-client/src/index.ts b/packages/js/core-client/src/index.ts deleted file mode 100644 index d65e626e47..0000000000 --- a/packages/js/core-client/src/index.ts +++ /dev/null @@ -1 +0,0 @@ -export * from "./PolywrapCoreClient"; diff --git a/packages/js/core-client/tsconfig.build.json b/packages/js/core-client/tsconfig.build.json deleted file mode 100644 index ec6eea7b58..0000000000 --- a/packages/js/core-client/tsconfig.build.json +++ /dev/null @@ -1,12 +0,0 @@ -{ - "extends": "./tsconfig.json", - "compilerOptions": { - "outDir": "build" - }, - "include": [ - "./src/**/*.ts" - ], - "exclude": [ - "./src/**/__tests__" - ] -} diff --git a/packages/js/core-client/tsconfig.json b/packages/js/core-client/tsconfig.json deleted file mode 100644 index 61edd1723e..0000000000 --- a/packages/js/core-client/tsconfig.json +++ /dev/null @@ -1,16 +0,0 @@ -{ - "extends": "../../../tsconfig", - "compilerOptions": { - "lib": [ - "es2020", - "es2015", - "es5", - "dom" - ], - }, - "include": [ - "./src/**/*.ts", - "./examples/**/*.ts" - ], - "exclude": [] -} diff --git a/packages/js/core/.eslintignore b/packages/js/core/.eslintignore deleted file mode 100644 index d2e7e39eeb..0000000000 --- a/packages/js/core/.eslintignore +++ /dev/null @@ -1 +0,0 @@ -src/manifest/formats \ No newline at end of file diff --git a/packages/js/core/.gitignore b/packages/js/core/.gitignore deleted file mode 100644 index b78cae4e43..0000000000 --- a/packages/js/core/.gitignore +++ /dev/null @@ -1 +0,0 @@ -readme/sub-sections/injected \ No newline at end of file diff --git a/packages/js/core/README.md b/packages/js/core/README.md deleted file mode 100644 index f122bcdaa5..0000000000 --- a/packages/js/core/README.md +++ /dev/null @@ -1,711 +0,0 @@ -# @polywrap/core-js - -A TypeScript / JavaScript implementation of the WRAP standard, including all fundamental types & algorithms. - -# Reference - -## Types - -### CoreClient - -```ts - -/** Core Client configuration that can be passed to the PolywrapClient or PolywrapCoreClient constructors */ -export interface CoreClientConfig { - /** register interface implementations */ - readonly interfaces?: ReadonlyUriMap; - - /** set environmental variables for a wrapper */ - readonly envs?: ReadonlyUriMap; - - /** configure URI resolution for redirects, packages, and wrappers */ - readonly resolver: Readonly>; -} - -/** Options for CoreClient's getFile method */ -export interface GetFileOptions { - /** file path from wrapper root */ - path: string; - - /** file encoding */ - encoding?: "utf-8" | string; -} - -/** Options for CoreClient's getImplementations method */ -export interface GetImplementationsOptions { - /** If true, follow redirects to resolve URIs */ - applyResolution?: boolean; - - /** Use and update an existing resolution context */ - resolutionContext?: IUriResolutionContext; -} - -/** Options for CoreClient's validate method */ -export interface ValidateOptions { - /** Validate full ABI */ - abi?: boolean; - - /** Recursively validate import URIs */ - recursive?: boolean; -} - -/** CoreClient invokes wrappers and interacts with wrap packages. */ -export interface CoreClient extends Invoker, UriResolverHandler { - /** - * Returns the configuration used to instantiate the client - * - * @returns an immutable core client config - */ - getConfig(): CoreClientConfig; - - /** - * returns all interfaces from the configuration used to instantiate the client - * - * @returns a Set of interfaces and their registered implementations - */ - getInterfaces(): ReadonlyUriMap | undefined; - - /** - * returns all env registrations from the configuration used to instantiate the client - * - * @returns an array of env objects containing wrapper environmental variables - */ - getEnvs(): ReadonlyUriMap | undefined; - - /** - * returns an env (a set of environmental variables) from the configuration used to instantiate the client - * - * @param uri - the URI used to register the env - * @returns an env, or undefined if an env is not found at the given URI - */ - getEnvByUri(uri: Uri): WrapperEnv | undefined; - - /** - * returns the URI resolver from the configuration used to instantiate the client - * - * @returns an object that implements the IUriResolver interface - */ - getResolver(): IUriResolver; - - /** - * returns a package's wrap manifest - * - * @param uri - a wrap URI - * @returns a Result containing the WrapManifest if the request was successful - */ - getManifest(uri: Uri): Promise>; - - /** - * returns a file contained in a wrap package - * - * @param uri - a wrap URI - * @param options - { path: string; encoding?: "utf-8" | string } - * @returns a Promise of a Result containing a file if the request was successful - */ - getFile( - uri: Uri, - options: GetFileOptions - ): Promise>; - - /** - * returns the interface implementations associated with an interface URI - * from the configuration used to instantiate the client - * - * @param uri - a wrap URI - * @param options - { applyResolution?: boolean; resolutionContext?: IUriResolutionContext } - * @returns a Result containing URI array if the request was successful - */ - getImplementations( - uri: Uri, - options: GetImplementationsOptions - ): Promise>; -} - -``` - -### Env - -```ts - -/** A map of string-indexed, Msgpack-serializable environmental variables associated with a wrapper */ -export interface WrapperEnv { - readonly [k: string]: unknown; -} -``` - -### Invoke - -```ts - -/** Options required for an Wrapper invocation. */ -export interface InvokeOptions { - /** The Wrapper's URI */ - uri: Uri; - - /** Method to be executed. */ - method: string; - - /** Arguments for the method, structured as a map, removing the chance of incorrectly ordered arguments. */ - args?: Record | Uint8Array; - - /** Env variables for the wrapper invocation. */ - env?: Record; - - /** A Uri resolution context */ - resolutionContext?: IUriResolutionContext; -} - -/** - * Result of an Wrapper invocation. - * - * @template TData Type of the invoke result data. - */ -export type InvokeResult = Result; - -/** - * Provides options for the invoker to set based on the state of the invocation. - * Extends InvokeOptions. - */ -export interface InvokerOptions extends InvokeOptions { - /** If true, the InvokeResult will (if successful) contain a Msgpack-encoded byte array */ - encodeResult?: boolean; -} - -/** - * An entity capable of invoking wrappers. - * - * @template TData Type of the invoke result data. - */ -export interface Invoker { - /** - * Invoke a wrapper using an instance of the wrapper. - * - * @param options - invoker options and a wrapper instance to invoke - * @returns A Promise with a Result containing the return value or an error - */ - invokeWrapper( - options: InvokerOptions & { wrapper: Wrapper } - ): Promise>; - - /** - * Invoke a wrapper. - * - * @remarks - * Unlike `invokeWrapper`, this method automatically retrieves and caches the wrapper. - * - * @param options - invoker options - * @returns A Promise with a Result containing the return value or an error - */ - invoke( - options: InvokerOptions - ): Promise>; -} - -/** - * Result of a Wrapper invocation, possibly Msgpack-encoded. - * - * @template TData Type of the invoke result data. - */ -export type InvocableResult = InvokeResult & { - /** If true, result (if successful) contains a Msgpack-encoded byte array */ - encoded?: boolean; -}; - -/** An invocable entity, such as a wrapper. */ -export interface Invocable { - /** - * Invoke this object. - * - * @param options - invoke options - * @param invoker - an Invoker, capable of invoking this object - * @returns A Promise with a Result containing the return value or an error - */ - invoke( - options: InvokeOptions, - invoker: Invoker - ): Promise>; -} - -``` - -### IUriPackage - -```ts - -/** Associates a URI with an embedded wrap package */ -export interface IUriPackage { - /** The package's URI */ - uri: Uri; - - /** The wrap package */ - package: IWrapPackage; -} - -``` - -### IUriRedirect - -```ts - -/** Redirect invocations from one URI to another */ -export interface IUriRedirect { - /** URI to redirect from */ - from: Uri; - - /** URI to redirect to */ - to: Uri; -} - -``` - -### IUriWrapper - -```ts - -/** Associates a URI with an embedded wrapper */ -export interface IUriWrapper { - /** The URI to resolve to the wrapper */ - uri: Uri; - - /** A wrapper instance */ - wrapper: Wrapper; -} - -``` - -### IWrapPackage - -```ts - -/** Options for IWrapPackage's getManifest method */ -export interface GetManifestOptions { - /** If true, manifest validation step will be skipped */ - noValidate?: boolean; -} - -/** A wrap package, capable of producing instances of a wrapper and its manifest */ -export interface IWrapPackage { - /** - * Produce an instance of the wrap manifest - * - * @param options - GetManifestOptions; customize manifest retrieval - * @returns A Promise with a Result containing the wrap manifest or an error - */ - getManifest( - options?: GetManifestOptions - ): Promise>; - - /** - * Produce an instance of the wrapper - * - * @param options - DeserializeManifestOptions; customize manifest deserialization - * @returns A Promise with a Result containing the wrapper or an error - */ - createWrapper( - options?: DeserializeManifestOptions - ): Promise>; -} - -``` - -### MaybeAsync - -```ts - -/** Alias for a type that is either a value or a promise that resolves to the value */ -export type MaybeAsync = Promise | T; - -``` - -### Uri - -#### UriConfig -```ts -/** URI configuration */ -export interface UriConfig { - /** URI Authority: allows the Polywrap URI resolution algorithm to determine an authoritative URI resolver. */ - authority: string; - - /** URI Path: tells the Authority where the Wrapper resides. */ - path: string; - - /** Full string representation of URI */ - uri: string; -} -``` - -#### Uri - -```ts -/** - * A Polywrap URI. Some examples of valid URIs are: - * wrap://ipfs/QmHASH - * wrap://ens/sub.dimain.eth - * wrap://fs/directory/file.txt - * wrap://uns/domain.crypto - * - * Breaking down the various parts of the URI, as it applies - * to [the URI standard](https://tools.ietf.org/html/rfc3986#section-3): - * **wrap://** - URI Scheme: differentiates Polywrap URIs. - * **ipfs/** - URI Authority: allows the Polywrap URI resolution algorithm to determine an authoritative URI resolver. - * **sub.domain.eth** - URI Path: tells the Authority where the Wrapper resides. - */ -export class Uri { -``` - -##### constructor -```ts - /** - * Construct a Uri instance from a wrap URI string - * - * @remarks - * Throws if URI string is invalid - * - * @param uri - a string representation of a wrap URI - */ - constructor(uri: string) -``` - -##### authority -```ts - /** @returns Uri authority */ - public get authority(): string -``` - -##### path -```ts - /** @returns Uri path */ - public get path(): string -``` - -##### uri -```ts - /** @returns Uri string representation */ - public get uri(): string -``` - -##### equals -```ts - /** Test two Uri instances for equality */ - public static equals(a: Uri, b: Uri): boolean -``` - -##### isUri -```ts - /** - * Check if a value is an instance of Uri - * - * @param value - value to check - * @returns true if value is a Uri instance */ - public static isUri(value: unknown): value is Uri -``` - -##### isValidUri -```ts - /** - * Test if a URI string is a valid wrap URI - * - * @param uri - URI string - * @param parsed? - UriConfig to update (mutate) with content of URI string - * @returns true if input string is a valid wrap URI */ - public static isValidUri(uri: string, parsed?: UriConfig): boolean -``` - -##### toString -```ts - /** @returns Uri string representation */ - public toString(): string -``` - -##### toJSON -```ts - /** @returns Uri string representation */ - public toJSON(): string -``` - -##### parseUri -```ts - /** - * Parse a wrap URI string into its authority and path - * - * @param uri - a string representation of a wrap URI - * @returns A Result containing a UriConfig, if successful, or an error - */ - public static parseUri(uri: string): Result -``` - -##### from -```ts - /** - * Construct a Uri instance from a Uri or a wrap URI string - * - * @remarks - * Throws if URI string is invalid - * - * @param uri - a Uri instance or a string representation of a wrap URI - */ - public static from(uri: Uri | string): Uri -``` - -### UriResolver - -```ts - -/** Options required for URI resolution. */ -export interface TryResolveUriOptions { - /** The Wrapper's URI */ - uri: Uri; - - /** A URI resolution context */ - resolutionContext?: IUriResolutionContext; -} - -/** An entity capable of resolving a wrap URI, typically by using an IUriResolver implementation */ -export interface UriResolverHandler { - /** - * Resolve a URI to a wrap package, a wrapper, or a uri - * - * @param options - TryResolveUriOptions - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - tryResolveUri( - options?: TryResolveUriOptions - ): Promise>; -} - -``` - -### Wrapper - -```ts - -/** - * The Wrapper definition, which can be used to spawn - * many invocations of this particular Wrapper. Internally - * this class may do things like caching WASM bytecode, spawning - * worker threads, or indexing into resolvers to find the requested method. - */ -export interface Wrapper extends Invocable { - /** - * Invoke the Wrapper based on the provided [[InvokeOptions]] - * - * @param options Options for this invocation. - * @param invoker The client instance requesting this invocation. - * This client will be used for any sub-invokes that occur. - */ - invoke( - options: InvokeOptions, - invoker: Invoker - ): Promise>; - - /** - * Get a file from the Wrapper package. - * - * @param options Configuration options for file retrieval - */ - getFile(options: GetFileOptions): Promise>; - - /** - * Get a manifest from the Wrapper package. - */ - getManifest(): WrapManifest; -} - -``` - -## UriResolverInterface - -### MaybeUriOrManifest -```ts -/** Contains either a Uri, a manifest, or neither */ -export interface MaybeUriOrManifest { - /** wrap URI */ - uri?: string | null; - - /** Serialized wrap manifest */ - manifest?: Uint8Array | null; -} -``` - -### Module - -#### tryResolveUri -```ts - /** - * Use an invoker to try to resolve a URI using a wrapper that implements the UriResolver interface - * - * @param invoker - invokes the wrapper with the resolution URI as an argument - * @param wrapper - URI for wrapper that implements the UriResolver interface - * @param uri - the URI to resolve - */ - tryResolveUri: async ( - invoker: Invoker, - wrapper: Uri, - uri: Uri - ): Promise> -``` - -#### getFile -```ts - /** - * Use an invoker to fetch a file using a wrapper that implements the UriResolver interface - * - * @param invoker - invokes the wrapper with the filepath as an argument - * @param wrapper - URI for wrapper that implements the UriResolver interface - * @param path - a filepath, the format of which depends on the UriResolver - */ - getFile: async ( - invoker: Invoker, - wrapper: Uri, - path: string - ): Promise> -``` - -## Uri Resolution - -### IUriResolutionContext - -```ts -/** Track and output URI resolution state, path, and history */ -export interface IUriResolutionContext { - /** - * Check if a URI is in the process of being resolved - * - * @param uri - URI to check - * @return true if URI resolution is in process, false otherwise - */ - isResolving(uri: Uri): boolean; - - /** - * Start resolving a URI - * - * @param uri - Uri to resolve - */ - startResolving(uri: Uri): void; - - /** - * Stop resolving a URI - * - * @param uri - Uri being resolved - */ - stopResolving(uri: Uri): void; - - /** - * Push a step onto the resolution history stack - * - * @param step - A completed resolution step - */ - trackStep(step: IUriResolutionStep): void; - - /** @return history of all URI resolution steps completed */ - getHistory(): IUriResolutionStep[]; - - /** @return current URI resolution path */ - getResolutionPath(): Uri[]; - - /** - * Create a new resolution context using the current URI resolution path - * - * @return a UriResolutionContext - */ - createSubHistoryContext(): IUriResolutionContext; - - /** - * Create a new resolution context using the current URI resolution history - * - * @return a UriResolutionContext - */ - createSubContext(): IUriResolutionContext; -} -``` - -### IUriResolutionStep - -```ts -/** A step in the URI resolution algorithm */ -export interface IUriResolutionStep { - /** The current URI being resolved */ - sourceUri: Uri; - - /** The resolution result for the current URI */ - result: Result; - - /** A text/visual description of this URI step */ - description?: string; - - /** History of sub-steps that exist within the context of this URI resolution step */ - subHistory?: IUriResolutionStep[]; -} -``` - -### IUriResolver - -```ts -/** Defines entity capable of resolving a wrap URI */ -export interface IUriResolver { - /** - * Resolve a URI to a wrap package, a wrapper, or a uri - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise>; -} -``` - -### UriPackageOrWrapper - -```ts - -/** Indicates that a URI resolved to a Uri */ -export type UriValue = { - type: "uri"; - uri: Uri; -}; - -/** Indicates that a URI resolved to a wrap package */ -export type UriPackageValue = IUriPackage & { - type: "package"; -}; - -/** Indicates that a URI resolved to a wrapper */ -export type UriWrapperValue = IUriWrapper & { - type: "wrapper"; -}; - -/** indicates that a URI resolved to either a wrap package, a wrapper, or a URI */ -export type UriPackageOrWrapper = UriValue | UriPackageValue | UriWrapperValue; - -``` - -### UriResolutionContext - -```ts -/** An implementation of the IUriResolutionContext interface */ -export class UriResolutionContext implements IUriResolutionContext { -``` - -#### constructor - -```ts - /** Construct a UriResolutionContext */ - constructor(); - constructor( - resolvingUriMap: Map, - resolutionPath: Set - ); - constructor( - resolvingUriMap: Map, - history: IUriResolutionStep[] - ); - constructor( - resolvingUriMap?: Map, - resolutionPathOrHistory?: Set | IUriResolutionStep[] - ) -``` diff --git a/packages/js/core/jest.config.js b/packages/js/core/jest.config.js deleted file mode 100644 index a5ca876a5a..0000000000 --- a/packages/js/core/jest.config.js +++ /dev/null @@ -1,11 +0,0 @@ -module.exports = { - collectCoverage: true, - preset: 'ts-jest', - testEnvironment: 'node', - testMatch: ["**/?(*.)+(spec|test).[jt]s?(x)"], - globals: { - 'ts-jest': { - diagnostics: false - } - } -}; diff --git a/packages/js/core/package.json b/packages/js/core/package.json deleted file mode 100644 index dadd0f2317..0000000000 --- a/packages/js/core/package.json +++ /dev/null @@ -1,46 +0,0 @@ -{ - "name": "@polywrap/core-js", - "description": "Polywrap Javascript Core", - "version": "0.10.0", - "license": "MIT", - "repository": { - "type": "git", - "url": "https://github.com/polywrap/monorepo.git" - }, - "main": "build/index.js", - "files": [ - "build" - ], - "scripts": { - "build": "yarn build:fast", - "build:docs": "yarn build:readme", - "build:fast": "rimraf ./build && tsc --project tsconfig.build.json", - "lint": "eslint --color -c ../../../.eslintrc.js src/", - "test": "jest --passWithNoTests --runInBand --verbose", - "test:watch": "yarn test -- --watch", - "build:readme:subsections": "yarn doc-snippets combine -c ./readme/config/sub-sections.json", - "build:readme:final": "yarn doc-snippets combine -c ./readme/config/final.json", - "build:readme": "yarn build:readme:subsections && yarn build:readme:final" - }, - "dependencies": { - "@polywrap/result": "0.10.0", - "@polywrap/tracing-js": "0.10.0", - "@polywrap/wrap-manifest-types-js": "0.10.0" - }, - "devDependencies": { - "@types/jest": "26.0.8", - "@types/mustache": "4.0.1", - "@types/prettier": "2.6.0", - "doc-snippets": "~1.0.0", - "jest": "26.6.3", - "mustache": "4.0.1", - "rimraf": "3.0.2", - "ts-jest": "26.5.4", - "ts-node": "10.9.1", - "typescript": "4.9.5" - }, - "gitHead": "7346adaf5adb7e6bbb70d9247583e995650d390a", - "publishConfig": { - "access": "public" - } -} diff --git a/packages/js/core/readme/README.md b/packages/js/core/readme/README.md deleted file mode 100644 index 7b412808b2..0000000000 --- a/packages/js/core/readme/README.md +++ /dev/null @@ -1,79 +0,0 @@ -# @polywrap/core-js - -A TypeScript / JavaScript implementation of the WRAP standard, including all fundamental types & algorithms. - -# Reference - -## Types - -### CoreClient - -```ts -$snippet: CoreClient.ts -``` - -### Env - -```ts -$snippet: Env.ts -``` - -### Invoke - -```ts -$snippet: Invoke.ts -``` - -### IUriPackage - -```ts -$snippet: IUriPackage.ts -``` - -### IUriRedirect - -```ts -$snippet: IUriRedirect.ts -``` - -### IUriWrapper - -```ts -$snippet: IUriWrapper.ts -``` - -### IWrapPackage - -```ts -$snippet: IWrapPackage.ts -``` - -### MaybeAsync - -```ts -$snippet: MaybeAsync.ts -``` - -### Uri - -$snippet: Uri.md - -### UriResolver - -```ts -$snippet: UriResolver.ts -``` - -### Wrapper - -```ts -$snippet: Wrapper.ts -``` - -## UriResolverInterface - -$snippet: UriResolverInterface - -## Uri Resolution - -$snippet: uri-resolution.md diff --git a/packages/js/core/readme/config/final.json b/packages/js/core/readme/config/final.json deleted file mode 100644 index 611ddc1e3e..0000000000 --- a/packages/js/core/readme/config/final.json +++ /dev/null @@ -1,41 +0,0 @@ -{ - "doc-snippets": { - "extract": { - "include": [ - "./src/**/*.{ts,tsx,json,yaml,txt,md,graphql,cue}", - "./readme/sub-sections/injected/**/*.{ts,tsx,json,yaml,txt,md,graphql,cue}" - ], - "ignore": [ - "./**/node_modules/**", - "./**/.polywrap/**", - "./**/__tests__/**" - ], - "dir": "./" - }, - "inject": { - "dir": "./readme", - "include": "./README.md" - }, - "startTokens": [ - { - "pattern": "$start: ", - "inline": false - }, - { - "pattern": "/* $: {SNIPPET_NAME} */", - "inline": true - } - ], - "endTokens": [ - { - "pattern": "$end", - "inline": false - }, - { - "pattern": "/* $ */", - "inline": true - } - ], - "outputDir": "./" - } -} \ No newline at end of file diff --git a/packages/js/core/readme/config/sub-sections.json b/packages/js/core/readme/config/sub-sections.json deleted file mode 100644 index cfde3d90eb..0000000000 --- a/packages/js/core/readme/config/sub-sections.json +++ /dev/null @@ -1,38 +0,0 @@ -{ - "doc-snippets": { - "extract": { - "include": "./**/*.{ts,tsx,json,yaml,txt,md,graphql,cue}", - "ignore": [ - "./**/node_modules/**", - "./**/.polywrap/**", - "./**/__tests__/**" - ], - "dir": "./src" - }, - "inject": { - "dir": "./readme/sub-sections/base", - "include": "./**/*.md" - }, - "startTokens": [ - { - "pattern": "$start: ", - "inline": false - }, - { - "pattern": "/* $: {SNIPPET_NAME} */", - "inline": true - } - ], - "endTokens": [ - { - "pattern": "$end", - "inline": false - }, - { - "pattern": "/* $ */", - "inline": true - } - ], - "outputDir": "./readme/sub-sections/injected" - } -} \ No newline at end of file diff --git a/packages/js/core/readme/sub-sections/base/Uri.md b/packages/js/core/readme/sub-sections/base/Uri.md deleted file mode 100644 index f808bd0eb5..0000000000 --- a/packages/js/core/readme/sub-sections/base/Uri.md +++ /dev/null @@ -1,67 +0,0 @@ -$start: Uri.md -#### UriConfig -```ts -$snippet: UriConfig -``` - -#### Uri - -```ts -$snippet: Uri -``` - -##### constructor -```ts -$snippet: Uri-constructor -``` - -##### authority -```ts -$snippet: Uri-authority -``` - -##### path -```ts -$snippet: Uri-path -``` - -##### uri -```ts -$snippet: Uri-uri -``` - -##### equals -```ts -$snippet: Uri-equals -``` - -##### isUri -```ts -$snippet: Uri-isUri -``` - -##### isValidUri -```ts -$snippet: Uri-isValidUri -``` - -##### toString -```ts -$snippet: Uri-toString -``` - -##### toJSON -```ts -$snippet: Uri-toJSON -``` - -##### parseUri -```ts -$snippet: Uri-parseUri -``` - -##### from -```ts -$snippet: Uri-from -``` -$end \ No newline at end of file diff --git a/packages/js/core/readme/sub-sections/base/UriResolverInterface.md b/packages/js/core/readme/sub-sections/base/UriResolverInterface.md deleted file mode 100644 index b290457e39..0000000000 --- a/packages/js/core/readme/sub-sections/base/UriResolverInterface.md +++ /dev/null @@ -1,18 +0,0 @@ -$start: UriResolverInterface -### MaybeUriOrManifest -```ts -$snippet: MaybeUriOrManifest -``` - -### Module - -#### tryResolveUri -```ts -$snippet: UriResolverInterface-tryResolveUri -``` - -#### getFile -```ts -$snippet: UriResolverInterface-getFile -``` -$end \ No newline at end of file diff --git a/packages/js/core/readme/sub-sections/base/uri-resolution.md b/packages/js/core/readme/sub-sections/base/uri-resolution.md deleted file mode 100644 index 5e226e9cf9..0000000000 --- a/packages/js/core/readme/sub-sections/base/uri-resolution.md +++ /dev/null @@ -1,37 +0,0 @@ -$start: uri-resolution.md -### IUriResolutionContext - -```ts -$snippet: IUriResolutionContext -``` - -### IUriResolutionStep - -```ts -$snippet: IUriResolutionStep -``` - -### IUriResolver - -```ts -$snippet: IUriResolver -``` - -### UriPackageOrWrapper - -```ts -$snippet: UriPackageOrWrapper.ts -``` - -### UriResolutionContext - -```ts -$snippet: UriResolutionContext -``` - -#### constructor - -```ts -$snippet: UriResolutionContext-constructor -``` -$end \ No newline at end of file diff --git a/packages/js/core/src/__tests__/MaybeAsync.spec.ts b/packages/js/core/src/__tests__/MaybeAsync.spec.ts deleted file mode 100644 index f9a297991d..0000000000 --- a/packages/js/core/src/__tests__/MaybeAsync.spec.ts +++ /dev/null @@ -1,41 +0,0 @@ -import { MaybeAsync } from ".."; - -interface IClassInterface { - normalMethod(arg: string): MaybeAsync; - asyncMethod(arg: string): MaybeAsync; -} - -class ClassInstance implements IClassInterface { - constructor(private _prop: string) {} - - normalMethod(arg: string): string { - return this._prop + arg; - } - - async asyncMethod(arg: string): Promise { - await new Promise((resolve) => setTimeout(resolve, 200)); - - return this._prop + arg; - } -} - -describe("MaybeAsync", () => { - const testFunction = (): MaybeAsync => { - return "foo"; - }; - const testFunctionReturnPromise = (): MaybeAsync => - new Promise((resolve) => { - resolve("foo"); - }); - - it("sanity", async () => { - expect(await testFunction()).toBe("foo"); - expect(await testFunctionReturnPromise()).toBe("foo"); - }); - - it("works with class instances", async () => { - const instance: IClassInterface = new ClassInstance("bar"); - expect(await instance.normalMethod("foo")).toBe("barfoo"); - expect(await instance.asyncMethod("foo")).toBe("barfoo"); - }); -}); diff --git a/packages/js/core/src/__tests__/Uri.spec.ts b/packages/js/core/src/__tests__/Uri.spec.ts deleted file mode 100644 index f38bfa7f1e..0000000000 --- a/packages/js/core/src/__tests__/Uri.spec.ts +++ /dev/null @@ -1,53 +0,0 @@ -import { Uri } from "../"; -import { UriConfig } from "../types/Uri"; - -describe("Uri", () => { - it("Inserts a wrap:// scheme when one is not present", () => { - const uri = new Uri("/authority-v2/path.to.thing.root/sub/path"); - - expect(uri.uri).toEqual("wrap://authority-v2/path.to.thing.root/sub/path"); - expect(uri.authority).toEqual("authority-v2"); - expect(uri.path).toEqual("path.to.thing.root/sub/path"); - }); - - it("isUri fails when given something that's not a URI", () => { - expect(Uri.isUri("not a Uri object" as never)).toBeFalsy(); - }); - - it("Fails if an authority is not present", () => { - expect(() => new Uri("wrap://path")).toThrowError(/URI is malformed,/); - }); - - it("Fails if a path is not present", () => { - expect(() => new Uri("wrap://authority/")).toThrowError(/URI is malformed,/); - }); - - it("Fails if scheme is not at the beginning", () => { - expect(() => new Uri("path/wrap://something")).toThrowError( - /The wrap:\/\/ scheme must/ - ); - }); - - it("Fails with an empty string", () => { - expect(() => new Uri("")).toThrowError("The provided URI is empty"); - }); - - it("Returns true if URI is valid", () => { - expect(Uri.isValidUri("wrap://valid/uri")).toBeTruthy(); - }); - - it("Returns false if URI is invalid", () => { - expect(Uri.isValidUri("wrap://.....")).toBeFalsy(); - }); - - it("Returns a parsed URI configuration from isValidUri", () => { - const config: UriConfig = {} as UriConfig; - - expect(Uri.isValidUri("wrap://valid/uri", config)).toBeTruthy(); - expect(config).toMatchObject({ - uri: "wrap://valid/uri", - authority: "valid", - path: "uri", - }); - }); -}); diff --git a/packages/js/core/src/__tests__/get-implementations.spec.ts b/packages/js/core/src/__tests__/get-implementations.spec.ts deleted file mode 100644 index fe514f9822..0000000000 --- a/packages/js/core/src/__tests__/get-implementations.spec.ts +++ /dev/null @@ -1,128 +0,0 @@ -import { - getImplementations, - Uri, - IUriRedirect, - UriPackageOrWrapper, -} from "../"; -import { CoreClient, UriMap } from "../types"; -import { Result, ResultOk } from "@polywrap/result"; - -const getClient = (redirects: IUriRedirect[]): CoreClient => { - return { - tryResolveUri: async ({ - uri, - }: { - uri: Uri; - }): Promise> => { - while (true) { - const redirect = redirects.find((x) => uri.uri === x.from.uri); - if (redirect) { - uri = redirect.to; - } else { - return ResultOk({ - type: "uri", - uri, - }); - } - } - }, - } as CoreClient; -}; - -describe("getImplementations", () => { - it("works with complex redirects", async () => { - const interface1Uri = "wrap://ens/some-interface1.eth"; - const interface2Uri = "wrap://ens/some-interface2.eth"; - const interface3Uri = "wrap://ens/some-interface3.eth"; - - const implementation1Uri = "wrap://ens/some-implementation.eth"; - const implementation2Uri = "wrap://ens/some-implementation2.eth"; - const implementation3Uri = "wrap://ens/some-implementation3.eth"; - - const redirects: IUriRedirect[] = [ - { - from: new Uri(interface1Uri), - to: new Uri(interface2Uri), - }, - { - from: new Uri(implementation1Uri), - to: new Uri(implementation2Uri), - }, - { - from: new Uri(implementation2Uri), - to: new Uri(implementation3Uri), - }, - ]; - - const interfaces: UriMap = new UriMap([ - [ - Uri.from(interface1Uri), - [Uri.from(implementation1Uri), Uri.from(implementation2Uri)], - ], - [Uri.from(interface2Uri), [Uri.from(implementation3Uri)]], - [Uri.from(interface3Uri), [Uri.from(implementation3Uri)]], - ]); - - const getImplementationsResult1 = await getImplementations( - new Uri(interface1Uri), - interfaces, - getClient(redirects) - ); - const getImplementationsResult2 = await getImplementations( - new Uri(interface2Uri), - interfaces, - getClient(redirects) - ); - const getImplementationsResult3 = await getImplementations( - new Uri(interface3Uri), - interfaces, - getClient(redirects) - ); - - expect(getImplementationsResult1).toEqual( - ResultOk([ - new Uri(implementation1Uri), - new Uri(implementation2Uri), - new Uri(implementation3Uri), - ]) - ); - - expect(getImplementationsResult2).toEqual( - ResultOk([ - new Uri(implementation1Uri), - new Uri(implementation2Uri), - new Uri(implementation3Uri), - ]) - ); - - expect(getImplementationsResult3).toEqual( - ResultOk([new Uri(implementation3Uri)]) - ); - }); - - it("interface implementations are not redirected", async () => { - const interface1Uri = "wrap://ens/some-interface1.eth"; - - const implementation1Uri = "wrap://ens/some-implementation.eth"; - const implementation2Uri = "wrap://ens/some-implementation2.eth"; - - const redirects: IUriRedirect[] = [ - { - from: new Uri(implementation1Uri), - to: new Uri(implementation2Uri), - }, - ]; - - const interfaces: UriMap = new UriMap([ - [Uri.from(interface1Uri), [Uri.from(implementation1Uri)]], - ]); - - const result = await getImplementations( - new Uri(interface1Uri), - interfaces, - getClient(redirects) - ); - - expect(result).toEqual(ResultOk([new Uri(implementation1Uri)])); - }); -}); diff --git a/packages/js/core/src/__tests__/is-buffer.spec.ts b/packages/js/core/src/__tests__/is-buffer.spec.ts deleted file mode 100644 index 57990ac379..0000000000 --- a/packages/js/core/src/__tests__/is-buffer.spec.ts +++ /dev/null @@ -1,15 +0,0 @@ -import { isBuffer } from "../utils/is-buffer"; - -it("Should check if object is buffer", () => { - const array = [ - 130, 168, 102, 105, 114, 115, 116, 75, - 101, 121, 170, 102, 105, 114, 115, 116, - 86, 97, 108, 117, 101, 169, 115, 101, - 99, 111, 110, 100, 75, 101, 121, 171, - 115, 101, 99, 111, 110, 100, 86, 97, - 108, 117, 101 - ] - expect(isBuffer(array)).toBeFalsy(); - expect(isBuffer(Uint8Array.from(array))).toBeTruthy(); - expect(isBuffer(Uint8Array.from(array).buffer)).toBeTruthy(); -}); diff --git a/packages/js/core/src/__tests__/typesHandler.spec.ts b/packages/js/core/src/__tests__/typesHandler.spec.ts deleted file mode 100644 index 9fd052261c..0000000000 --- a/packages/js/core/src/__tests__/typesHandler.spec.ts +++ /dev/null @@ -1,57 +0,0 @@ -import { typesHandler } from "../utils"; - -describe('typesHandler', () => { - it('should return the original value if it is not a Map', () => { - const value = { a: 1 }; - expect(typesHandler(undefined, value)).toEqual(value); - }); - - it('should return an empty object if the Map keys are not of type string', () => { - const value = new Map([[1, 'one'], [2, 'two']]); - expect(typesHandler(undefined, value)).toEqual({}); - }); - - it('should convert empty Map into empty object', () => { - const value = new Map(); - const expected = {}; - expect(typesHandler(undefined, value)).toEqual(expected); - }); - - it('should convert Map object with string keys into object with key-value pairs', () => { - const value = new Map([['a', 1], ['b', 2]]); - const expected = { a: 1, b: 2 }; - expect(typesHandler(undefined, value)).toEqual(expected); - }); - - it('should correctly stringify a Map object with string keys', () => { - const myObject = { - myMap: new Map([['a', 1], ['b', 2]]) - }; - const expected = '{\n "myMap": {\n "a": 1,\n "b": 2\n }\n}'; - - const stringified = JSON.stringify(myObject, typesHandler, 2); - expect(stringified).toEqual(expected); - }); - - it('should correctly stringify a Map object with non-string values', () => { - const myObject = { - myMap: new Map([['a', { foo: 'bar' }]]) - }; - const expected = '{\n "myMap": {\n "a": {\n "foo": "bar"\n }\n }\n}'; - - const stringified = JSON.stringify(myObject, typesHandler, 2); - - expect(stringified).toEqual(expected); - }); - - it('should correctly stringify a non-Map object', () => { - const myObject = { - foo: 'bar', - baz: 42 - }; - const expected = '{\n "foo": "bar",\n "baz": 42\n}'; - - const stringified = JSON.stringify(myObject, typesHandler, 2); - expect(stringified).toEqual(expected); - }); -}); diff --git a/packages/js/core/src/algorithms/applyResolution.ts b/packages/js/core/src/algorithms/applyResolution.ts deleted file mode 100644 index a86f425d94..0000000000 --- a/packages/js/core/src/algorithms/applyResolution.ts +++ /dev/null @@ -1,17 +0,0 @@ -import { Uri, CoreClient, IUriResolutionContext } from ".."; - -import { Result, ResultOk } from "@polywrap/result"; - -export const applyResolution = async ( - uri: Uri, - client: CoreClient, - resolutionContext?: IUriResolutionContext -): Promise> => { - const result = await client.tryResolveUri({ uri, resolutionContext }); - - if (!result.ok) { - return result; - } - - return ResultOk(result.value.uri); -}; diff --git a/packages/js/core/src/algorithms/clean-uri-history/CleanResolutionStep.ts b/packages/js/core/src/algorithms/clean-uri-history/CleanResolutionStep.ts deleted file mode 100644 index 4e31bf618c..0000000000 --- a/packages/js/core/src/algorithms/clean-uri-history/CleanResolutionStep.ts +++ /dev/null @@ -1 +0,0 @@ -export type CleanResolutionStep = (string | CleanResolutionStep)[]; diff --git a/packages/js/core/src/algorithms/clean-uri-history/buildCleanUriHistory.ts b/packages/js/core/src/algorithms/clean-uri-history/buildCleanUriHistory.ts deleted file mode 100644 index 18732997cd..0000000000 --- a/packages/js/core/src/algorithms/clean-uri-history/buildCleanUriHistory.ts +++ /dev/null @@ -1,89 +0,0 @@ -import { IUriResolutionStep } from "../.."; -import { CleanResolutionStep } from "./CleanResolutionStep"; - -export const buildCleanUriHistory = ( - history: IUriResolutionStep[], - depth?: number -): CleanResolutionStep => { - const cleanHistory: CleanResolutionStep = []; - - if (depth != null) { - depth--; - } - - if (!history) { - return cleanHistory; - } - for (const step of history) { - if (step.result.ok) { - const uriPackageOrWrapper = step.result.value; - - switch (uriPackageOrWrapper.type) { - case "uri": - if (step.sourceUri.uri === uriPackageOrWrapper.uri.uri) { - cleanHistory.push( - step.description - ? `${step.sourceUri.uri} => ${step.description}` - : `${step.sourceUri.uri}` - ); - } else { - cleanHistory.push( - step.description - ? `${step.sourceUri.uri} => ${step.description} => uri (${uriPackageOrWrapper.uri.uri})` - : `${step.sourceUri.uri} => uri (${uriPackageOrWrapper.uri.uri})` - ); - } - break; - case "package": - cleanHistory.push( - step.description - ? `${step.sourceUri.uri} => ${step.description} => package (${uriPackageOrWrapper.uri.uri})` - : `${step.sourceUri.uri} => package (${uriPackageOrWrapper.uri.uri})` - ); - break; - case "wrapper": - cleanHistory.push( - step.description - ? `${step.sourceUri.uri} => ${step.description} => wrapper (${uriPackageOrWrapper.uri.uri})` - : `${step.sourceUri.uri} => wrapper (${uriPackageOrWrapper.uri.uri})` - ); - break; - } - } else { - if (typeof step.result.error === "string") { - cleanHistory.push( - step.description - ? `${step.sourceUri.uri} => ${step.description} => error (${step.result.error})` - : `${step.sourceUri.uri} => error (${step.result.error})` - ); - } else if (step.result.error instanceof Error) { - cleanHistory.push( - step.description - ? `${step.sourceUri.uri} => ${step.description} => error (${step.result.error.message})` - : `${step.sourceUri.uri} => error (${step.result.error.message})` - ); - } else { - cleanHistory.push( - step.description - ? `${step.sourceUri.uri} => ${step.description} => error` - : `${step.sourceUri.uri} => error` - ); - } - } - - if ( - !step.subHistory || - step.subHistory.length === 0 || - (depth != null && depth < 0) - ) { - continue; - } - - const subHistory = buildCleanUriHistory(step.subHistory, depth); - if (subHistory.length > 0) { - cleanHistory.push(subHistory); - } - } - - return cleanHistory; -}; diff --git a/packages/js/core/src/algorithms/clean-uri-history/index.ts b/packages/js/core/src/algorithms/clean-uri-history/index.ts deleted file mode 100644 index 171a629f2b..0000000000 --- a/packages/js/core/src/algorithms/clean-uri-history/index.ts +++ /dev/null @@ -1,2 +0,0 @@ -export * from "./CleanResolutionStep"; -export * from "./buildCleanUriHistory"; diff --git a/packages/js/core/src/algorithms/get-implementations.ts b/packages/js/core/src/algorithms/get-implementations.ts deleted file mode 100644 index 9a23f9ca03..0000000000 --- a/packages/js/core/src/algorithms/get-implementations.ts +++ /dev/null @@ -1,90 +0,0 @@ -import { - Uri, - CoreClient, - WrapError, - WrapErrorCode, - ReadonlyUriMap, -} from "../types"; -import { IUriResolutionContext } from "../uri-resolution"; -import { applyResolution } from "./applyResolution"; - -import { Result, ResultErr, ResultOk } from "@polywrap/result"; - -export const getImplementations = async ( - wrapperInterfaceUri: Uri, - interfaces: ReadonlyUriMap, - client?: CoreClient, - resolutionContext?: IUriResolutionContext -): Promise> => { - const result: Uri[] = []; - - const addUniqueResult = (uri: Uri) => { - // If the URI hasn't been added already - if (result.findIndex((i) => Uri.equals(i, uri)) === -1) { - result.push(uri); - } - }; - - const addAllImplementationsFromImplementationsArray = async ( - impls: ReadonlyUriMap, - wrapperInterfaceUri: Uri - ): Promise> => { - for (const impl of impls.keys()) { - let fullyResolvedUri: Uri; - if (client) { - const redirectsResult = await applyResolution( - impl, - client, - resolutionContext - ); - if (!redirectsResult.ok) { - const error = new WrapError("Failed to resolve redirects", { - uri: impl.uri, - code: WrapErrorCode.CLIENT_GET_IMPLEMENTATIONS_ERROR, - cause: redirectsResult.error, - }); - return ResultErr(error); - } - fullyResolvedUri = redirectsResult.value; - } else { - fullyResolvedUri = impl; - } - - if (Uri.equals(fullyResolvedUri, wrapperInterfaceUri)) { - const implementations = impls.get(impl); - if (implementations) { - for (const implementation of implementations) { - addUniqueResult(Uri.from(implementation)); - } - } - } - } - return ResultOk(undefined); - }; - - let finalUri = wrapperInterfaceUri; - - if (client) { - const redirectsResult = await applyResolution( - wrapperInterfaceUri, - client, - resolutionContext - ); - if (!redirectsResult.ok) { - const error = new WrapError("Failed to resolve redirects", { - uri: wrapperInterfaceUri.uri, - code: WrapErrorCode.CLIENT_GET_IMPLEMENTATIONS_ERROR, - cause: redirectsResult.error, - }); - return ResultErr(error); - } - finalUri = redirectsResult.value; - } - - const addAllImp = await addAllImplementationsFromImplementationsArray( - interfaces, - finalUri - ); - - return addAllImp.ok ? ResultOk(result) : addAllImp; -}; diff --git a/packages/js/core/src/algorithms/index.ts b/packages/js/core/src/algorithms/index.ts deleted file mode 100644 index 2983415b25..0000000000 --- a/packages/js/core/src/algorithms/index.ts +++ /dev/null @@ -1,3 +0,0 @@ -export * from "./applyResolution"; -export * from "./get-implementations"; -export * from "./clean-uri-history"; diff --git a/packages/js/core/src/index.ts b/packages/js/core/src/index.ts deleted file mode 100644 index dd5ce13c32..0000000000 --- a/packages/js/core/src/index.ts +++ /dev/null @@ -1,6 +0,0 @@ -export * from "./types"; -export * from "./algorithms"; -export * from "./interfaces"; -export * from "./uri-resolution"; -export * from "./utils"; -export { Result } from "@polywrap/result"; diff --git a/packages/js/core/src/interfaces/index.ts b/packages/js/core/src/interfaces/index.ts deleted file mode 100644 index 0692db5fd5..0000000000 --- a/packages/js/core/src/interfaces/index.ts +++ /dev/null @@ -1 +0,0 @@ -export * as UriResolverInterface from "./uri-resolver"; diff --git a/packages/js/core/src/interfaces/uri-resolver.ts b/packages/js/core/src/interfaces/uri-resolver.ts deleted file mode 100644 index 5b86661cd5..0000000000 --- a/packages/js/core/src/interfaces/uri-resolver.ts +++ /dev/null @@ -1,60 +0,0 @@ -import { Uri, Invoker, WrapError } from "../"; - -import { Result } from "@polywrap/result"; - -// $start: MaybeUriOrManifest -/** Contains either a Uri, a manifest, or neither */ -export interface MaybeUriOrManifest { - /** wrap URI */ - uri?: string | null; - - /** Serialized wrap manifest */ - manifest?: Uint8Array | null; -} -// $end - -export const module = { - // $start: UriResolverInterface-tryResolveUri - /** - * Use an invoker to try to resolve a URI using a wrapper that implements the UriResolver interface - * - * @param invoker - invokes the wrapper with the resolution URI as an argument - * @param wrapper - URI for wrapper that implements the UriResolver interface - * @param uri - the URI to resolve - */ - tryResolveUri: async ( - invoker: Invoker, - wrapper: Uri, - uri: Uri - ): Promise> /* $ */ => { - return invoker.invoke({ - uri: wrapper, - method: `tryResolveUri`, - args: { - authority: uri.authority, - path: uri.path, - }, - }); - }, - // $start: UriResolverInterface-getFile - /** - * Use an invoker to fetch a file using a wrapper that implements the UriResolver interface - * - * @param invoker - invokes the wrapper with the filepath as an argument - * @param wrapper - URI for wrapper that implements the UriResolver interface - * @param path - a filepath, the format of which depends on the UriResolver - */ - getFile: async ( - invoker: Invoker, - wrapper: Uri, - path: string - ): Promise> /* $ */ => { - return invoker.invoke({ - uri: wrapper, - method: "getFile", - args: { - path, - }, - }); - }, -}; diff --git a/packages/js/core/src/types/CoreClient.ts b/packages/js/core/src/types/CoreClient.ts deleted file mode 100644 index da099a6b0f..0000000000 --- a/packages/js/core/src/types/CoreClient.ts +++ /dev/null @@ -1,122 +0,0 @@ -import { Invoker, Uri, WrapError, WrapperEnv } from "."; -import { IUriResolutionContext, IUriResolver } from "../uri-resolution"; -import { UriResolverHandler } from "./UriResolver"; -import { ReadonlyUriMap } from "./UriMap"; - -import { WrapManifest } from "@polywrap/wrap-manifest-types-js"; -import { Result } from "@polywrap/result"; - -// $start: CoreClient.ts - -/** Core Client configuration that can be passed to the PolywrapClient or PolywrapCoreClient constructors */ -export interface CoreClientConfig { - /** register interface implementations */ - readonly interfaces?: ReadonlyUriMap; - - /** set environmental variables for a wrapper */ - readonly envs?: ReadonlyUriMap; - - /** configure URI resolution for redirects, packages, and wrappers */ - readonly resolver: Readonly>; -} - -/** Options for CoreClient's getFile method */ -export interface GetFileOptions { - /** file path from wrapper root */ - path: string; - - /** file encoding */ - encoding?: "utf-8" | string; -} - -/** Options for CoreClient's getImplementations method */ -export interface GetImplementationsOptions { - /** If true, follow redirects to resolve URIs */ - applyResolution?: boolean; - - /** Use and update an existing resolution context */ - resolutionContext?: IUriResolutionContext; -} - -/** Options for CoreClient's validate method */ -export interface ValidateOptions { - /** Validate full ABI */ - abi?: boolean; - - /** Recursively validate import URIs */ - recursive?: boolean; -} - -/** CoreClient invokes wrappers and interacts with wrap packages. */ -export interface CoreClient extends Invoker, UriResolverHandler { - /** - * Returns the configuration used to instantiate the client - * - * @returns an immutable core client config - */ - getConfig(): CoreClientConfig; - - /** - * returns all interfaces from the configuration used to instantiate the client - * - * @returns a Set of interfaces and their registered implementations - */ - getInterfaces(): ReadonlyUriMap | undefined; - - /** - * returns all env registrations from the configuration used to instantiate the client - * - * @returns an array of env objects containing wrapper environmental variables - */ - getEnvs(): ReadonlyUriMap | undefined; - - /** - * returns an env (a set of environmental variables) from the configuration used to instantiate the client - * - * @param uri - the URI used to register the env - * @returns an env, or undefined if an env is not found at the given URI - */ - getEnvByUri(uri: Uri): WrapperEnv | undefined; - - /** - * returns the URI resolver from the configuration used to instantiate the client - * - * @returns an object that implements the IUriResolver interface - */ - getResolver(): IUriResolver; - - /** - * returns a package's wrap manifest - * - * @param uri - a wrap URI - * @returns a Result containing the WrapManifest if the request was successful - */ - getManifest(uri: Uri): Promise>; - - /** - * returns a file contained in a wrap package - * - * @param uri - a wrap URI - * @param options - { path: string; encoding?: "utf-8" | string } - * @returns a Promise of a Result containing a file if the request was successful - */ - getFile( - uri: Uri, - options: GetFileOptions - ): Promise>; - - /** - * returns the interface implementations associated with an interface URI - * from the configuration used to instantiate the client - * - * @param uri - a wrap URI - * @param options - { applyResolution?: boolean; resolutionContext?: IUriResolutionContext } - * @returns a Result containing URI array if the request was successful - */ - getImplementations( - uri: Uri, - options: GetImplementationsOptions - ): Promise>; -} - -// $end diff --git a/packages/js/core/src/types/Env.ts b/packages/js/core/src/types/Env.ts deleted file mode 100644 index 1b88c52c8b..0000000000 --- a/packages/js/core/src/types/Env.ts +++ /dev/null @@ -1,7 +0,0 @@ -// $start: Env.ts - -/** A map of string-indexed, Msgpack-serializable environmental variables associated with a wrapper */ -export interface WrapperEnv { - readonly [k: string]: unknown; -} -// $end diff --git a/packages/js/core/src/types/IUriPackage.ts b/packages/js/core/src/types/IUriPackage.ts deleted file mode 100644 index bad2933fa1..0000000000 --- a/packages/js/core/src/types/IUriPackage.ts +++ /dev/null @@ -1,14 +0,0 @@ -import { Uri, IWrapPackage } from "."; - -// $start: IUriPackage.ts - -/** Associates a URI with an embedded wrap package */ -export interface IUriPackage { - /** The package's URI */ - uri: Uri; - - /** The wrap package */ - package: IWrapPackage; -} - -// $end diff --git a/packages/js/core/src/types/IUriRedirect.ts b/packages/js/core/src/types/IUriRedirect.ts deleted file mode 100644 index 0e7b4ccc0c..0000000000 --- a/packages/js/core/src/types/IUriRedirect.ts +++ /dev/null @@ -1,14 +0,0 @@ -import { Uri } from "."; - -// $start: IUriRedirect.ts - -/** Redirect invocations from one URI to another */ -export interface IUriRedirect { - /** URI to redirect from */ - from: Uri; - - /** URI to redirect to */ - to: Uri; -} - -// $end diff --git a/packages/js/core/src/types/IUriWrapper.ts b/packages/js/core/src/types/IUriWrapper.ts deleted file mode 100644 index a7166609d4..0000000000 --- a/packages/js/core/src/types/IUriWrapper.ts +++ /dev/null @@ -1,14 +0,0 @@ -import { Uri, Wrapper } from "."; - -// $start: IUriWrapper.ts - -/** Associates a URI with an embedded wrapper */ -export interface IUriWrapper { - /** The URI to resolve to the wrapper */ - uri: Uri; - - /** A wrapper instance */ - wrapper: Wrapper; -} - -// $end diff --git a/packages/js/core/src/types/IWrapPackage.ts b/packages/js/core/src/types/IWrapPackage.ts deleted file mode 100644 index ac28aa4726..0000000000 --- a/packages/js/core/src/types/IWrapPackage.ts +++ /dev/null @@ -1,40 +0,0 @@ -import { Wrapper } from "."; - -import { - DeserializeManifestOptions, - WrapManifest, -} from "@polywrap/wrap-manifest-types-js"; -import { Result } from "@polywrap/result"; - -// $start: IWrapPackage.ts - -/** Options for IWrapPackage's getManifest method */ -export interface GetManifestOptions { - /** If true, manifest validation step will be skipped */ - noValidate?: boolean; -} - -/** A wrap package, capable of producing instances of a wrapper and its manifest */ -export interface IWrapPackage { - /** - * Produce an instance of the wrap manifest - * - * @param options - GetManifestOptions; customize manifest retrieval - * @returns A Promise with a Result containing the wrap manifest or an error - */ - getManifest( - options?: GetManifestOptions - ): Promise>; - - /** - * Produce an instance of the wrapper - * - * @param options - DeserializeManifestOptions; customize manifest deserialization - * @returns A Promise with a Result containing the wrapper or an error - */ - createWrapper( - options?: DeserializeManifestOptions - ): Promise>; -} - -// $end diff --git a/packages/js/core/src/types/Invoke.ts b/packages/js/core/src/types/Invoke.ts deleted file mode 100644 index f5f1e25296..0000000000 --- a/packages/js/core/src/types/Invoke.ts +++ /dev/null @@ -1,97 +0,0 @@ -import { WrapError, Uri, Wrapper } from "."; -import { IUriResolutionContext } from "../uri-resolution"; - -import { Result } from "@polywrap/result"; - -// $start: Invoke.ts - -/** Options required for an Wrapper invocation. */ -export interface InvokeOptions { - /** The Wrapper's URI */ - uri: Uri; - - /** Method to be executed. */ - method: string; - - /** Arguments for the method, structured as a map, removing the chance of incorrectly ordered arguments. */ - args?: Record | Uint8Array; - - /** Env variables for the wrapper invocation. */ - env?: Record; - - /** A Uri resolution context */ - resolutionContext?: IUriResolutionContext; -} - -/** - * Result of an Wrapper invocation. - * - * @template TData Type of the invoke result data. - */ -export type InvokeResult = Result; - -/** - * Provides options for the invoker to set based on the state of the invocation. - * Extends InvokeOptions. - */ -export interface InvokerOptions extends InvokeOptions { - /** If true, the InvokeResult will (if successful) contain a Msgpack-encoded byte array */ - encodeResult?: boolean; -} - -/** - * An entity capable of invoking wrappers. - * - * @template TData Type of the invoke result data. - */ -export interface Invoker { - /** - * Invoke a wrapper using an instance of the wrapper. - * - * @param options - invoker options and a wrapper instance to invoke - * @returns A Promise with a Result containing the return value or an error - */ - invokeWrapper( - options: InvokerOptions & { wrapper: Wrapper } - ): Promise>; - - /** - * Invoke a wrapper. - * - * @remarks - * Unlike `invokeWrapper`, this method automatically retrieves and caches the wrapper. - * - * @param options - invoker options - * @returns A Promise with a Result containing the return value or an error - */ - invoke( - options: InvokerOptions - ): Promise>; -} - -/** - * Result of a Wrapper invocation, possibly Msgpack-encoded. - * - * @template TData Type of the invoke result data. - */ -export type InvocableResult = InvokeResult & { - /** If true, result (if successful) contains a Msgpack-encoded byte array */ - encoded?: boolean; -}; - -/** An invocable entity, such as a wrapper. */ -export interface Invocable { - /** - * Invoke this object. - * - * @param options - invoke options - * @param invoker - an Invoker, capable of invoking this object - * @returns A Promise with a Result containing the return value or an error - */ - invoke( - options: InvokeOptions, - invoker: Invoker - ): Promise>; -} - -// $end diff --git a/packages/js/core/src/types/MaybeAsync.ts b/packages/js/core/src/types/MaybeAsync.ts deleted file mode 100644 index 9c47e84aaa..0000000000 --- a/packages/js/core/src/types/MaybeAsync.ts +++ /dev/null @@ -1,6 +0,0 @@ -// $start: MaybeAsync.ts - -/** Alias for a type that is either a value or a promise that resolves to the value */ -export type MaybeAsync = Promise | T; - -// $end diff --git a/packages/js/core/src/types/Uri.ts b/packages/js/core/src/types/Uri.ts deleted file mode 100644 index 755e32a39e..0000000000 --- a/packages/js/core/src/types/Uri.ts +++ /dev/null @@ -1,197 +0,0 @@ -import { Result, ResultErr, ResultOk } from "@polywrap/result"; - -// $start: UriConfig -/** URI configuration */ -export interface UriConfig { - /** URI Authority: allows the Polywrap URI resolution algorithm to determine an authoritative URI resolver. */ - authority: string; - - /** URI Path: tells the Authority where the Wrapper resides. */ - path: string; - - /** Full string representation of URI */ - uri: string; -} -// $end - -// $start: Uri -/** - * A Polywrap URI. Some examples of valid URIs are: - * wrap://ipfs/QmHASH - * wrap://ens/sub.dimain.eth - * wrap://fs/directory/file.txt - * wrap://uns/domain.crypto - * - * Breaking down the various parts of the URI, as it applies - * to [the URI standard](https://tools.ietf.org/html/rfc3986#section-3): - * **wrap://** - URI Scheme: differentiates Polywrap URIs. - * **ipfs/** - URI Authority: allows the Polywrap URI resolution algorithm to determine an authoritative URI resolver. - * **sub.domain.eth** - URI Path: tells the Authority where the Wrapper resides. - */ -export class Uri { - // $end - private _config: UriConfig; - - // $start: Uri-authority - /** @returns Uri authority */ - public get authority(): string /* $ */ { - return this._config.authority; - } - - // $start: Uri-path - /** @returns Uri path */ - public get path(): string /* $ */ { - return this._config.path; - } - - // $start: Uri-uri - /** @returns Uri string representation */ - public get uri(): string /* $ */ { - return this._config.uri; - } - - // $start: Uri-constructor - /** - * Construct a Uri instance from a wrap URI string - * - * @remarks - * Throws if URI string is invalid - * - * @param uri - a string representation of a wrap URI - */ - constructor(uri: string) /* $ */ { - const result = Uri.parseUri(uri); - if (!result.ok) { - throw result.error; - } - this._config = result.value; - } - - // $start: Uri-equals - /** Test two Uri instances for equality */ - public static equals(a: Uri, b: Uri): boolean /* $ */ { - return a.uri === b.uri; - } - - // $start: Uri-isUri - /** - * Check if a value is an instance of Uri - * - * @param value - value to check - * @returns true if value is a Uri instance */ - public static isUri(value: unknown): value is Uri /* $ */ { - return typeof value === "object" && (value as Uri).uri !== undefined; - } - - // $start: Uri-isValidUri - /** - * Test if a URI string is a valid wrap URI - * - * @param uri - URI string - * @param parsed? - UriConfig to update (mutate) with content of URI string - * @returns true if input string is a valid wrap URI */ - public static isValidUri(uri: string, parsed?: UriConfig): boolean /* $ */ { - const result = Uri.parseUri(uri); - - if (parsed && result.ok) { - Object.assign(parsed, result.value); - } - - return result.ok; - } - - // $start: Uri-parseUri - /** - * Parse a wrap URI string into its authority and path - * - * @param uri - a string representation of a wrap URI - * @returns A Result containing a UriConfig, if successful, or an error - */ - public static parseUri(uri: string): Result /* $ */ { - if (!uri) { - return ResultErr(Error("The provided URI is empty")); - } - - let processed = uri; - - // Trim preceding '/' characters - while (processed[0] === "/") { - processed = processed.substring(1); - } - - // Check for the wrap:// scheme, add if it isn't there - const wrapSchemeIdx = processed.indexOf("wrap://"); - - // If it's missing the wrap:// scheme, add it - if (wrapSchemeIdx === -1) { - processed = "wrap://" + processed; - } - - // If the wrap:// is not in the beginning, return an error - if (wrapSchemeIdx > -1 && wrapSchemeIdx !== 0) { - return ResultErr( - Error("The wrap:// scheme must be at the beginning of the URI string") - ); - } - - // Extract the authoriy & path - const result = processed.match(/wrap:\/\/([a-z][a-z0-9-_]+)\/(.*)/); - let uriParts: string[]; - - // Remove all empty strings - if (result) { - uriParts = result.filter((str) => !!str); - } else { - uriParts = []; - } - - if (uriParts.length !== 3) { - return ResultErr( - Error( - `URI is malformed, here are some examples of valid URIs:\n` + - `wrap://ipfs/QmHASH\n` + - `wrap://ens/domain.eth\n` + - `ens/domain.eth\n\n` + - `Invalid URI Received: ${uri}` - ) - ); - } - - return ResultOk({ - uri: processed, - authority: uriParts[1], - path: uriParts[2], - }); - } - - // $start: Uri-from - /** - * Construct a Uri instance from a Uri or a wrap URI string - * - * @remarks - * Throws if URI string is invalid - * - * @param uri - a Uri instance or a string representation of a wrap URI - */ - public static from(uri: Uri | string): Uri /* $ */ { - if (typeof uri === "string") { - return new Uri(uri); - } else if (Uri.isUri(uri)) { - return uri; - } else { - throw Error(`Unknown uri type, cannot convert. ${JSON.stringify(uri)}`); - } - } - - // $start: Uri-toString - /** @returns Uri string representation */ - public toString(): string /* $ */ { - return this._config.uri; - } - - // $start: Uri-toJSON - /** @returns Uri string representation */ - public toJSON(): string /* $ */ { - return this._config.uri; - } -} diff --git a/packages/js/core/src/types/UriMap.ts b/packages/js/core/src/types/UriMap.ts deleted file mode 100644 index a6e218cdd6..0000000000 --- a/packages/js/core/src/types/UriMap.ts +++ /dev/null @@ -1,67 +0,0 @@ -import { Uri } from "./Uri"; - -export class UriMap - implements Map, ReadonlyUriMap { - private map: Map; - - constructor(entries?: readonly (readonly [Uri, TValue])[]) { - this.map = new Map(entries?.map((x) => [x[0].uri, x[1]])); - } - - clear(): void { - this.map.clear(); - } - - delete(key: Uri): boolean { - return this.map.delete(key.uri); - } - - forEach( - callbackfn: (value: TValue, key: Uri, map: Map) => void, - thisArg?: unknown - ): void { - this.map.forEach((v, k) => callbackfn(v, Uri.from(k), this), thisArg); - } - - get(key: Uri): TValue | undefined { - return this.map.get(key.uri); - } - - has(key: Uri): boolean { - return this.map.has(key.uri); - } - - set(key: Uri, value: TValue): this { - this.map.set(key.uri, value); - - return this; - } - - get size(): number { - return this.map.size; - } - - [Symbol.toStringTag] = "UriMap"; - - *entries(): IterableIterator<[Uri, TValue]> { - for (const [k, v] of this.map.entries()) { - yield [Uri.from(k), v]; - } - } - - *keys(): IterableIterator { - for (const k of this.map.keys()) { - yield Uri.from(k); - } - } - - values(): IterableIterator { - return this.map.values(); - } - - [Symbol.iterator](): IterableIterator<[Uri, TValue]> { - return this.entries(); - } -} - -export type ReadonlyUriMap = ReadonlyMap; diff --git a/packages/js/core/src/types/UriResolver.ts b/packages/js/core/src/types/UriResolver.ts deleted file mode 100644 index 05a49a6812..0000000000 --- a/packages/js/core/src/types/UriResolver.ts +++ /dev/null @@ -1,30 +0,0 @@ -import { Uri } from "."; -import { IUriResolutionContext, UriPackageOrWrapper } from "../uri-resolution"; - -import { Result } from "@polywrap/result"; - -// $start: UriResolver.ts - -/** Options required for URI resolution. */ -export interface TryResolveUriOptions { - /** The Wrapper's URI */ - uri: Uri; - - /** A URI resolution context */ - resolutionContext?: IUriResolutionContext; -} - -/** An entity capable of resolving a wrap URI, typically by using an IUriResolver implementation */ -export interface UriResolverHandler { - /** - * Resolve a URI to a wrap package, a wrapper, or a uri - * - * @param options - TryResolveUriOptions - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - tryResolveUri( - options?: TryResolveUriOptions - ): Promise>; -} - -// $end diff --git a/packages/js/core/src/types/WrapError.ts b/packages/js/core/src/types/WrapError.ts deleted file mode 100644 index 38641858b1..0000000000 --- a/packages/js/core/src/types/WrapError.ts +++ /dev/null @@ -1,293 +0,0 @@ -import { CleanResolutionStep } from "../algorithms"; - -export type ErrorSource = Readonly<{ - file?: string; - row?: number; - col?: number; -}>; - -/** -Wrap error codes provide additional context to WrapErrors. - -Error code naming convention (approximate): - type of handler - type of functionality - piece of functionality - ==> handler_typeFn_pieceFn - -Error code map: - 0 -> Invalid - 1-25 -> Client - 26-50 -> URI resolution - 51-75 -> Wrapper invocation & sub-invocation - 76-255 -> Unallocated - */ -export enum WrapErrorCode { - CLIENT_LOAD_WRAPPER_ERROR = 1, - CLIENT_GET_FILE_ERROR, - CLIENT_GET_IMPLEMENTATIONS_ERROR, - CLIENT_VALIDATE_RESOLUTION_FAIL, - CLIENT_VALIDATE_ABI_FAIL, - CLIENT_VALIDATE_RECURSIVE_FAIL, - URI_RESOLUTION_ERROR = 26, - URI_RESOLVER_ERROR, - URI_NOT_FOUND, - WRAPPER_INVOKE_ABORTED = 51, - WRAPPER_SUBINVOKE_ABORTED, - WRAPPER_INVOKE_FAIL, - WRAPPER_READ_FAIL, - WRAPPER_INTERNAL_ERROR, - WRAPPER_METHOD_NOT_FOUND, - WRAPPER_ARGS_MALFORMED, -} - -export interface WrapErrorOptions { - code: WrapErrorCode; - uri: string; - method?: string; - args?: string; - source?: ErrorSource; - resolutionStack?: CleanResolutionStep; - cause?: unknown; - innerError?: WrapError; -} - -type RegExpGroups = - | (RegExpExecArray & { - groups?: { [name in T]: string | undefined } | { [key: string]: string }; - }) - | null; - -export class WrapError extends Error { - readonly name: string = "WrapError"; - readonly code: WrapErrorCode; - readonly reason: string; - readonly uri: string; - readonly method?: string; - readonly args?: string; - readonly source?: ErrorSource; - readonly resolutionStack?: CleanResolutionStep; - readonly cause?: unknown; - readonly innerError?: WrapError; - - constructor(reason = "Encountered an exception.", options: WrapErrorOptions) { - super(WrapError.stringify(reason, options)); - - this.code = options.code; - this.reason = reason; - this.uri = options.uri; - this.method = options.method; - this.args = options.args; - this.source = options.source; - this.resolutionStack = options.resolutionStack; - this.cause = options.cause; - this.innerError = options.innerError; - - Object.setPrototypeOf(this, WrapError.prototype); - Error.captureStackTrace(this, this.constructor); - } - - private static re = new RegExp( - [ - /^(?:[A-Za-z_:()` ]*;? "?)?WrapError: (?(?:.|\r|\n)*)/.source, - // there is some padding added to the number of words expected in an error code - /(?:\r\n|\r|\n)code: (?1?[0-9]{1,2}|2[0-4][0-9]|25[0-5]) (?:[A-Z]+ ?){1,5}/ - .source, - /(?:\r\n|\r|\n)uri: (?wrap:\/\/[A-Za-z0-9_-]+\/.+)/.source, - /(?:(?:\r\n|\r|\n)method: (?([A-Za-z_]{1}[A-Za-z0-9_]*)))?/ - .source, - /(?:(?:\r\n|\r|\n)args: (?\{(?:.|\r|\n)+} ))?/.source, - /(?:(?:\r\n|\r|\n)source: \{ file: "(?.+)", row: (?[0-9]+), col: (?[0-9]+) })?/ - .source, - /(?:(?:\r\n|\r|\n)uriResolutionStack: (?\[(?:.|\r|\n)+]))?/ - .source, - /(?:(?:\r\n|\r|\n){2}This exception was caused by the following exception:(?:\r\n|\r|\n)(?(?:.|\r|\n)+))?/ - .source, - /"?$/.source, - ].join("") - ); - - static parse(error: string): WrapError | undefined { - error = WrapError.sanitizeUnwrappedRustResult(error); - const delim = "\n\nAnother exception was encountered during execution:\n"; - const errorStrings = error.split(delim); - - // case: single WrapError or not a WrapError - if (errorStrings.length === 1) { - const args = WrapError._parse(error); - return args ? new WrapError(args.reason, args.options) : undefined; - } - - // case: stack of WrapErrors stringified - const errArgs = errorStrings.map(WrapError._parse); - - // iterate through args to assign `cause` and `prev` - let curr: WrapError | undefined = undefined; - for (let i = errArgs.length - 1; i >= 0; i--) { - const currArgs = errArgs[i]; - if (!currArgs) { - // should only happen if a user includes the delimiter in their error message - throw new Error("Failed to parse WrapError"); - } - curr = new WrapError(currArgs.reason, { - ...currArgs.options, - innerError: curr, - }); - } - return curr; - } - - toString(): string { - return `${this.name}: ${this.message}`; - } - - toJSON(): string { - return this.toString(); - } - - // remove escape characters that may have been added by Rust - private static sanitizeUnwrappedRustResult(error: string): string { - if ( - error.startsWith( - "__wrap_abort: called `Result::unwrap()` on an `Err` value: " - ) - ) { - error = error.replace(/\\"/g, '"'); - error = error.replace(/\\n/g, "\n"); - } - return error; - } - - // parse a single WrapError, where the 'prev' property is undefined - private static _parse( - error: string - ): { reason: string; options: WrapErrorOptions } | undefined { - const result: RegExpGroups< - | "code" - | "reason" - | "uri" - | "method" - | "args" - | "file" - | "row" - | "col" - | "resolutionStack" - | "cause" - > = WrapError.re.exec(error); - if (!result) { - return undefined; - } - const { - code: codeStr, - reason, - uri, - method, - args, - file, - row, - col, - resolutionStack: resolutionStackStr, - cause, - // eslint-disable-next-line @typescript-eslint/no-non-null-assertion - } = result.groups!; - - const code = parseInt(codeStr as string); - - const source: ErrorSource | undefined = file - ? { - file, - row: row ? parseInt(row) : undefined, - col: col ? parseInt(col) : undefined, - } - : undefined; - - const resolutionStack = resolutionStackStr - ? JSON.parse(resolutionStackStr) - : undefined; - - return { - reason: reason as string, - options: { - code, - uri: uri as string, - method, - args: args?.trim(), - source, - resolutionStack, - cause, - }, - }; - } - - private static stringify(reason: string, options: WrapErrorOptions) { - const { - code, - uri, - method, - args, - source, - resolutionStack, - cause, - innerError, - } = options; - const formattedCode = `${code} ${WrapErrorCode[code].replace(/_/g, " ")}`; - - // Some items are not always present - const maybeMethod = method ? `method: ${method}` : ""; - const maybeArgs = args ? `args: ${args} ` : ""; - // source is uses () instead of {} to facilitate regex - const maybeSource = source - ? `source: { file: "${source?.file}", row: ${source?.row}, col: ${source?.col} }` - : ""; - const maybeResolutionStack = resolutionStack - ? `uriResolutionStack: ${JSON.stringify(resolutionStack, null, 2)}` - : ""; - - const errorCause = WrapError.stringifyCause(cause); - const maybeCause = errorCause - ? `\nThis exception was caused by the following exception:\n${errorCause}` - : ""; - - const maybeDelim = innerError - ? `\nAnother exception was encountered during execution:\n${innerError}` - : ""; - - return [ - `${reason}`, - `code: ${formattedCode}`, - `uri: ${uri}`, - maybeMethod, - maybeArgs, - maybeSource, - maybeResolutionStack, - maybeCause, - maybeDelim, - ] - .filter((it) => !!it) - .join("\n"); - } - - private static stringifyCause(cause: unknown): string | undefined { - if (cause === undefined || cause === null) { - return undefined; - } else if (cause instanceof Error) { - return cause.toString(); - } else if (typeof cause === "object" && cause) { - if ( - cause.toString !== Object.prototype.toString && - typeof cause.toString === "function" - ) { - return cause.toString(); - } - return JSON.stringify(cause); - } else if ( - typeof cause === "function" && - cause.toString !== Object.prototype.toString && - typeof cause.toString === "function" - ) { - return cause.toString(); - } else { - return `${cause}`; - } - } -} diff --git a/packages/js/core/src/types/Wrapper.ts b/packages/js/core/src/types/Wrapper.ts deleted file mode 100644 index 83fd65f96a..0000000000 --- a/packages/js/core/src/types/Wrapper.ts +++ /dev/null @@ -1,46 +0,0 @@ -import { - GetFileOptions, - InvokeOptions, - Invocable, - Invoker, - InvocableResult, -} from "."; - -import { WrapManifest } from "@polywrap/wrap-manifest-types-js"; -import { Result } from "@polywrap/result"; - -// $start: Wrapper.ts - -/** - * The Wrapper definition, which can be used to spawn - * many invocations of this particular Wrapper. Internally - * this class may do things like caching WASM bytecode, spawning - * worker threads, or indexing into resolvers to find the requested method. - */ -export interface Wrapper extends Invocable { - /** - * Invoke the Wrapper based on the provided [[InvokeOptions]] - * - * @param options Options for this invocation. - * @param invoker The client instance requesting this invocation. - * This client will be used for any sub-invokes that occur. - */ - invoke( - options: InvokeOptions, - invoker: Invoker - ): Promise>; - - /** - * Get a file from the Wrapper package. - * - * @param options Configuration options for file retrieval - */ - getFile(options: GetFileOptions): Promise>; - - /** - * Get a manifest from the Wrapper package. - */ - getManifest(): WrapManifest; -} - -// $end diff --git a/packages/js/core/src/types/index.ts b/packages/js/core/src/types/index.ts deleted file mode 100644 index 832a906a57..0000000000 --- a/packages/js/core/src/types/index.ts +++ /dev/null @@ -1,13 +0,0 @@ -export * from "./Wrapper"; -export * from "./CoreClient"; -export * from "./Invoke"; -export * from "./MaybeAsync"; -export * from "./Uri"; -export * from "./Env"; -export * from "./UriResolver"; -export * from "./IWrapPackage"; -export * from "./IUriRedirect"; -export * from "./IUriWrapper"; -export * from "./IUriPackage"; -export * from "./WrapError"; -export * from "./UriMap"; diff --git a/packages/js/core/src/uri-resolution/IUriResolutionContext.ts b/packages/js/core/src/uri-resolution/IUriResolutionContext.ts deleted file mode 100644 index 7e04869a88..0000000000 --- a/packages/js/core/src/uri-resolution/IUriResolutionContext.ts +++ /dev/null @@ -1,56 +0,0 @@ -import { IUriResolutionStep } from "./IUriResolutionStep"; -import { Uri } from ".."; - -// $start: IUriResolutionContext -/** Track and output URI resolution state, path, and history */ -export interface IUriResolutionContext { - /** - * Check if a URI is in the process of being resolved - * - * @param uri - URI to check - * @return true if URI resolution is in process, false otherwise - */ - isResolving(uri: Uri): boolean; - - /** - * Start resolving a URI - * - * @param uri - Uri to resolve - */ - startResolving(uri: Uri): void; - - /** - * Stop resolving a URI - * - * @param uri - Uri being resolved - */ - stopResolving(uri: Uri): void; - - /** - * Push a step onto the resolution history stack - * - * @param step - A completed resolution step - */ - trackStep(step: IUriResolutionStep): void; - - /** @return history of all URI resolution steps completed */ - getHistory(): IUriResolutionStep[]; - - /** @return current URI resolution path */ - getResolutionPath(): Uri[]; - - /** - * Create a new resolution context using the current URI resolution path - * - * @return a UriResolutionContext - */ - createSubHistoryContext(): IUriResolutionContext; - - /** - * Create a new resolution context using the current URI resolution history - * - * @return a UriResolutionContext - */ - createSubContext(): IUriResolutionContext; -} -// $end diff --git a/packages/js/core/src/uri-resolution/IUriResolutionStep.ts b/packages/js/core/src/uri-resolution/IUriResolutionStep.ts deleted file mode 100644 index 535796f78f..0000000000 --- a/packages/js/core/src/uri-resolution/IUriResolutionStep.ts +++ /dev/null @@ -1,21 +0,0 @@ -import { Uri } from ".."; -import { UriPackageOrWrapper } from "./UriPackageOrWrapper"; - -import { Result } from "@polywrap/result"; - -// $start: IUriResolutionStep -/** A step in the URI resolution algorithm */ -export interface IUriResolutionStep { - /** The current URI being resolved */ - sourceUri: Uri; - - /** The resolution result for the current URI */ - result: Result; - - /** A text/visual description of this URI step */ - description?: string; - - /** History of sub-steps that exist within the context of this URI resolution step */ - subHistory?: IUriResolutionStep[]; -} -// $end diff --git a/packages/js/core/src/uri-resolution/IUriResolver.ts b/packages/js/core/src/uri-resolution/IUriResolver.ts deleted file mode 100644 index 4d7d0667c9..0000000000 --- a/packages/js/core/src/uri-resolution/IUriResolver.ts +++ /dev/null @@ -1,24 +0,0 @@ -import { Uri, CoreClient } from ".."; -import { IUriResolutionContext } from "./IUriResolutionContext"; -import { UriPackageOrWrapper } from "./UriPackageOrWrapper"; - -import { Result } from "@polywrap/result"; - -// $start: IUriResolver -/** Defines entity capable of resolving a wrap URI */ -export interface IUriResolver { - /** - * Resolve a URI to a wrap package, a wrapper, or a uri - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise>; -} -// $end diff --git a/packages/js/core/src/uri-resolution/UriPackageOrWrapper.ts b/packages/js/core/src/uri-resolution/UriPackageOrWrapper.ts deleted file mode 100644 index 5d54e5cd6c..0000000000 --- a/packages/js/core/src/uri-resolution/UriPackageOrWrapper.ts +++ /dev/null @@ -1,25 +0,0 @@ -import { Uri } from ".."; -import { IUriPackage, IUriWrapper } from "../types"; - -// $start: UriPackageOrWrapper.ts - -/** Indicates that a URI resolved to a Uri */ -export type UriValue = { - type: "uri"; - uri: Uri; -}; - -/** Indicates that a URI resolved to a wrap package */ -export type UriPackageValue = IUriPackage & { - type: "package"; -}; - -/** Indicates that a URI resolved to a wrapper */ -export type UriWrapperValue = IUriWrapper & { - type: "wrapper"; -}; - -/** indicates that a URI resolved to either a wrap package, a wrapper, or a URI */ -export type UriPackageOrWrapper = UriValue | UriPackageValue | UriWrapperValue; - -// $end diff --git a/packages/js/core/src/uri-resolution/UriResolutionContext.ts b/packages/js/core/src/uri-resolution/UriResolutionContext.ts deleted file mode 100644 index 98a263f05b..0000000000 --- a/packages/js/core/src/uri-resolution/UriResolutionContext.ts +++ /dev/null @@ -1,77 +0,0 @@ -import { IUriResolutionStep } from "./IUriResolutionStep"; -import { IUriResolutionContext } from "./IUriResolutionContext"; -import { Uri } from "../types"; - -// $start: UriResolutionContext -/** An implementation of the IUriResolutionContext interface */ -export class UriResolutionContext implements IUriResolutionContext { - // $end - private _resolvingUriMap: Map; - private _resolutionPath: Set; - private _history: IUriResolutionStep[]; - - // $start: UriResolutionContext-constructor - /** Construct a UriResolutionContext */ - constructor(); - constructor( - resolvingUriMap: Map, - resolutionPath: Set - ); - constructor( - resolvingUriMap: Map, - history: IUriResolutionStep[] - ); - constructor( - resolvingUriMap?: Map, - resolutionPathOrHistory?: Set | IUriResolutionStep[] - ) /* $ */ { - this._resolvingUriMap = resolvingUriMap ?? new Map(); - - if (Array.isArray(resolutionPathOrHistory)) { - this._resolutionPath = new Set(); - this._history = resolutionPathOrHistory; - } else if (resolutionPathOrHistory instanceof Set) { - this._resolutionPath = resolutionPathOrHistory; - this._history = []; - } else { - this._resolutionPath = new Set(); - this._history = []; - } - } - - isResolving(uri: Uri): boolean { - return !!this._resolvingUriMap.get(uri.toString()); - } - - startResolving(uri: Uri): void { - this._resolvingUriMap.set(uri.toString(), true); - this._resolutionPath.add(uri.toString()); - } - - stopResolving(uri: Uri): void { - this._resolvingUriMap.delete(uri.toString()); - } - - trackStep(step: IUriResolutionStep): void { - this._history.push(step); - } - - getHistory(): IUriResolutionStep[] { - return this._history; - } - - getResolutionPath(): Uri[] { - return [...this._resolutionPath].map((x) => new Uri(x)); - } - - createSubHistoryContext(): IUriResolutionContext { - return new UriResolutionContext( - this._resolvingUriMap, - this._resolutionPath - ); - } - - createSubContext(): IUriResolutionContext { - return new UriResolutionContext(this._resolvingUriMap, this._history); - } -} diff --git a/packages/js/core/src/uri-resolution/index.ts b/packages/js/core/src/uri-resolution/index.ts deleted file mode 100644 index 94cbea5324..0000000000 --- a/packages/js/core/src/uri-resolution/index.ts +++ /dev/null @@ -1,5 +0,0 @@ -export * from "./IUriResolutionStep"; -export * from "./IUriResolver"; -export * from "./UriPackageOrWrapper"; -export * from "./IUriResolutionContext"; -export * from "./UriResolutionContext"; diff --git a/packages/js/core/src/utils/combinePaths.ts b/packages/js/core/src/utils/combinePaths.ts deleted file mode 100644 index 01824d7ef3..0000000000 --- a/packages/js/core/src/utils/combinePaths.ts +++ /dev/null @@ -1,17 +0,0 @@ -export const combinePaths = (a: string, b: string): string => { - // Normalize all path separators - a = a.replace(/\\/g, "/"); - b = b.replace(/\\/g, "/"); - - // Append a separator if one doesn't exist - if (a[a.length - 1] !== "/") { - a += "/"; - } - - // Remove any leading separators from - while (b[0] === "/" || b[0] === ".") { - b = b.substring(1); - } - - return a + b; -}; diff --git a/packages/js/core/src/utils/getEnvFromUriHistory.ts b/packages/js/core/src/utils/getEnvFromUriHistory.ts deleted file mode 100644 index 4bf6623798..0000000000 --- a/packages/js/core/src/utils/getEnvFromUriHistory.ts +++ /dev/null @@ -1,16 +0,0 @@ -import { Uri, CoreClient, WrapperEnv } from "../types"; - -export const getEnvFromUriHistory = ( - uriHistory: Uri[], - client: CoreClient -): Readonly | undefined => { - for (const uri of uriHistory) { - const env = client.getEnvByUri(uri); - - if (env) { - return env; - } - } - - return undefined; -}; diff --git a/packages/js/core/src/utils/index.ts b/packages/js/core/src/utils/index.ts deleted file mode 100644 index f52298232c..0000000000 --- a/packages/js/core/src/utils/index.ts +++ /dev/null @@ -1,4 +0,0 @@ -export * from "./combinePaths"; -export * from "./getEnvFromUriHistory"; -export * from "./is-buffer"; -export * from "./typesHandler"; diff --git a/packages/js/core/src/utils/is-buffer.ts b/packages/js/core/src/utils/is-buffer.ts deleted file mode 100644 index c2245a87ae..0000000000 --- a/packages/js/core/src/utils/is-buffer.ts +++ /dev/null @@ -1,7 +0,0 @@ -export function isBuffer(maybeBuf: unknown): maybeBuf is BufferSource { - if (maybeBuf instanceof ArrayBuffer || ArrayBuffer.isView(maybeBuf)) { - return true; - } else { - return false; - } -} diff --git a/packages/js/core/src/utils/typesHandler.ts b/packages/js/core/src/utils/typesHandler.ts deleted file mode 100644 index ae6d083327..0000000000 --- a/packages/js/core/src/utils/typesHandler.ts +++ /dev/null @@ -1,24 +0,0 @@ -/** - * Converts a Map object with string keys into an object with key-value pairs - * that can be stringified using JSON.stringify. Returns an empty object if the - * keys are not of type string. Returns the original value if it is not a Map. - * - * @param _ Unused. - * @param value The value from the object to be stringified. - * @returns The converted object or the original value if it is not a Map - * or if the Map's keys are not of type string. - */ -export const typesHandler = (_: unknown, value: unknown): unknown => { - if (value instanceof Map) { - const obj: Record = {}; - const firstKey = value.keys().next().value; - if (typeof firstKey === "string") { - for (const [k, v] of value.entries()) { - obj[k] = v; - } - } - return obj; - } - - return value; -}; diff --git a/packages/js/core/tsconfig.build.json b/packages/js/core/tsconfig.build.json deleted file mode 100644 index 9708b5768a..0000000000 --- a/packages/js/core/tsconfig.build.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "extends": "./tsconfig.json", - "include": [ - "./src/**/*.ts" - ], - "exclude": [ - "./src/**/__tests__" - ] -} \ No newline at end of file diff --git a/packages/js/core/tsconfig.json b/packages/js/core/tsconfig.json deleted file mode 100644 index 5d37204c00..0000000000 --- a/packages/js/core/tsconfig.json +++ /dev/null @@ -1,10 +0,0 @@ -{ - "extends": "../../../tsconfig", - "compilerOptions": { - "outDir": "build" - }, - "include": [ - "./src/**/*.ts" - ], - "exclude": [] -} diff --git a/packages/js/manifests/wrap/README.md b/packages/js/manifests/wrap/README.md deleted file mode 100644 index 7aacc21985..0000000000 --- a/packages/js/manifests/wrap/README.md +++ /dev/null @@ -1,3 +0,0 @@ -# @polywrap/wrap-manifest-types-js - -TypeScript typings for the `@polywrap/wrap-manifest-schemas` package. diff --git a/packages/js/manifests/wrap/jest.config.js b/packages/js/manifests/wrap/jest.config.js deleted file mode 100644 index a5ca876a5a..0000000000 --- a/packages/js/manifests/wrap/jest.config.js +++ /dev/null @@ -1,11 +0,0 @@ -module.exports = { - collectCoverage: true, - preset: 'ts-jest', - testEnvironment: 'node', - testMatch: ["**/?(*.)+(spec|test).[jt]s?(x)"], - globals: { - 'ts-jest': { - diagnostics: false - } - } -}; diff --git a/packages/js/manifests/wrap/package.json b/packages/js/manifests/wrap/package.json deleted file mode 100644 index bcb50ce796..0000000000 --- a/packages/js/manifests/wrap/package.json +++ /dev/null @@ -1,42 +0,0 @@ -{ - "name": "@polywrap/wrap-manifest-types-js", - "description": "WRAP Manifest TypeScript Typings", - "version": "0.10.0", - "license": "MIT", - "repository": { - "type": "git", - "url": "https://github.com/polywrap/monorepo.git" - }, - "main": "./build/index.js", - "scripts": { - "build": "rimraf ./build && tsc --project tsconfig.build.json", - "prebuild": "ts-node ./scripts/generate.ts", - "test": "jest --passWithNoTests --runInBand --verbose", - "test:watch": "yarn test -- --watch" - }, - "dependencies": { - "@apidevtools/json-schema-ref-parser": "9.0.9", - "jsonschema": "1.4.0", - "semver": "7.5.0" - }, - "devDependencies": { - "@polywrap/msgpack-js": "0.10.0", - "@polywrap/os-js": "0.10.0", - "@polywrap/wrap-manifest-schemas": "0.9.3", - "@types/jest": "26.0.8", - "@types/mustache": "4.0.1", - "@types/prettier": "2.6.0", - "@types/semver": "7.3.11", - "jest": "26.6.3", - "json-schema-to-typescript": "11.0.2", - "mustache": "4.0.1", - "rimraf": "3.0.2", - "ts-jest": "26.5.4", - "ts-node": "10.9.1", - "typescript": "4.9.5" - }, - "gitHead": "7346adaf5adb7e6bbb70d9247583e995650d390a", - "publishConfig": { - "access": "public" - } -} diff --git a/packages/js/manifests/wrap/scripts/generate.ts b/packages/js/manifests/wrap/scripts/generate.ts deleted file mode 100644 index da89fac070..0000000000 --- a/packages/js/manifests/wrap/scripts/generate.ts +++ /dev/null @@ -1,181 +0,0 @@ -import path from "path"; -import fs from "fs"; -import axios from "axios"; -import * as os from "@polywrap/os-js"; -import Mustache from "mustache"; -import { compile } from "json-schema-to-typescript"; -import { FileInfo, bundle, JSONSchema } from "@apidevtools/json-schema-ref-parser"; -// Workaround: https://github.com/APIDevTools/json-schema-ref-parser/issues/139#issuecomment-940500698 -import $RefParser from '@apidevtools/json-schema-ref-parser'; -$RefParser.bundle = $RefParser.bundle.bind($RefParser); - -async function wrapCodegen() { - const formatTypeName = "wrap.info"; - const wrapOutputDir = path.join( - __dirname, - `../src/formats/${formatTypeName}` - ); - - const wrapSchemas: JSONSchema[] = []; - - const wrapModules: { - interface: string; - version: string; - abiVersion: string; - }[] = []; - - const versions = ( - await axios.get( - "https://raw.githubusercontent.com/polywrap/wrap/master/manifest/wrap.info/versions.json" - ) - ).data; - for (const version of versions) { - const wrapSchema = (await axios.get( - `https://raw.githubusercontent.com/polywrap/wrap/master/manifest/wrap.info/${version}.json` - )).data; - - const bundledSchema = await bundle(wrapSchema, { - resolve: { - http: { - read: async (file: FileInfo) => { - const response = await axios.get(file.url); - return response.data; - }, - }, - }, - }); - - wrapSchemas.push(bundledSchema); - - // Convert it to a TypeScript interface - let tsFile = await compile(bundledSchema as any, wrapSchema.id, {additionalProperties: false}); - - // Emit the result - const tsOutputPath = path.join(wrapOutputDir, `${version}.ts`); - fs.mkdirSync(path.dirname(tsOutputPath), { recursive: true }); - os.writeFileSync( - tsOutputPath, - `/* eslint-disable @typescript-eslint/naming-convention */\n${tsFile}` - ); - - const schemaOutputPath = path.join(wrapOutputDir, `${version}.schema.json`); - os.writeFileSync(schemaOutputPath, JSON.stringify(bundledSchema, null ,2)); - - // Add metadata for the root index.ts file to use - wrapModules.push({ - interface: wrapSchema.id, - version: version, - abiVersion: version, - }); - } - - const renderTemplate = (name: string, context: unknown) => { - const tsTemplate = fs.readFileSync( - path.join(__dirname, `/templates/${name}-ts.mustache`), - { encoding: "utf-8" } - ); - - // Render the template - const tsSrc = Mustache.render(tsTemplate, context); - - // Emit the source - const tsOutputPath = path.join(wrapOutputDir, `${name}.ts`); - fs.mkdirSync(path.dirname(tsOutputPath), { recursive: true }); - os.writeFileSync(tsOutputPath, tsSrc); - }; - - const lastItem = (arr: Array) => arr[arr.length - 1]; - const versionToTs = (version: string) => - version.replace(/\./g, "_").replace(/\-/g, "_"); - - const formats = wrapModules.map((module) => { - return { - type: module.interface, - version: module.version, - tsVersion: versionToTs(module.version), - abiVersion: module.abiVersion, - abiTsVersion: versionToTs(module.abiVersion), - }; - }); - const latest = lastItem(formats); - - // Generate an index.ts file that exports root types that aggregate all versions - const indexContext = { - formats, - latest, - }; - - renderTemplate("index", indexContext); - - // Generate a migrate.ts file that exports a migration function from all version to the latest version - const migrateContext = { - prevFormats: [...formats], - latest: latest, - }; - migrateContext.prevFormats.pop(); - - renderTemplate("migrate", migrateContext); - - // Generate a deserialize.ts file that exports a deserialization function for the latest format version - const serializeContext = { - type: migrateContext.latest.type, - }; - - renderTemplate("deserialize", serializeContext); - renderTemplate("serialize", serializeContext); - - // Generate a validate.ts file that validates the manifest against the JSON schema - const validateFormats = wrapModules.map((module) => { - return { - type: module.interface, - version: module.version, - tsVersion: versionToTs(module.version), - abiVersion: module.abiVersion, - abiTsVersion: versionToTs(module.abiVersion), - dir: formatTypeName, - }; - }); - - const validateContext = { - formats: validateFormats, - latest: lastItem(validateFormats), - validators: [] as string[], - }; - - // Extract all validators - for (let k = 0; k < wrapSchemas.length; ++k) { - const formatSchema = wrapSchemas[k]; - - const getValidator = (obj: Record) => { - if (typeof obj !== "object") { - return; - } - - if (obj.format && typeof obj.format === "string") { - if (validateContext.validators.indexOf(obj.format) === -1) { - validateContext.validators.push(obj.format); - } - } - - const keys = Object.keys(obj); - for (let j = 0; j < keys.length; ++j) { - getValidator(obj[keys[j]] as Record); - } - }; - - getValidator(formatSchema as Record); - } - - renderTemplate("validate", validateContext); - - return Promise.resolve(); -} - -wrapCodegen() - .then(() => { - process.exit(); - }) - .catch((err) => { - console.error(err); - process.abort(); - }); diff --git a/packages/js/manifests/wrap/scripts/templates/deserialize-ts.mustache b/packages/js/manifests/wrap/scripts/templates/deserialize-ts.mustache deleted file mode 100644 index 003f6b51b6..0000000000 --- a/packages/js/manifests/wrap/scripts/templates/deserialize-ts.mustache +++ /dev/null @@ -1,52 +0,0 @@ -/* eslint-disable */ -/** - * This file was automatically generated by scripts/manifest/deserialize-ts.mustache. - * DO NOT MODIFY IT BY HAND. Instead, modify scripts/manifest/deserialize-ts.mustache, - * and run ts-node ./scripts/generateWrapManifestTypes.ts to regenerate this file. - */ - -import { - WrapManifest, - AnyWrapManifest, - migrateWrapManifest, - validateWrapManifest, - latestWrapManifestVersion, -} from "."; -import { DeserializeManifestOptions } from "../../"; - -import { msgpackDecode } from "@polywrap/msgpack-js"; -import * as Semver from "semver"; - -export async function deserializeWrapManifest( - manifest: Uint8Array, - options?: DeserializeManifestOptions -): Promise { - let anyWrapManifest: AnyWrapManifest | undefined; - try { - anyWrapManifest = msgpackDecode(manifest, true) as AnyWrapManifest; - } catch (e) { - throw Error(`Unable to parse WrapManifest: ${`[${new Uint8Array(manifest).toString()}]`}`); - } - - if (!options || !options.noValidate) { - await validateWrapManifest(anyWrapManifest); - } - - const versionCompare = Semver.compare( - Semver.coerce(anyWrapManifest.version) || anyWrapManifest.version, - Semver.coerce(latestWrapManifestVersion) || latestWrapManifestVersion - ); - - if (versionCompare === -1) { - // Upgrade - return migrateWrapManifest(anyWrapManifest, latestWrapManifestVersion); - } else if (versionCompare === 1) { - // Downgrade - throw Error( - `Cannot downgrade WrapManifest version ${anyWrapManifest.version}, please upgrade your WRAP package.` - ); - } else { - // Latest - return anyWrapManifest as WrapManifest; - } -} diff --git a/packages/js/manifests/wrap/scripts/templates/index-ts.mustache b/packages/js/manifests/wrap/scripts/templates/index-ts.mustache deleted file mode 100644 index 3aa1fd9adc..0000000000 --- a/packages/js/manifests/wrap/scripts/templates/index-ts.mustache +++ /dev/null @@ -1,68 +0,0 @@ -/* eslint-disable */ -/** - * This file was automatically generated by scripts/manifest/index-ts.mustache. - * DO NOT MODIFY IT BY HAND. Instead, modify scripts/manifest/index-ts.mustache, - * and run node ./scripts/manifest/generateTypes.js to regenerate this file. - */ - -{{#formats}} -import { - WrapManifest as WrapManifest_{{tsVersion}}, - Abi as WrapAbi_{{tsVersion}}_{{abiTsVersion}} -} from "./{{version}}"; -{{/formats}} - -{{#latest}}export * from "./{{version}}";{{/latest}} - -{{#formats}} -import WrapManifestSchema_{{tsVersion}} from "./{{version}}.schema.json"; -{{/formats}} - -export { - {{#formats}} - WrapManifest_{{tsVersion}}, - WrapAbi_{{tsVersion}}_{{abiTsVersion}}, - WrapManifestSchema_{{tsVersion}} - {{/formats}} -}; - -export enum WrapManifestVersions { - // NOTE: Patch fix for backwards compatability - "v0.1.0" = "0.1.0", - {{#formats}} - "v{{version}}" = "{{version}}", - {{/formats}} -}; - -export enum WrapManifestAbiVersions { - {{#formats}} - "v{{version}}" = "{{abiVersion}}", - {{/formats}} -}; - -export enum WrapAbiVersions { - {{#formats}} - "v{{abiVersion}}" = "{{abiVersion}}", - {{/formats}} -}; - -export type AnyWrapManifest = -{{#formats}} - | WrapManifest_{{tsVersion}} -{{/formats}}; - -export type AnyWrapAbi = -{{#formats}} - | WrapAbi_{{tsVersion}}_{{abiTsVersion}} -{{/formats}}; - -{{#latest}}export type WrapManifest = WrapManifest_{{tsVersion}}{{/latest}}; -{{#latest}}export type WrapAbi = WrapAbi_{{tsVersion}}_{{abiTsVersion}}{{/latest}}; - -{{#latest}}export const latestWrapManifestVersion = WrapManifestVersions["v{{version}}"]{{/latest}}; -{{#latest}}export const latestWrapAbiVersion = "{{abiVersion}}"{{/latest}}; - -export { migrateWrapManifest } from "./migrate"; -export { deserializeWrapManifest } from "./deserialize"; -export { serializeWrapManifest } from "./serialize"; -export { validateWrapManifest } from "./validate"; \ No newline at end of file diff --git a/packages/js/manifests/wrap/scripts/templates/migrate-ts.mustache b/packages/js/manifests/wrap/scripts/templates/migrate-ts.mustache deleted file mode 100644 index 7ff2ac58cb..0000000000 --- a/packages/js/manifests/wrap/scripts/templates/migrate-ts.mustache +++ /dev/null @@ -1,57 +0,0 @@ -/* eslint-disable */ -/** - * This file was automatically generated by scripts/manifest/migrate-ts.mustache. - * DO NOT MODIFY IT BY HAND. Instead, modify scripts/manifest/migrate-ts.mustache, - * and run node ./scripts/manifest/generateFormatTypes.js to regenerate this file. - */ -import { - AnyWrapManifest, - WrapManifest, - WrapManifestVersions, - latestWrapManifestVersion -} from "."; - -{{#prevFormats}} -import { - migrate as migrate_{{tsVersion}}_to_{{#latest}}{{tsVersion}}{{/latest}} -} from "./migrators/{{version}}_to_{{#latest}}{{version}}{{/latest}}"; -{{/prevFormats}} - -type Migrator = { - [key in WrapManifestVersions]?: (m: AnyWrapManifest) => WrapManifest; -}; - -export const migrators: Migrator = { -{{#prevFormats}} - "{{version}}": migrate_{{tsVersion}}_to_{{#latest}}{{tsVersion}}{{/latest}}, -{{/prevFormats}} -}; - -export function migrateWrapManifest( - manifest: AnyWrapManifest, - to: WrapManifestVersions -): WrapManifest { - const from = manifest.version as WrapManifestVersions; - - if (from === latestWrapManifestVersion) { - return manifest as WrapManifest; - } - - if (!(from in WrapManifestVersions)) { - throw new Error(`Unrecognized WrapManifestVersion "${manifest.version}"`); - } - -{{#prevFormats.length}} - const migrator = migrators[from]; - if (!migrator) { - throw new Error( - `Migrator from WrapManifestVersion "${from}" to "${to}" is not available` - ); - } - - return migrator(manifest); -{{/prevFormats.length}} -{{^prevFormats.length}} - throw new Error(`This should never happen, WrapManifest migrators is empty. from: ${from}, to: ${to}`); -{{/prevFormats.length}} -} diff --git a/packages/js/manifests/wrap/scripts/templates/serialize-ts.mustache b/packages/js/manifests/wrap/scripts/templates/serialize-ts.mustache deleted file mode 100644 index ba50dd48a4..0000000000 --- a/packages/js/manifests/wrap/scripts/templates/serialize-ts.mustache +++ /dev/null @@ -1,18 +0,0 @@ -import { - AnyWrapManifest, - validateWrapManifest -} from "."; -import { SerializeManifestOptions } from "../../"; - -import { msgpackEncode } from "@polywrap/msgpack-js"; - -export async function serializeWrapManifest( - manifest: AnyWrapManifest, - options?: SerializeManifestOptions -): Promise { - if (!options || !options.noValidate) { - await validateWrapManifest(manifest); - } - - return msgpackEncode(manifest, true); -} diff --git a/packages/js/manifests/wrap/scripts/templates/validate-ts.mustache b/packages/js/manifests/wrap/scripts/templates/validate-ts.mustache deleted file mode 100644 index 96ca2aff02..0000000000 --- a/packages/js/manifests/wrap/scripts/templates/validate-ts.mustache +++ /dev/null @@ -1,88 +0,0 @@ -/* eslint-disable */ -/** - * This file was automatically generated by scripts/manifest/validate-ts.mustache. - * DO NOT MODIFY IT BY HAND. Instead, modify scripts/manifest/validate-ts.mustache, - * and run node ./scripts/manifest/generateFormatTypes.js to regenerate this file. - */ -import { - AnyWrapManifest, - WrapManifestVersions, - {{#formats}} - WrapManifestSchema_{{tsVersion}} - {{/formats}} -} from "."; -{{#validators.length}}import * as Validators from "../validators";{{/validators.length}} - -import { - Schema, - Validator, - ValidationError, - ValidatorResult -} from "jsonschema"; -import { resolve, $Refs } from "@apidevtools/json-schema-ref-parser"; -// Workaround: https://github.com/APIDevTools/json-schema-ref-parser/issues/139#issuecomment-940500698 -import $RefParser from '@apidevtools/json-schema-ref-parser'; -$RefParser.resolve = $RefParser.resolve.bind($RefParser); - -type WrapManifestSchemas = { - [key in WrapManifestVersions]: Schema | undefined -}; - -const schemas: WrapManifestSchemas = { - // NOTE: Patch fix for backwards compatability - "0.1.0": WrapManifestSchema_0_1, - {{#formats}} - "{{version}}": WrapManifestSchema_{{tsVersion}}, - {{/formats}} -}; - -{{#validators}} -Validator.prototype.{{.}} = Validators.{{.}}; -{{/validators}} - -function throwIfErrors(result: ValidatorResult, version: string) { - if (result.errors.length) { - throw new Error([ - `Validation errors encountered while sanitizing WrapManifest version ${version}`, - ...result.errors.map((error: ValidationError) => error.toString()) - ].join("\n")); - } -} - -export async function validateWrapManifest( - manifest: AnyWrapManifest, - extSchema: Schema | undefined = undefined -): Promise { - const schema = schemas[manifest.version as WrapManifestVersions]; - - if (!schema) { - throw new Error(`Unrecognized WrapManifest schema version "${manifest.version}"\nmanifest: ${JSON.stringify(manifest, null, 2)}`); - } - - const refs: $Refs = await resolve(schema as any); - - const validator = new Validator(); - validator.addSchema(schema); - - const resolveRefs = () => { - const unresolvedRef = validator.unresolvedRefs.shift(); - if (!unresolvedRef) return; - - const relRefIdx = unresolvedRef.indexOf("#"); - const relRef = unresolvedRef.slice(relRefIdx); - - const resolvedSchema = refs.get(relRef); - if (!resolvedSchema) throw new Error(`Failed to resolve the ref: ${relRef}`); - validator.addSchema(resolvedSchema as Schema, unresolvedRef); - - resolveRefs(); - } - - resolveRefs(); - - throwIfErrors(validator.validate(manifest, schema), manifest.version); - - if (extSchema) { - throwIfErrors(validator.validate(manifest, extSchema), manifest.version); - } -} diff --git a/packages/js/manifests/wrap/src/__tests__/WrapManifest.spec.ts b/packages/js/manifests/wrap/src/__tests__/WrapManifest.spec.ts deleted file mode 100644 index 4c2628db7f..0000000000 --- a/packages/js/manifests/wrap/src/__tests__/WrapManifest.spec.ts +++ /dev/null @@ -1,139 +0,0 @@ -import { WrapManifest, deserializeWrapManifest } from ".."; -import { msgpackEncode } from "@polywrap/msgpack-js"; - -const testManifest: WrapManifest = { - abi: { - objectTypes: [ - { - type: "SampleResult", - kind: 1, - properties: [ - { - type: "String", - name: "value", - required: true, - kind: 34, - scalar: { - type: "String", - name: "value", - required: true, - kind: 4, - }, - }, - ], - interfaces: [], - }, - ], - enumTypes: [], - interfaceTypes: [], - importedObjectTypes: [], - importedModuleTypes: [], - importedEnumTypes: [], - importedEnvTypes: [], - moduleType: { - type: "Module", - kind: 128, - methods: [ - { - type: "Method", - name: "sampleMethod", - required: true, - kind: 64, - arguments: [ - { - type: "String", - name: "arg", - required: true, - kind: 34, - scalar: { - type: "String", - name: "arg", - required: true, - kind: 4, - }, - }, - ], - return: { - type: "SampleResult", - name: "sampleMethod", - required: true, - kind: 34, - object: { - type: "SampleResult", - name: "sampleMethod", - required: true, - kind: 8192, - }, - }, - }, - ], - imports: [], - interfaces: [], - }, - }, - name: "template-wasm-as", - type: "wasm", - version: "0.1.0", -}; - -describe("Polywrap Manifest Validation", () => { - it("Should succeed", async () => { - const manifest = msgpackEncode(testManifest, true); - expect(await deserializeWrapManifest(manifest)).toMatchObject(testManifest); - }); - - it("Should throw incorrect version format error", async () => { - const manifest = msgpackEncode({ - ...testManifest, - version: "bad-str", - }, true); - - await expect(() => deserializeWrapManifest(manifest)).rejects.toThrow( - /Unrecognized WrapManifest schema version/ - ); - }); - - it("Should throw not accepted field error", async () => { - const manifest = msgpackEncode({ - ...testManifest, - not_accepted_field: "not_accepted_field", - }, true); - - await expect(() => deserializeWrapManifest(manifest)).rejects.toThrow( - /not allowed to have the additional property "not_accepted_field"/ - ); - }); - - it("Should throw required field missing error", async () => { - const manifest = msgpackEncode({ - ...testManifest, - name: undefined, - }, true); - - await expect(() => deserializeWrapManifest(manifest)).rejects.toThrow( - /instance requires property "name"/ - ); - }); - - it("Should throw if name field incorrect patterh", async () => { - const manifest = msgpackEncode({ - ...testManifest, - name: "foo bar baz $%##$@#$@#$@#$#$", - }, true); - - await expect(() => deserializeWrapManifest(manifest)).rejects.toThrow( - /instance.name does not match pattern/ - ); - }); - - it("Should throw wrong type error", async () => { - const manifest = msgpackEncode({ - ...testManifest, - abi: true, - }, true); - - await expect(() => deserializeWrapManifest(manifest)).rejects.toThrow( - /instance.abi is not of a type\(s\) object/ - ); - }); -}); diff --git a/packages/js/manifests/wrap/src/compareSignature.ts b/packages/js/manifests/wrap/src/compareSignature.ts deleted file mode 100644 index d9a9550617..0000000000 --- a/packages/js/manifests/wrap/src/compareSignature.ts +++ /dev/null @@ -1,25 +0,0 @@ -import { - MethodDefinition, PropertyDefinition, -} from "."; - -export default ( - importedMethod: MethodDefinition, - expectedMethod: MethodDefinition -): boolean => { - if (expectedMethod.name === importedMethod.name) { - return false - } - - if (expectedMethod.arguments) { - const expectedArgs = expectedMethod.arguments.some(({type, name}, index) => { - const importedArgs = importedMethod.arguments as PropertyDefinition[] - const { name: importedName, type: importedType } = importedArgs[index] - return importedName === name && importedType === type - }) - - if (!expectedArgs) { - return false - } - } - return true -} diff --git a/packages/js/manifests/wrap/src/formats/index.ts b/packages/js/manifests/wrap/src/formats/index.ts deleted file mode 100644 index 2a999f615e..0000000000 --- a/packages/js/manifests/wrap/src/formats/index.ts +++ /dev/null @@ -1 +0,0 @@ -export * from "./wrap.info"; diff --git a/packages/js/manifests/wrap/src/formats/wrap.info/0.1.schema.json b/packages/js/manifests/wrap/src/formats/wrap.info/0.1.schema.json deleted file mode 100644 index 1c457327b0..0000000000 --- a/packages/js/manifests/wrap/src/formats/wrap.info/0.1.schema.json +++ /dev/null @@ -1,626 +0,0 @@ -{ - "id": "WrapManifest", - "type": "object", - "additionalProperties": false, - "required": [ - "version", - "name", - "type", - "abi" - ], - "properties": { - "version": { - "description": "WRAP Standard Version", - "type": "string", - "enum": [ - "0.1.0", - "0.1" - ] - }, - "type": { - "description": "Wrapper Package Type", - "type": "string", - "enum": [ - "wasm", - "interface", - "plugin" - ] - }, - "name": { - "description": "Wrapper Name", - "type": "string", - "pattern": "^[a-zA-Z0-9\\-\\_]+$" - }, - "abi": { - "description": "Information of modules", - "id": "Abi", - "type": "object", - "unevaluatedProperties": false, - "properties": { - "version": { - "description": "ABI Version", - "type": "string", - "const": "0.1" - }, - "objectTypes": { - "type": "array", - "items": { - "$ref": "#/properties/abi/definitions/objectDefinition" - } - }, - "moduleType": { - "$ref": "#/properties/abi/definitions/moduleDefinition" - }, - "enumTypes": { - "type": "array", - "items": { - "$ref": "#/properties/abi/definitions/enumDefinition" - } - }, - "interfaceTypes": { - "type": "array", - "items": { - "$ref": "#/properties/abi/definitions/interfaceDefinition" - } - }, - "importedObjectTypes": { - "type": "array", - "items": { - "$ref": "#/properties/abi/definitions/importedObjectDefinition" - } - }, - "importedModuleTypes": { - "type": "array", - "items": { - "$ref": "#/properties/abi/definitions/importedModuleDefinition" - } - }, - "importedEnumTypes": { - "type": "array", - "items": { - "$ref": "#/properties/abi/definitions/importedEnumDefinition" - } - }, - "importedEnvTypes": { - "type": "array", - "items": { - "$ref": "#/properties/abi/definitions/importedEnvDefinition" - } - }, - "envType": { - "$ref": "#/properties/abi/definitions/envDefinition" - } - }, - "definitions": { - "objectDefinition": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/genericDefinition" - }, - { - "$ref": "#/properties/abi/definitions/withComment" - }, - { - "properties": { - "properties": { - "type": "array", - "items": { - "$ref": "#/properties/abi/definitions/propertyDefinition" - } - }, - "interfaces": { - "type": "array", - "items": { - "$ref": "#/properties/abi/definitions/interfaceImplementedDefinition" - } - } - }, - "unevaluatedProperties": false - } - ], - "unevaluatedProperties": false - }, - "moduleDefinition": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/genericDefinition" - }, - { - "$ref": "#/properties/abi/definitions/withComment" - }, - { - "properties": { - "methods": { - "type": "array", - "items": { - "$ref": "#/properties/abi/definitions/methodDefinition" - } - }, - "imports": { - "type": "array", - "items": { - "$ref": "#/properties/abi/definitions/importedModuleRef" - } - }, - "interfaces": { - "type": "array", - "items": { - "$ref": "#/properties/abi/definitions/interfaceImplementedDefinition" - } - } - }, - "unevaluatedProperties": false - } - ], - "unevaluatedProperties": false - }, - "interfaceImplementedDefinition": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/genericDefinition" - } - ], - "unevaluatedProperties": false - }, - "methodDefinition": { - "type": "object", - "required": [ - "return" - ], - "allOf": [ - { - "$ref": "#/properties/abi/definitions/genericDefinition" - }, - { - "$ref": "#/properties/abi/definitions/withComment" - }, - { - "properties": { - "arguments": { - "type": "array", - "items": { - "$ref": "#/properties/abi/definitions/propertyDefinition" - } - }, - "env": { - "type": "object", - "properties": { - "required": { - "type": "boolean" - } - }, - "unevaluatedProperties": false - }, - "return": { - "$ref": "#/properties/abi/definitions/propertyDefinition" - } - }, - "unevaluatedProperties": false - } - ], - "unevaluatedProperties": false - }, - "envDefinition": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/objectDefinition" - } - ] - }, - "enumDefinition": { - "type": "object", - "required": [ - "constants" - ], - "allOf": [ - { - "$ref": "#/properties/abi/definitions/genericDefinition" - }, - { - "$ref": "#/properties/abi/definitions/withComment" - }, - { - "properties": { - "constants": { - "type": "array", - "items": { - "type": "string" - } - } - }, - "unevaluatedProperties": false - } - ], - "unevaluatedProperties": false - }, - "interfaceDefinition": { - "type": "object", - "required": [ - "capabilities" - ], - "allOf": [ - { - "$ref": "#/properties/abi/definitions/genericDefinition" - }, - { - "$ref": "#/properties/abi/definitions/importedDefinition" - }, - { - "properties": { - "capabilities": { - "$ref": "#/properties/abi/definitions/capabilityDefinition" - } - }, - "unevaluatedProperties": false - } - ], - "unevaluatedProperties": false - }, - "capabilityDefinition": { - "type": "object", - "properties": { - "getImplementations": { - "type": "object", - "required": [ - "enabled" - ], - "properties": { - "enabled": { - "type": "boolean" - } - }, - "unevaluatedProperties": false - } - }, - "unevaluatedProperties": false - }, - "importedDefinition": { - "type": "object", - "required": [ - "uri", - "namespace", - "nativeType" - ], - "properties": { - "uri": { - "type": "string" - }, - "namespace": { - "type": "string" - }, - "nativeType": { - "type": "string" - } - }, - "unevaluatedProperties": false - }, - "importedObjectDefinition": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/objectDefinition" - }, - { - "$ref": "#/properties/abi/definitions/importedDefinition" - }, - { - "$ref": "#/properties/abi/definitions/withComment" - } - ], - "unevaluatedProperties": false - }, - "importedModuleDefinition": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/genericDefinition" - }, - { - "$ref": "#/properties/abi/definitions/importedDefinition" - }, - { - "$ref": "#/properties/abi/definitions/withComment" - }, - { - "properties": { - "methods": { - "type": "array", - "items": { - "$ref": "#/properties/abi/definitions/methodDefinition" - } - }, - "isInterface": { - "type": [ - "boolean" - ] - } - }, - "unevaluatedProperties": false - } - ], - "unevaluatedProperties": false - }, - "importedEnumDefinition": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/enumDefinition" - }, - { - "$ref": "#/properties/abi/definitions/importedDefinition" - } - ], - "unevaluatedProperties": false - }, - "importedEnvDefinition": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/importedObjectDefinition" - } - ], - "unevaluatedProperties": false - }, - "withKind": { - "type": "object", - "properties": { - "kind": { - "type": "number" - } - }, - "unevaluatedProperties": false, - "required": [ - "kind" - ] - }, - "withComment": { - "type": "object", - "properties": { - "comment": { - "type": "string" - } - }, - "unevaluatedProperties": false - }, - "propertyDefinition": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/withComment" - }, - { - "$ref": "#/properties/abi/definitions/anyDefinition" - } - ], - "unevaluatedProperties": false - }, - "genericDefinition": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/withKind" - }, - { - "required": [ - "type" - ], - "properties": { - "type": { - "type": "string" - }, - "name": { - "type": [ - "string" - ] - }, - "required": { - "type": [ - "boolean" - ] - } - }, - "unevaluatedProperties": false - } - ], - "unevaluatedProperties": false - }, - "anyDefinition": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/genericDefinition" - }, - { - "properties": { - "array": { - "$ref": "#/properties/abi/definitions/arrayDefinition" - }, - "scalar": { - "$ref": "#/properties/abi/definitions/scalarDefinition" - }, - "map": { - "$ref": "#/properties/abi/definitions/mapDefinition" - }, - "object": { - "$ref": "#/properties/abi/definitions/objectRef" - }, - "enum": { - "allOf": [ - { - "$ref": "#/properties/abi/definitions/enumRef" - } - ], - "required": [ - "type" - ] - }, - "unresolvedObjectOrEnum": { - "$ref": "#/properties/abi/definitions/unresolvedObjectOrEnumRef" - } - }, - "unevaluatedProperties": false - } - ], - "unevaluatedProperties": false - }, - "arrayDefinition": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/anyDefinition" - }, - { - "properties": { - "item": { - "$ref": "#/properties/abi/definitions/genericDefinition" - } - }, - "unevaluatedProperties": false - } - ], - "unevaluatedProperties": false, - "required": [ - "item" - ] - }, - "scalarType": { - "type": "string", - "enum": [ - "UInt", - "UInt8", - "UInt16", - "UInt32", - "Int", - "Int8", - "Int16", - "Int32", - "String", - "Boolean", - "Bytes", - "BigInt", - "BigNumber", - "JSON" - ] - }, - "scalarDefinition": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/genericDefinition" - } - ], - "properties": { - "type": { - "$ref": "#/properties/abi/definitions/scalarType" - } - }, - "unevaluatedProperties": false, - "required": [ - "type" - ] - }, - "mapKeyType": { - "type": "string", - "enum": [ - "UInt", - "UInt8", - "UInt16", - "UInt32", - "Int", - "Int8", - "Int16", - "Int32", - "String" - ] - }, - "mapKeyDefinition": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/anyDefinition" - }, - { - "properties": { - "type": { - "$ref": "#/properties/abi/definitions/mapKeyType" - } - }, - "unevaluatedProperties": false - } - ], - "unevaluatedProperties": false, - "required": [ - "type" - ] - }, - "mapDefinition": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/anyDefinition" - }, - { - "$ref": "#/properties/abi/definitions/withComment" - }, - { - "properties": { - "key": { - "$ref": "#/properties/abi/definitions/mapKeyDefinition" - }, - "value": { - "$ref": "#/properties/abi/definitions/genericDefinition" - } - }, - "unevaluatedProperties": false - } - ], - "unevaluatedProperties": false, - "required": [ - "key", - "value" - ] - }, - "objectRef": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/genericDefinition" - } - ], - "unevaluatedProperties": false - }, - "enumRef": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/genericDefinition" - } - ], - "unevaluatedProperties": false - }, - "unresolvedObjectOrEnumRef": { - "type": "object", - "allOf": [ - { - "$ref": "#/properties/abi/definitions/genericDefinition" - } - ], - "unevaluatedProperties": false - }, - "importedModuleRef": { - "type": "object", - "properties": { - "type": { - "type": "string" - } - }, - "unevaluatedProperties": false - } - } - } - } -} \ No newline at end of file diff --git a/packages/js/manifests/wrap/src/formats/wrap.info/0.1.ts b/packages/js/manifests/wrap/src/formats/wrap.info/0.1.ts deleted file mode 100644 index 6c22a48547..0000000000 --- a/packages/js/manifests/wrap/src/formats/wrap.info/0.1.ts +++ /dev/null @@ -1,144 +0,0 @@ -/* eslint-disable @typescript-eslint/naming-convention */ -/* tslint:disable */ -/** - * This file was automatically generated by json-schema-to-typescript. - * DO NOT MODIFY IT BY HAND. Instead, modify the source JSONSchema file, - * and run json-schema-to-typescript to regenerate this file. - */ - -export type ObjectDefinition = GenericDefinition & - WithComment & { - properties?: PropertyDefinition[]; - interfaces?: InterfaceImplementedDefinition[]; - }; -export type GenericDefinition = WithKind & { - type: string; - name?: string; - required?: boolean; -}; -export type PropertyDefinition = WithComment & AnyDefinition; -export type AnyDefinition = GenericDefinition & { - array?: ArrayDefinition; - scalar?: ScalarDefinition; - map?: MapDefinition; - object?: ObjectRef; - enum?: EnumRef; - unresolvedObjectOrEnum?: UnresolvedObjectOrEnumRef; -}; -export type ArrayDefinition = AnyDefinition & { - item?: GenericDefinition; -}; -export type ScalarDefinition = GenericDefinition & { - type: - | "UInt" - | "UInt8" - | "UInt16" - | "UInt32" - | "Int" - | "Int8" - | "Int16" - | "Int32" - | "String" - | "Boolean" - | "Bytes" - | "BigInt" - | "BigNumber" - | "JSON"; -}; -export type MapDefinition = AnyDefinition & - WithComment & { - key?: MapKeyDefinition; - value?: GenericDefinition; - }; -export type MapKeyDefinition = AnyDefinition & { - type?: "UInt" | "UInt8" | "UInt16" | "UInt32" | "Int" | "Int8" | "Int16" | "Int32" | "String"; -}; -export type ObjectRef = GenericDefinition; -export type EnumRef = GenericDefinition; -export type UnresolvedObjectOrEnumRef = GenericDefinition; -export type InterfaceImplementedDefinition = GenericDefinition; -export type ModuleDefinition = GenericDefinition & - WithComment & { - methods?: MethodDefinition[]; - imports?: ImportedModuleRef[]; - interfaces?: InterfaceImplementedDefinition[]; - }; -export type MethodDefinition = GenericDefinition & - WithComment & { - arguments?: PropertyDefinition[]; - env?: { - required?: boolean; - }; - return?: PropertyDefinition; - }; -export type EnumDefinition = GenericDefinition & - WithComment & { - constants?: string[]; - }; -export type InterfaceDefinition = GenericDefinition & - ImportedDefinition & { - capabilities?: CapabilityDefinition; - }; -export type ImportedObjectDefinition = ObjectDefinition & ImportedDefinition & WithComment; -export type ImportedModuleDefinition = GenericDefinition & - ImportedDefinition & - WithComment & { - methods?: MethodDefinition[]; - isInterface?: boolean; - }; -export type ImportedEnumDefinition = EnumDefinition & ImportedDefinition; -export type ImportedEnvDefinition = ImportedObjectDefinition; -export type EnvDefinition = ObjectDefinition; - -export interface WrapManifest { - /** - * WRAP Standard Version - */ - version: "0.1.0" | "0.1"; - /** - * Wrapper Package Type - */ - type: "wasm" | "interface" | "plugin"; - /** - * Wrapper Name - */ - name: string; - abi: Abi; -} -/** - * Information of modules - */ -export interface Abi { - /** - * ABI Version - */ - version?: "0.1"; - objectTypes?: ObjectDefinition[]; - moduleType?: ModuleDefinition; - enumTypes?: EnumDefinition[]; - interfaceTypes?: InterfaceDefinition[]; - importedObjectTypes?: ImportedObjectDefinition[]; - importedModuleTypes?: ImportedModuleDefinition[]; - importedEnumTypes?: ImportedEnumDefinition[]; - importedEnvTypes?: ImportedEnvDefinition[]; - envType?: EnvDefinition; -} -export interface WithKind { - kind: number; -} -export interface WithComment { - comment?: string; -} -export interface ImportedModuleRef { - type?: string; -} -export interface ImportedDefinition { - uri: string; - namespace: string; - nativeType: string; -} -export interface CapabilityDefinition { - getImplementations?: { - enabled: boolean; - }; -} diff --git a/packages/js/manifests/wrap/src/formats/wrap.info/deserialize.ts b/packages/js/manifests/wrap/src/formats/wrap.info/deserialize.ts deleted file mode 100644 index 003f6b51b6..0000000000 --- a/packages/js/manifests/wrap/src/formats/wrap.info/deserialize.ts +++ /dev/null @@ -1,52 +0,0 @@ -/* eslint-disable */ -/** - * This file was automatically generated by scripts/manifest/deserialize-ts.mustache. - * DO NOT MODIFY IT BY HAND. Instead, modify scripts/manifest/deserialize-ts.mustache, - * and run ts-node ./scripts/generateWrapManifestTypes.ts to regenerate this file. - */ - -import { - WrapManifest, - AnyWrapManifest, - migrateWrapManifest, - validateWrapManifest, - latestWrapManifestVersion, -} from "."; -import { DeserializeManifestOptions } from "../../"; - -import { msgpackDecode } from "@polywrap/msgpack-js"; -import * as Semver from "semver"; - -export async function deserializeWrapManifest( - manifest: Uint8Array, - options?: DeserializeManifestOptions -): Promise { - let anyWrapManifest: AnyWrapManifest | undefined; - try { - anyWrapManifest = msgpackDecode(manifest, true) as AnyWrapManifest; - } catch (e) { - throw Error(`Unable to parse WrapManifest: ${`[${new Uint8Array(manifest).toString()}]`}`); - } - - if (!options || !options.noValidate) { - await validateWrapManifest(anyWrapManifest); - } - - const versionCompare = Semver.compare( - Semver.coerce(anyWrapManifest.version) || anyWrapManifest.version, - Semver.coerce(latestWrapManifestVersion) || latestWrapManifestVersion - ); - - if (versionCompare === -1) { - // Upgrade - return migrateWrapManifest(anyWrapManifest, latestWrapManifestVersion); - } else if (versionCompare === 1) { - // Downgrade - throw Error( - `Cannot downgrade WrapManifest version ${anyWrapManifest.version}, please upgrade your WRAP package.` - ); - } else { - // Latest - return anyWrapManifest as WrapManifest; - } -} diff --git a/packages/js/manifests/wrap/src/formats/wrap.info/index.ts b/packages/js/manifests/wrap/src/formats/wrap.info/index.ts deleted file mode 100644 index 2151d613b2..0000000000 --- a/packages/js/manifests/wrap/src/formats/wrap.info/index.ts +++ /dev/null @@ -1,54 +0,0 @@ -/* eslint-disable */ -/** - * This file was automatically generated by scripts/manifest/index-ts.mustache. - * DO NOT MODIFY IT BY HAND. Instead, modify scripts/manifest/index-ts.mustache, - * and run node ./scripts/manifest/generateTypes.js to regenerate this file. - */ - -import { - WrapManifest as WrapManifest_0_1, - Abi as WrapAbi_0_1_0_1 -} from "./0.1"; - -export * from "./0.1"; - -import WrapManifestSchema_0_1 from "./0.1.schema.json"; - -export { - WrapManifest_0_1, - WrapAbi_0_1_0_1, - WrapManifestSchema_0_1 -}; - -export enum WrapManifestVersions { - // NOTE: Patch fix for backwards compatability - "v0.1.0" = "0.1.0", - "v0.1" = "0.1", -}; - -export enum WrapManifestAbiVersions { - "v0.1" = "0.1", -}; - -export enum WrapAbiVersions { - "v0.1" = "0.1", -}; - -export type AnyWrapManifest = - | WrapManifest_0_1 -; - -export type AnyWrapAbi = - | WrapAbi_0_1_0_1 -; - -export type WrapManifest = WrapManifest_0_1; -export type WrapAbi = WrapAbi_0_1_0_1; - -export const latestWrapManifestVersion = WrapManifestVersions["v0.1"]; -export const latestWrapAbiVersion = "0.1"; - -export { migrateWrapManifest } from "./migrate"; -export { deserializeWrapManifest } from "./deserialize"; -export { serializeWrapManifest } from "./serialize"; -export { validateWrapManifest } from "./validate"; \ No newline at end of file diff --git a/packages/js/manifests/wrap/src/formats/wrap.info/migrate.ts b/packages/js/manifests/wrap/src/formats/wrap.info/migrate.ts deleted file mode 100644 index 9cdb713beb..0000000000 --- a/packages/js/manifests/wrap/src/formats/wrap.info/migrate.ts +++ /dev/null @@ -1,37 +0,0 @@ -/* eslint-disable */ -/** - * This file was automatically generated by scripts/manifest/migrate-ts.mustache. - * DO NOT MODIFY IT BY HAND. Instead, modify scripts/manifest/migrate-ts.mustache, - * and run node ./scripts/manifest/generateFormatTypes.js to regenerate this file. - */ -import { - AnyWrapManifest, - WrapManifest, - WrapManifestVersions, - latestWrapManifestVersion -} from "."; - - -type Migrator = { - [key in WrapManifestVersions]?: (m: AnyWrapManifest) => WrapManifest; -}; - -export const migrators: Migrator = { -}; - -export function migrateWrapManifest( - manifest: AnyWrapManifest, - to: WrapManifestVersions -): WrapManifest { - const from = manifest.version as WrapManifestVersions; - - if (from === latestWrapManifestVersion) { - return manifest as WrapManifest; - } - - if (!(from in WrapManifestVersions)) { - throw new Error(`Unrecognized WrapManifestVersion "${manifest.version}"`); - } - - throw new Error(`This should never happen, WrapManifest migrators is empty. from: ${from}, to: ${to}`); -} diff --git a/packages/js/manifests/wrap/src/formats/wrap.info/serialize.ts b/packages/js/manifests/wrap/src/formats/wrap.info/serialize.ts deleted file mode 100644 index ba50dd48a4..0000000000 --- a/packages/js/manifests/wrap/src/formats/wrap.info/serialize.ts +++ /dev/null @@ -1,18 +0,0 @@ -import { - AnyWrapManifest, - validateWrapManifest -} from "."; -import { SerializeManifestOptions } from "../../"; - -import { msgpackEncode } from "@polywrap/msgpack-js"; - -export async function serializeWrapManifest( - manifest: AnyWrapManifest, - options?: SerializeManifestOptions -): Promise { - if (!options || !options.noValidate) { - await validateWrapManifest(manifest); - } - - return msgpackEncode(manifest, true); -} diff --git a/packages/js/manifests/wrap/src/formats/wrap.info/validate.ts b/packages/js/manifests/wrap/src/formats/wrap.info/validate.ts deleted file mode 100644 index 38e675ed56..0000000000 --- a/packages/js/manifests/wrap/src/formats/wrap.info/validate.ts +++ /dev/null @@ -1,81 +0,0 @@ -/* eslint-disable */ -/** - * This file was automatically generated by scripts/manifest/validate-ts.mustache. - * DO NOT MODIFY IT BY HAND. Instead, modify scripts/manifest/validate-ts.mustache, - * and run node ./scripts/manifest/generateFormatTypes.js to regenerate this file. - */ -import { - AnyWrapManifest, - WrapManifestVersions, - WrapManifestSchema_0_1 -} from "."; - - -import { - Schema, - Validator, - ValidationError, - ValidatorResult -} from "jsonschema"; -import { resolve, $Refs } from "@apidevtools/json-schema-ref-parser"; -// Workaround: https://github.com/APIDevTools/json-schema-ref-parser/issues/139#issuecomment-940500698 -import $RefParser from '@apidevtools/json-schema-ref-parser'; -$RefParser.resolve = $RefParser.resolve.bind($RefParser); - -type WrapManifestSchemas = { - [key in WrapManifestVersions]: Schema | undefined -}; - -const schemas: WrapManifestSchemas = { - // NOTE: Patch fix for backwards compatability - "0.1.0": WrapManifestSchema_0_1, - "0.1": WrapManifestSchema_0_1, -}; - - -function throwIfErrors(result: ValidatorResult, version: string) { - if (result.errors.length) { - throw new Error([ - `Validation errors encountered while sanitizing WrapManifest version ${version}`, - ...result.errors.map((error: ValidationError) => error.toString()) - ].join("\n")); - } -} - -export async function validateWrapManifest( - manifest: AnyWrapManifest, - extSchema: Schema | undefined = undefined -): Promise { - const schema = schemas[manifest.version as WrapManifestVersions]; - - if (!schema) { - throw new Error(`Unrecognized WrapManifest schema version "${manifest.version}"\nmanifest: ${JSON.stringify(manifest, null, 2)}`); - } - - const refs: $Refs = await resolve(schema as any); - - const validator = new Validator(); - validator.addSchema(schema); - - const resolveRefs = () => { - const unresolvedRef = validator.unresolvedRefs.shift(); - if (!unresolvedRef) return; - - const relRefIdx = unresolvedRef.indexOf("#"); - const relRef = unresolvedRef.slice(relRefIdx); - - const resolvedSchema = refs.get(relRef); - if (!resolvedSchema) throw new Error(`Failed to resolve the ref: ${relRef}`); - validator.addSchema(resolvedSchema as Schema, unresolvedRef); - - resolveRefs(); - } - - resolveRefs(); - - throwIfErrors(validator.validate(manifest, schema), manifest.version); - - if (extSchema) { - throwIfErrors(validator.validate(manifest, extSchema), manifest.version); - } -} diff --git a/packages/js/manifests/wrap/src/index.ts b/packages/js/manifests/wrap/src/index.ts deleted file mode 100644 index 488e650484..0000000000 --- a/packages/js/manifests/wrap/src/index.ts +++ /dev/null @@ -1,3 +0,0 @@ -export * from "./formats"; -export * from "./types"; -export { default as compareSignature } from "./compareSignature" \ No newline at end of file diff --git a/packages/js/manifests/wrap/src/types.ts b/packages/js/manifests/wrap/src/types.ts deleted file mode 100644 index 2a2366e0fe..0000000000 --- a/packages/js/manifests/wrap/src/types.ts +++ /dev/null @@ -1,7 +0,0 @@ -export interface DeserializeManifestOptions { - noValidate?: boolean; -} - -export interface SerializeManifestOptions { - noValidate?: boolean; -} diff --git a/packages/js/manifests/wrap/tsconfig.build.json b/packages/js/manifests/wrap/tsconfig.build.json deleted file mode 100644 index 9708b5768a..0000000000 --- a/packages/js/manifests/wrap/tsconfig.build.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "extends": "./tsconfig.json", - "include": [ - "./src/**/*.ts" - ], - "exclude": [ - "./src/**/__tests__" - ] -} \ No newline at end of file diff --git a/packages/js/manifests/wrap/tsconfig.json b/packages/js/manifests/wrap/tsconfig.json deleted file mode 100644 index 85d516ce30..0000000000 --- a/packages/js/manifests/wrap/tsconfig.json +++ /dev/null @@ -1,10 +0,0 @@ -{ - "extends": "../../../../tsconfig", - "compilerOptions": { - "outDir": "build" - }, - "include": [ - "./src/**/*.ts" - ], - "exclude": [] -} diff --git a/packages/js/msgpack/README.md b/packages/js/msgpack/README.md deleted file mode 100644 index 01dad04140..0000000000 --- a/packages/js/msgpack/README.md +++ /dev/null @@ -1,23 +0,0 @@ -# @polywrap/msgpack-js - -TypeScript / JavaScript implementation of the WRAP MsgPack encoding standard. - -## Usage - -```typescript -import { msgpackEncode, msgpackDecode } from "@polywrap/msgpack-js"; - -const test = { - foo: 5, - bar: [true, false], - baz: { - prop: "value" - } -}; - -const encoded: Uint8Array = msgpackEncode(test); - -const decoded = msgpackDecode(encoded); - -expect(decoded).toEqual(test); -``` diff --git a/packages/js/msgpack/jest.config.js b/packages/js/msgpack/jest.config.js deleted file mode 100644 index a5ca876a5a..0000000000 --- a/packages/js/msgpack/jest.config.js +++ /dev/null @@ -1,11 +0,0 @@ -module.exports = { - collectCoverage: true, - preset: 'ts-jest', - testEnvironment: 'node', - testMatch: ["**/?(*.)+(spec|test).[jt]s?(x)"], - globals: { - 'ts-jest': { - diagnostics: false - } - } -}; diff --git a/packages/js/msgpack/package.json b/packages/js/msgpack/package.json deleted file mode 100644 index c396fd8052..0000000000 --- a/packages/js/msgpack/package.json +++ /dev/null @@ -1,34 +0,0 @@ -{ - "name": "@polywrap/msgpack-js", - "description": "WRAP MsgPack Encoding", - "version": "0.10.0", - "license": "MIT", - "repository": { - "type": "git", - "url": "https://github.com/polywrap/monorepo.git" - }, - "main": "build/index.js", - "files": [ - "build" - ], - "scripts": { - "build": "rimraf ./build && tsc --project tsconfig.build.json", - "lint": "eslint --color -c ../../../.eslintrc.js --ignore-pattern src/__tests__/cases/* src/", - "test": "jest --passWithNoTests --runInBand --verbose", - "test:watch": "yarn test -- --watch" - }, - "dependencies": { - "@msgpack/msgpack": "2.7.2" - }, - "devDependencies": { - "@types/jest": "26.0.8", - "@types/prettier": "2.6.0", - "jest": "26.6.3", - "rimraf": "3.0.2", - "typescript": "4.9.5" - }, - "gitHead": "7346adaf5adb7e6bbb70d9247583e995650d390a", - "publishConfig": { - "access": "public" - } -} diff --git a/packages/js/msgpack/src/__tests__/msgpack.spec.ts b/packages/js/msgpack/src/__tests__/msgpack.spec.ts deleted file mode 100644 index e27bd09b8b..0000000000 --- a/packages/js/msgpack/src/__tests__/msgpack.spec.ts +++ /dev/null @@ -1,54 +0,0 @@ -import { msgpackEncode, msgpackDecode } from "../"; - -describe("msgpack", () => { - const expectedArrayLike = [ - 130, 168, 102, 105, 114, 115, 116, 75, - 101, 121, 170, 102, 105, 114, 115, 116, - 86, 97, 108, 117, 101, 169, 115, 101, - 99, 111, 110, 100, 75, 101, 121, 171, - 115, 101, 99, 111, 110, 100, 86, 97, - 108, 117, 101 - ] - it("Should encode and decode object", () => { - const customObject = { - "firstKey": "firstValue", - "secondKey": "secondValue", - } - const encoded = msgpackEncode(customObject) - expect(encoded).toEqual(Uint8Array.from(expectedArrayLike)) - const decoded = msgpackDecode(encoded) - expect(decoded).toEqual(customObject); - }); - - it("Should encode and decode map", () => { - const customMap = new Map() - customMap.set("firstKey", "firstValue") - customMap.set("secondKey", "secondValue") - - const encoded = msgpackEncode(customMap) - const decoded = msgpackDecode(encoded) - expect(decoded).toEqual(customMap); - }); - - it("Should encode and decode nested map", () => { - const customMap: Map> = new Map() - // @ts-ignore - customMap.set("firstKey", new Map([["one", "1"]])); - customMap.set("secondKey", new Map([["second", "2"]])); - - const encoded = msgpackEncode(customMap) - const decoded = msgpackDecode(encoded) - expect(decoded).toEqual(customMap); - }); - - it("Should encode and decode map of bytes", () => { - const customMap: Map = new Map() - customMap.set("firstKey", new Uint8Array([1, 2, 3])); - customMap.set("secondKey", new Uint8Array([3, 2, 1])); - - const encoded = msgpackEncode(customMap) - const decoded = msgpackDecode(encoded) - expect(decoded).toEqual(customMap); - }) - -}); diff --git a/packages/js/msgpack/src/index.ts b/packages/js/msgpack/src/index.ts deleted file mode 100644 index 40dda4b21a..0000000000 --- a/packages/js/msgpack/src/index.ts +++ /dev/null @@ -1,95 +0,0 @@ -import { Encoder, Decoder, ExtensionCodec } from "@msgpack/msgpack"; - -enum ExtensionTypes { - // must be in range 0-127 - GENERIC_MAP = 1, -} - -const extensionCodec = new ExtensionCodec(); - -// Generic Map: Map -extensionCodec.register({ - type: ExtensionTypes.GENERIC_MAP, - encode: (object: unknown): Uint8Array | null => { - if (object instanceof Map) { - const optimized: Record = {}; - for (const [key, value] of object) { - optimized[key] = value; - } - return msgpackEncode(optimized); - } else { - return null; - } - }, - decode: (data: Uint8Array) => { - const obj = msgpackDecode(data) as Record; - const map = new Map(); - - for (const [key, value] of Object.entries(obj)) { - map.set(key, value); - } - return map; - }, -}); - -const shouldIgnore = (obj: unknown) => - obj instanceof ArrayBuffer || ArrayBuffer.isView(obj) || obj instanceof Map; - -function sanitize(obj: Record): Record { - if (shouldIgnore(obj)) { - return obj; - } - - for (const key of Object.keys(obj)) { - if (typeof obj[key] === "function") { - delete obj[key]; - } else if (obj[key] === null || obj[key] === undefined) { - delete obj[key]; - } else if (typeof obj[key] === "object") { - const sanitized = sanitize(obj[key] as Record); - if (Array.isArray(obj[key])) { - obj[key] = Object.values(sanitized); - } else { - obj[key] = sanitized; - } - } - } - return obj; -} - -export function msgpackEncode( - object: unknown, - sanitizeObj = false -): Uint8Array { - const encoder = new Encoder( - extensionCodec, - undefined, // context - undefined, // maxDepth - undefined, // initialBufferSize - undefined, // sortKeys - undefined, // forceFloat32 - true, // ignoreUndefined - undefined // forceIntegerToFloat - ); - - if (sanitizeObj && typeof object === "object" && !shouldIgnore(object)) { - const deepClone = JSON.parse(JSON.stringify(object)); - object = sanitize(deepClone); - } - - return encoder.encode(object); -} - -export function msgpackDecode( - buffer: ArrayLike | BufferSource, - sanitizeResult = false -): unknown { - const decoder = new Decoder(extensionCodec); - const result = decoder.decode(buffer); - - if (sanitizeResult && typeof result === "object" && !shouldIgnore(result)) { - return sanitize(result as Record); - } else { - return result; - } -} diff --git a/packages/js/msgpack/tsconfig.build.json b/packages/js/msgpack/tsconfig.build.json deleted file mode 100644 index 77aadfdd2f..0000000000 --- a/packages/js/msgpack/tsconfig.build.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "extends": "./tsconfig.json", - "include": [ - "./src/**/*.ts" - ], - "exclude": [ - "./src/**/__tests__" - ] -} diff --git a/packages/js/msgpack/tsconfig.json b/packages/js/msgpack/tsconfig.json deleted file mode 100644 index 920efc3c9d..0000000000 --- a/packages/js/msgpack/tsconfig.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "extends": "../../../tsconfig", - "compilerOptions": { - "lib": [ - "es2020", - "es2015", - "es5", - "dom" - ], - "outDir": "build" - }, - "include": [ - "./src/**/*.ts" - ], - "exclude": [ - "./src/__tests__/cases/*.ts" - ] -} diff --git a/packages/js/plugin/README.md b/packages/js/plugin/README.md deleted file mode 100644 index 238e9df99b..0000000000 --- a/packages/js/plugin/README.md +++ /dev/null @@ -1,5 +0,0 @@ -# @polywrap/plugin-js - -## Description - -Helpers to improve plugin wrapper development experience. diff --git a/packages/js/plugin/jest.config.js b/packages/js/plugin/jest.config.js deleted file mode 100644 index b156259895..0000000000 --- a/packages/js/plugin/jest.config.js +++ /dev/null @@ -1,12 +0,0 @@ -module.exports = { - collectCoverage: true, - preset: 'ts-jest', - testEnvironment: 'node', - testMatch: ["**/?(*.)+(spec|test).[jt]s?(x)"], - modulePathIgnorePatterns: ['./src/__tests__/apis'], - globals: { - 'ts-jest': { - diagnostics: false - } - } -}; diff --git a/packages/js/plugin/package.json b/packages/js/plugin/package.json deleted file mode 100644 index 205c468485..0000000000 --- a/packages/js/plugin/package.json +++ /dev/null @@ -1,41 +0,0 @@ -{ - "name": "@polywrap/plugin-js", - "description": "Polywrap plugin core package for plugin wrappers", - "version": "0.10.0", - "license": "MIT", - "repository": { - "type": "git", - "url": "https://github.com/polywrap/monorepo.git" - }, - "main": "build/index.js", - "files": [ - "build" - ], - "scripts": { - "build": "rimraf ./build && tsc --project tsconfig.build.json", - "lint": "eslint --color -c ../../../.eslintrc.js src/", - "test": "jest --passWithNoTests --runInBand --verbose", - "test:watch": "yarn test -- --watch" - }, - "dependencies": { - "@polywrap/core-js": "0.10.0", - "@polywrap/msgpack-js": "0.10.0", - "@polywrap/result": "0.10.0", - "@polywrap/tracing-js": "0.10.0", - "@polywrap/wrap-manifest-types-js": "0.10.0" - }, - "peerDependencies": { - "@polywrap/core-js": "0.10.x" - }, - "devDependencies": { - "@types/jest": "26.0.8", - "jest": "26.6.3", - "rimraf": "3.0.2", - "ts-jest": "26.5.4", - "ts-node": "10.9.1", - "typescript": "4.9.5" - }, - "publishConfig": { - "access": "public" - } -} diff --git a/packages/js/plugin/src/PluginFactory.ts b/packages/js/plugin/src/PluginFactory.ts deleted file mode 100644 index 0dbc5d0f07..0000000000 --- a/packages/js/plugin/src/PluginFactory.ts +++ /dev/null @@ -1,5 +0,0 @@ -import { PluginPackage } from "./PluginPackage"; - -export type PluginFactory = ( - config: TConfig -) => PluginPackage; diff --git a/packages/js/plugin/src/PluginMethod.ts b/packages/js/plugin/src/PluginMethod.ts deleted file mode 100644 index 0575f94ba1..0000000000 --- a/packages/js/plugin/src/PluginMethod.ts +++ /dev/null @@ -1,16 +0,0 @@ -/* eslint-disable @typescript-eslint/naming-convention */ -import { CoreClient, MaybeAsync } from "@polywrap/core-js"; - -/** - * Invocable plugin method. - * - * @param args Arguments for the method, structured as - * a map, removing the chance of incorrectly ordering arguments. - * @param client The client instance requesting this invocation. - * This client will be used for any sub-invokes that occur. - */ -export type PluginMethod< - TArgs extends Record = Record, - TResult = unknown, - TEnv extends Record = Record -> = (args: TArgs, client: CoreClient, env: TEnv) => MaybeAsync; diff --git a/packages/js/plugin/src/PluginModule.ts b/packages/js/plugin/src/PluginModule.ts deleted file mode 100644 index 04dbbd649d..0000000000 --- a/packages/js/plugin/src/PluginModule.ts +++ /dev/null @@ -1,65 +0,0 @@ -/* eslint-disable @typescript-eslint/naming-convention */ -import { PluginMethod } from "./PluginMethod"; - -import { CoreClient, WrapErrorCode } from "@polywrap/core-js"; -import { Result, ResultErr, ResultOk } from "@polywrap/result"; - -export abstract class PluginModule< - TConfig, - TEnv extends Record = Record -> { - private _config: TConfig; - - constructor(config: TConfig) { - this._config = config; - } - - public get config(): TConfig { - return this._config; - } - - public async _wrap_invoke< - TArgs extends Record = Record, - TResult = unknown - >( - method: string, - args: TArgs, - client: CoreClient, - env: TEnv - ): Promise> { - const fn = this.getMethod(method); - - if (!fn) { - return ResultErr(Error(`Plugin missing method "${method}"`)); - } - - if (typeof fn !== "function") { - return ResultErr( - Error(`Plugin method "${method}" must be of type 'function'`) - ); - } - - try { - const data = await fn(args, client, env); - return ResultOk(data); - } catch (e) { - e.code = WrapErrorCode.WRAPPER_INVOKE_ABORTED; - return ResultErr(e); - } - } - - public getMethod< - TArgs extends Record = Record, - TResult = unknown, - TEnv extends Record = Record - >(method: string): PluginMethod | undefined { - const fn: - | PluginMethod - | undefined = ((this as unknown) as Record< - string, - PluginMethod - >)[method]; - - return fn?.bind(this); - } -} diff --git a/packages/js/plugin/src/PluginPackage.ts b/packages/js/plugin/src/PluginPackage.ts deleted file mode 100644 index 6f42e72c2f..0000000000 --- a/packages/js/plugin/src/PluginPackage.ts +++ /dev/null @@ -1,60 +0,0 @@ -import { PluginModule } from "./PluginModule"; -import { PluginWrapper } from "./PluginWrapper"; -import { GetPluginMethodsFunc, PluginModuleWithMethods } from "./utils"; - -import { IWrapPackage, Wrapper } from "@polywrap/core-js"; -import { Result, ResultOk } from "@polywrap/result"; -import { WrapManifest } from "@polywrap/wrap-manifest-types-js"; - -export class PluginPackage< - TConfig, - TEnv extends Record = Record -> implements IWrapPackage { - constructor( - private _pluginModule: PluginModule, - private _manifest: WrapManifest - ) {} - - static from< - TConfig, - TEnv extends Record = Record - >( - pluginModule: PluginModule, - manifest?: WrapManifest - ): PluginPackage; - static from = Record>( - getPluginFuncs: GetPluginMethodsFunc, - manifest?: WrapManifest - ): PluginPackage; - static from< - TConfig, - TEnv extends Record = Record - >( - pluginModuleOrGetPluginFuncs: - | PluginModule - | GetPluginMethodsFunc, - manifest?: WrapManifest - ): PluginPackage { - if (typeof pluginModuleOrGetPluginFuncs === "function") { - const getPluginFuncs = pluginModuleOrGetPluginFuncs as GetPluginMethodsFunc; - - return new PluginPackage( - new PluginModuleWithMethods(getPluginFuncs), - manifest || ({} as WrapManifest) - ) as PluginPackage; - } else { - return new PluginPackage( - pluginModuleOrGetPluginFuncs as PluginModule, - manifest || ({} as WrapManifest) - ); - } - } - - async getManifest(): Promise> { - return ResultOk(this._manifest); - } - - async createWrapper(): Promise> { - return ResultOk(new PluginWrapper(this._manifest, this._pluginModule)); - } -} diff --git a/packages/js/plugin/src/PluginWrapper.ts b/packages/js/plugin/src/PluginWrapper.ts deleted file mode 100644 index 7281f40b2c..0000000000 --- a/packages/js/plugin/src/PluginWrapper.ts +++ /dev/null @@ -1,114 +0,0 @@ -import { PluginModule } from "./PluginModule"; -import { getErrorSource } from "./utils/getErrorSource"; - -import { - Wrapper, - CoreClient, - InvokeOptions, - InvocableResult, - GetFileOptions, - isBuffer, - WrapError, - WrapErrorCode, -} from "@polywrap/core-js"; -import { WrapManifest } from "@polywrap/wrap-manifest-types-js"; -import { msgpackDecode } from "@polywrap/msgpack-js"; -import { Result, ResultErr, ResultOk } from "@polywrap/result"; - -export class PluginWrapper implements Wrapper { - constructor( - private _manifest: WrapManifest, - private _module: PluginModule - ) {} - - public async getFile( - _: GetFileOptions - ): Promise> { - return ResultErr( - Error("client.getFile(...) is not implemented for Plugins.") - ); - } - - public getManifest(): WrapManifest { - return this._manifest; - } - - public async invoke( - options: InvokeOptions, - client: CoreClient - ): Promise> { - const { method } = options; - const args = options.args || {}; - - if (!this._module.getMethod(method)) { - const error = new WrapError(`Plugin missing method "${method}"`, { - code: WrapErrorCode.WRAPPER_METHOD_NOT_FOUND, - uri: options.uri.uri, - method, - }); - return ResultErr(error); - } - - // NOTE: this is used just in case the module instance - // we're interacting with is from versions < 0.10 - const genericModule = (this._module as unknown) as Record; - if (genericModule.setEnv) { - (genericModule.setEnv as (env: unknown) => void)(options.env || {}); - } - - let jsArgs: Record; - - // If the args are a msgpack buffer, deserialize it - if (isBuffer(args)) { - const result = msgpackDecode(args); - - if (typeof result !== "object") { - const error = new WrapError( - `Decoded MsgPack args did not result in an object.\nResult: ${result}`, - { - code: WrapErrorCode.WRAPPER_ARGS_MALFORMED, - uri: options.uri.uri, - method, - args: JSON.stringify(args), - } - ); - return ResultErr(error); - } - - jsArgs = result as Record; - } else { - jsArgs = args as Record; - } - - // Invoke the function - const result = await this._module._wrap_invoke( - method, - jsArgs, - client, - options.env || {} - ); - - if (result.ok) { - const data = result.value; - - return { - ...ResultOk(data), - encoded: false, - }; - } else { - const code = - (result.error as { code?: WrapErrorCode })?.code ?? - WrapErrorCode.WRAPPER_INVOKE_FAIL; - const reason = - result.error?.message ?? `Failed to invoke method "${method}"`; - const error = new WrapError(reason, { - code, - uri: options.uri.toString(), - method, - args: JSON.stringify(jsArgs, null, 2), - source: getErrorSource(result.error), - }); - return ResultErr(error); - } - } -} diff --git a/packages/js/plugin/src/index.ts b/packages/js/plugin/src/index.ts deleted file mode 100644 index efa3750dd0..0000000000 --- a/packages/js/plugin/src/index.ts +++ /dev/null @@ -1,5 +0,0 @@ -export * from "./PluginFactory"; -export * from "./PluginMethod"; -export * from "./PluginModule"; -export * from "./PluginPackage"; -export * from "./PluginWrapper"; diff --git a/packages/js/plugin/src/utils/GetPluginMethodsFunc.ts b/packages/js/plugin/src/utils/GetPluginMethodsFunc.ts deleted file mode 100644 index 6d95ce1467..0000000000 --- a/packages/js/plugin/src/utils/GetPluginMethodsFunc.ts +++ /dev/null @@ -1,10 +0,0 @@ -import { PluginModule, PluginMethod } from ".."; - -export type GetPluginMethodsFunc< - TEnv extends Record = Record -> = ( - module: PluginModule -) => Record< - string, - PluginMethod, unknown, Record> ->; diff --git a/packages/js/plugin/src/utils/PluginModuleWithMethods.ts b/packages/js/plugin/src/utils/PluginModuleWithMethods.ts deleted file mode 100644 index 03b1e6d639..0000000000 --- a/packages/js/plugin/src/utils/PluginModuleWithMethods.ts +++ /dev/null @@ -1,61 +0,0 @@ -/* eslint-disable @typescript-eslint/naming-convention */ - -import { PluginMethod } from "../PluginMethod"; -import { PluginModule } from "../PluginModule"; -import { GetPluginMethodsFunc } from "./GetPluginMethodsFunc"; - -import { CoreClient, WrapErrorCode } from "@polywrap/core-js"; -import { Result, ResultErr, ResultOk } from "@polywrap/result"; - -export class PluginModuleWithMethods< - TEnv extends Record = Record -> extends PluginModule { - constructor(private _getPluginMethods: GetPluginMethodsFunc) { - super({} as never); - } - - async _wrap_invoke< - TArgs extends Record = Record, - TResult = unknown - >( - method: string, - args: TArgs, - client: CoreClient, - env: TEnv - ): Promise> { - const fn = this.getMethod(method); - - if (!fn) { - return ResultErr(Error(`Plugin missing method "${method}"`)); - } - - if (typeof fn !== "function") { - return ResultErr( - Error(`Plugin method "${method}" must be of type 'function'`) - ); - } - - try { - const data = await fn(args, client, env); - return ResultOk(data); - } catch (e) { - e.code = WrapErrorCode.WRAPPER_INVOKE_ABORTED; - return ResultErr(e); - } - } - - getMethod< - TArgs extends Record = Record, - TResult = unknown - >(method: string): PluginMethod | undefined { - const fn: - | PluginMethod - | undefined = this._getPluginMethods(this)[method] as PluginMethod< - TArgs, - TResult, - TEnv - >; - - return fn?.bind(this); - } -} diff --git a/packages/js/plugin/src/utils/getErrorSource.ts b/packages/js/plugin/src/utils/getErrorSource.ts deleted file mode 100644 index 8b737f432a..0000000000 --- a/packages/js/plugin/src/utils/getErrorSource.ts +++ /dev/null @@ -1,31 +0,0 @@ -import { ErrorSource } from "@polywrap/core-js"; - -type RegExpGroups = - | (RegExpExecArray & { - groups?: { [name in T]: string | undefined } | { [key: string]: string }; - }) - | null; - -const re = /\((?.*):(?\d+):(?\d+)\)$/; - -// retrieve the most recent line of source information for an error -export function getErrorSource(error?: Error): ErrorSource | undefined { - if (!error || !error.stack) return undefined; - - // find first source line in stack - const stack = error.stack?.split("\n"); - let i = 0; - for (i; i < stack.length && !stack[i].startsWith(` at`); i++) {} // eslint-disable-line no-empty - - const result: RegExpGroups<"file" | "row" | "col"> = re.exec(stack[i]); - if (!result) return undefined; - - const { file, row, col } = result.groups!; // eslint-disable-line @typescript-eslint/no-non-null-assertion - return file - ? { - file, - row: row ? parseInt(row) : undefined, - col: col ? parseInt(col) : undefined, - } - : undefined; -} diff --git a/packages/js/plugin/src/utils/index.ts b/packages/js/plugin/src/utils/index.ts deleted file mode 100644 index 6301d810d9..0000000000 --- a/packages/js/plugin/src/utils/index.ts +++ /dev/null @@ -1,2 +0,0 @@ -export * from "./GetPluginMethodsFunc"; -export * from "./PluginModuleWithMethods"; diff --git a/packages/js/plugin/tsconfig.build.json b/packages/js/plugin/tsconfig.build.json deleted file mode 100644 index 77aadfdd2f..0000000000 --- a/packages/js/plugin/tsconfig.build.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "extends": "./tsconfig.json", - "include": [ - "./src/**/*.ts" - ], - "exclude": [ - "./src/**/__tests__" - ] -} diff --git a/packages/js/plugin/tsconfig.json b/packages/js/plugin/tsconfig.json deleted file mode 100644 index 5d37204c00..0000000000 --- a/packages/js/plugin/tsconfig.json +++ /dev/null @@ -1,10 +0,0 @@ -{ - "extends": "../../../tsconfig", - "compilerOptions": { - "outDir": "build" - }, - "include": [ - "./src/**/*.ts" - ], - "exclude": [] -} diff --git a/packages/js/result/README.md b/packages/js/result/README.md deleted file mode 100644 index 50f8ff24f2..0000000000 --- a/packages/js/result/README.md +++ /dev/null @@ -1,6 +0,0 @@ -# @polywrap/result - -## Description - -Result helpers to enable the "Result" pattern. -Enables compile-time error checking. diff --git a/packages/js/result/package.json b/packages/js/result/package.json deleted file mode 100644 index 0f67d4b86d..0000000000 --- a/packages/js/result/package.json +++ /dev/null @@ -1,26 +0,0 @@ -{ - "name": "@polywrap/result", - "description": "Result helpers", - "version": "0.10.0", - "license": "MIT", - "repository": { - "type": "git", - "url": "https://github.com/polywrap/monorepo.git" - }, - "main": "build/index.js", - "files": [ - "build" - ], - "scripts": { - "build": "rimraf ./build && tsc --project tsconfig.build.json", - "lint": "eslint --color -c ../../../.eslintrc.js src/" - }, - "devDependencies": { - "rimraf": "3.0.2", - "ts-node": "10.9.1", - "typescript": "4.9.5" - }, - "publishConfig": { - "access": "public" - } -} diff --git a/packages/js/result/src/Result.ts b/packages/js/result/src/Result.ts deleted file mode 100644 index 6ee3082756..0000000000 --- a/packages/js/result/src/Result.ts +++ /dev/null @@ -1,3 +0,0 @@ -export type Result = - | { ok: true; value: T } - | { ok: false; error: E | undefined }; diff --git a/packages/js/result/src/ResultErr.ts b/packages/js/result/src/ResultErr.ts deleted file mode 100644 index 7f7d962fc5..0000000000 --- a/packages/js/result/src/ResultErr.ts +++ /dev/null @@ -1,6 +0,0 @@ -import { Result } from "./Result"; - -// eslint-disable-next-line @typescript-eslint/naming-convention -export const ResultErr = (error?: E): Result => { - return { ok: false, error }; -}; diff --git a/packages/js/result/src/ResultOk.ts b/packages/js/result/src/ResultOk.ts deleted file mode 100644 index c7216f3d1c..0000000000 --- a/packages/js/result/src/ResultOk.ts +++ /dev/null @@ -1,6 +0,0 @@ -import { Result } from "./Result"; - -// eslint-disable-next-line @typescript-eslint/naming-convention -export const ResultOk = (data: T): Result => { - return { ok: true, value: data }; -}; diff --git a/packages/js/result/src/index.ts b/packages/js/result/src/index.ts deleted file mode 100644 index ef45426c3a..0000000000 --- a/packages/js/result/src/index.ts +++ /dev/null @@ -1,3 +0,0 @@ -export * from "./Result"; -export * from "./ResultErr"; -export * from "./ResultOk"; diff --git a/packages/js/result/tsconfig.build.json b/packages/js/result/tsconfig.build.json deleted file mode 100644 index 77aadfdd2f..0000000000 --- a/packages/js/result/tsconfig.build.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "extends": "./tsconfig.json", - "include": [ - "./src/**/*.ts" - ], - "exclude": [ - "./src/**/__tests__" - ] -} diff --git a/packages/js/result/tsconfig.json b/packages/js/result/tsconfig.json deleted file mode 100644 index 5d37204c00..0000000000 --- a/packages/js/result/tsconfig.json +++ /dev/null @@ -1,10 +0,0 @@ -{ - "extends": "../../../tsconfig", - "compilerOptions": { - "outDir": "build" - }, - "include": [ - "./src/**/*.ts" - ], - "exclude": [] -} diff --git a/packages/js/tracing/README.md b/packages/js/tracing/README.md deleted file mode 100644 index 1a8a7e5e93..0000000000 --- a/packages/js/tracing/README.md +++ /dev/null @@ -1,27 +0,0 @@ -# @polywrap/tracing-js - -## Steps to use tracing - -1. Run the zipkin client using docker - - ``` - docker run -d -p 9411:9411 openzipkin/zipkin - ``` - -2. Enable tracing when creating the `PolywrapClient` - - ```typescript - const client = new PolywrapClient({ - ..., - tracingEnabled: true - }) - ``` - - Or you can turn on tracing while running the `PolywrapClient` by calling the `tracingEnabled` method of `PolywrapClient`. - - ```typescript - // Turn tracing off - client.tracingEnabled(false); - ``` - -3. Once you run the app and started producing logs, go to zipkin client which is running on `http://localhost:9411`. There you can click `RUN QUERY` button without any filters to show all the logs. diff --git a/packages/js/tracing/package.json b/packages/js/tracing/package.json deleted file mode 100644 index fce8da2ec7..0000000000 --- a/packages/js/tracing/package.json +++ /dev/null @@ -1,35 +0,0 @@ -{ - "name": "@polywrap/tracing-js", - "description": "Polywrap Core Tracing", - "version": "0.10.0", - "license": "MIT", - "repository": { - "type": "git", - "url": "https://github.com/polywrap/monorepo.git" - }, - "main": "build/index.js", - "files": [ - "build" - ], - "scripts": { - "build": "rimraf ./build && tsc --project tsconfig.build.json", - "lint": "eslint --color -c ../../../.eslintrc.js src/" - }, - "dependencies": { - "@fetsorn/opentelemetry-console-exporter": "0.0.3", - "@opentelemetry/api": "1.2.0", - "@opentelemetry/exporter-trace-otlp-http": "0.32.0", - "@opentelemetry/resources": "1.6.0", - "@opentelemetry/sdk-trace-base": "1.6.0", - "@opentelemetry/sdk-trace-web": "1.6.0" - }, - "devDependencies": { - "@types/node": "^18.14.6", - "rimraf": "3.0.2", - "typescript": "4.9.5" - }, - "gitHead": "7346adaf5adb7e6bbb70d9247583e995650d390a", - "publishConfig": { - "access": "public" - } -} diff --git a/packages/js/tracing/src/index.ts b/packages/js/tracing/src/index.ts deleted file mode 100644 index 48c02cea7c..0000000000 --- a/packages/js/tracing/src/index.ts +++ /dev/null @@ -1,283 +0,0 @@ -import { - BasicTracerProvider, - SimpleSpanProcessor, - BatchSpanProcessor, - Tracer as otTracer, -} from "@opentelemetry/sdk-trace-base"; -import { WebTracerProvider } from "@opentelemetry/sdk-trace-web"; -import * as api from "@opentelemetry/api"; -import { Resource } from "@opentelemetry/resources"; -import { ConsoleExporterIcon } from "@fetsorn/opentelemetry-console-exporter"; -import { OTLPTraceExporter } from "@opentelemetry/exporter-trace-otlp-http"; -type MaybeAsync = Promise | T; - -export enum TracingLevel { - Low = 0, - Medium, - High, -} - -export interface TracerConfig { - tracingLevel: TracingLevel; - consoleEnabled: boolean; - consoleDetailed: boolean; - httpEnabled: boolean; - httpUrl: string; -} - -const isPromise = ( - test?: MaybeAsync -): test is Promise => - !!test && typeof (test as Promise).then === "function"; - -export class Tracer { - private static _config: TracerConfig = { - consoleEnabled: false, - tracingLevel: TracingLevel.High, - consoleDetailed: false, - httpEnabled: false, - httpUrl: "http://localhost:4318/v1/traces", - }; - - private static _tracer: otTracer; - private static _provider: - | WebTracerProvider - | BasicTracerProvider - | null = null; - private static _spans: Array = []; - - static enableTracing( - tracerName: string, - config: Partial - ): void { - this._config.tracingLevel = - config.tracingLevel ?? this._config.tracingLevel; - this._config.consoleEnabled = - config.consoleEnabled ?? this._config.consoleEnabled; - this._config.consoleDetailed = - config.consoleDetailed ?? this._config.consoleDetailed; - this._config.httpEnabled = config.httpEnabled ?? this._config.httpEnabled; - this._config.httpUrl = config.httpUrl ?? this._config.httpUrl; - this._initProvider(tracerName); - - if (this._provider) { - this._tracer = this._provider.getTracer(tracerName) as otTracer; - } - } - - static disableTracing(): void { - this._config.consoleEnabled = false; - this._config.httpEnabled = false; - } - - static startSpan(spanName: string, tracingLevel = TracingLevel.Low): void { - if ( - (!this._config.consoleEnabled && !this._config.httpEnabled) || - tracingLevel < this._config.tracingLevel - ) - return; - - const currentSpan = this._currentSpan(); - const span = this._tracer.startSpan( - spanName, - {}, - currentSpan - ? api.trace.setSpanContext( - api.context.active(), - currentSpan.spanContext() - ) - : undefined - ); - this._pushSpan(span); - } - - static endSpan(tracingLevel = TracingLevel.Low): void { - if ( - (!this._config.consoleEnabled && !this._config.httpEnabled) || - tracingLevel < this._config.tracingLevel - ) - return; - - const span = this._currentSpan(); - if (span) { - span.end(); - this._popSpan(); - } - } - - static setAttribute( - attrName: string, - data: unknown, - tracingLevel = TracingLevel.Low - ): void { - if ( - (!this._config.consoleEnabled && !this._config.httpEnabled) || - tracingLevel < this._config.tracingLevel - ) - return; - - const span = this._currentSpan(); - if (span) { - span.setAttribute(attrName, JSON.stringify(data)); - } - } - - static addEvent( - event: string, - data?: unknown, - tracingLevel = TracingLevel.Low - ): void { - if ( - (!this._config.consoleEnabled && !this._config.httpEnabled) || - tracingLevel < this._config.tracingLevel - ) - return; - - const span = this._currentSpan(); - - if (span) { - span.addEvent(event, { data: JSON.stringify(data) }); - } - } - - static recordException( - error: api.Exception, - tracingLevel = TracingLevel.Low - ): void { - if ( - (!this._config.consoleEnabled && !this._config.httpEnabled) || - tracingLevel < this._config.tracingLevel - ) - return; - - const span = this._currentSpan(); - - if (span) { - // recordException converts the error into a span event. - span.recordException(error); - - // If the exception means the operation results in an - // error state, you can also use it to update the span status. - span.setStatus({ code: api.SpanStatusCode.ERROR }); - } - } - - static traceMethod( - span: string, - tracingLevel: TracingLevel = TracingLevel.Low - ) { - return function ( - target: unknown, - key: string | symbol, - descriptor: PropertyDescriptor - ): PropertyDescriptor { - const original = descriptor.value; - - descriptor.value = function , TReturn>( - ...args: TArgs[] - ): TReturn { - try { - Tracer.startSpan(span, tracingLevel); - Tracer.setAttribute("args", { ...args }, tracingLevel); - - const result = original.apply(this, args); - - if (isPromise(result)) { - return (result.then((result) => { - Tracer.setAttribute("output", result, tracingLevel); - Tracer.endSpan(tracingLevel); - return result; - }) as unknown) as TReturn; - } else { - Tracer.setAttribute("output", result, tracingLevel); - Tracer.endSpan(tracingLevel); - return result; - } - } catch (error) { - Tracer.recordException(error, tracingLevel); - Tracer.endSpan(tracingLevel); - throw error; - } - }; - - return descriptor; - }; - } - - static traceFunc, TReturn>( - span: string, - func: (...args: TArgs) => TReturn, - tracingLevel: TracingLevel = TracingLevel.Low - ) { - return (...args: TArgs): TReturn => { - try { - this.startSpan(span, tracingLevel); - this.setAttribute("args", { ...args }, tracingLevel); - - const result = func(...args); - - if (isPromise(result)) { - return (result.then((result) => { - this.setAttribute("output", result, tracingLevel); - this.endSpan(tracingLevel); - return result; - }) as unknown) as TReturn; - } else { - this.setAttribute("output", result, tracingLevel); - this.endSpan(tracingLevel); - return result; - } - } catch (error) { - this.recordException(error, tracingLevel); - this.endSpan(tracingLevel); - throw error; - } - }; - } - - static _initProvider(name: string): void { - const providerResources = new Resource({ - "service.name": name, - }); - - if (typeof window === "undefined") { - this._provider = new BasicTracerProvider({ - resource: providerResources, - }); - } else { - this._provider = new WebTracerProvider({ - resource: providerResources, - }); - } - - // Configure span processor to send spans to the exporter - if (this._config.httpEnabled) { - this._provider.addSpanProcessor( - new SimpleSpanProcessor( - new OTLPTraceExporter({ url: this._config.httpUrl }) - ) - ); - } - if (this._config.consoleEnabled) { - this._provider.addSpanProcessor( - new BatchSpanProcessor( - new ConsoleExporterIcon({ isDetailed: this._config.consoleDetailed }) - ) - ); - } - - this._provider.register(); - } - - static _pushSpan(span: api.Span): void { - this._spans.push(span); - } - - static _currentSpan(): api.Span | undefined { - return this._spans.slice(-1)[0]; - } - - static _popSpan(): void { - this._spans.pop(); - } -} diff --git a/packages/js/tracing/tsconfig.build.json b/packages/js/tracing/tsconfig.build.json deleted file mode 100644 index 77aadfdd2f..0000000000 --- a/packages/js/tracing/tsconfig.build.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "extends": "./tsconfig.json", - "include": [ - "./src/**/*.ts" - ], - "exclude": [ - "./src/**/__tests__" - ] -} diff --git a/packages/js/tracing/tsconfig.json b/packages/js/tracing/tsconfig.json deleted file mode 100644 index fd4ebb1a2c..0000000000 --- a/packages/js/tracing/tsconfig.json +++ /dev/null @@ -1,13 +0,0 @@ -{ - "extends": "../../../tsconfig", - "compilerOptions": { - "outDir": "build", - "typeRoots": [ - "./src/**/*.d.ts" - ] - }, - "include": [ - "./src/**/*.ts" - ], - "exclude": [] -} diff --git a/packages/js/uri-resolver-extensions/.gitignore b/packages/js/uri-resolver-extensions/.gitignore deleted file mode 100644 index 24fcff1e7b..0000000000 --- a/packages/js/uri-resolver-extensions/.gitignore +++ /dev/null @@ -1,4 +0,0 @@ -readme/sub-sections/injected -/examples/**/*.d.ts -/examples/**/*.js -/examples/**/*.js.map diff --git a/packages/js/uri-resolver-extensions/README.md b/packages/js/uri-resolver-extensions/README.md deleted file mode 100644 index ba4639560e..0000000000 --- a/packages/js/uri-resolver-extensions/README.md +++ /dev/null @@ -1,259 +0,0 @@ -# @polywrap/uri-resolver-extensions-js - -npm - - -
-
-Polywrap URI resolver extensions to customize resolution in the Polywrap Client. - -## Installation - -```bash -npm install --save @polywrap/uri-resolver-extensions-js -``` - -## Usage - -If you build a configuration for the Polywrap client using the `ClientConfigBuilder` in the `@polywrap/client-config-builder-js` package, the `ExtendableUriResovler` is included by default. In that case you only need to register implementations of the URI Resolver Extension interface. - -Otherwise, you must also add the `ExtendableUriResolver` to your resolver. - -```ts - const clientConfig: CoreClientConfig = { - interfaces: new UriMap([ - [ - Uri.from("wrap://ens/uri-resolver.core.polywrap.eth"), - [ - Uri.from("wrap://ens/fs-resolver.polywrap.eth"), - Uri.from("wrap://ens/ipfs-resolver.polywrap.eth"), - Uri.from("wrap://ens/ens-resolver.polywrap.eth"), - ], - ], - ]), - resolver: RecursiveResolver.from( - [ - StaticResolver.from([ - ...redirects, - ...wrappers, - ...packages, - ]), - new ExtendableUriResolver(), - ] - ) - }; -``` - -# Reference - -## ExtendableUriResolver - -```ts -/** - * A Uri Resolver that delegates resolution to wrappers implementing the - * URI Resolver Extension Interface. - * */ -export class ExtendableUriResolver extends UriResolverAggregatorBase< - Error, - Error -> -``` - -### Properties - -#### extInterfaceUri (static) -```ts - /** The supported interface URIs to which resolver-ext implementations should be registered */ - public static defaultExtInterfaceUris: Uri[] = [ - Uri.from("wrap://ens/wraps.eth:uri-resolver-ext@1.1.0"), - Uri.from("wrap://ens/wraps.eth:uri-resolver-ext@1.0.0"), - ]; -``` - -#### extInterfaceUri -```ts - /** The active interface URIs to which implementations should be registered */ - public readonly extInterfaceUris: Uri[]; -``` - -### constructor -```ts - /** - * Create an ExtendableUriResolver - * - * @param extInterfaceUris - URI Resolver Interface URIs - * @param resolverName - Name to use in resolution history output - * */ - constructor( - extInterfaceUris: Uri[] = ExtendableUriResolver.defaultExtInterfaceUris, - resolverName = "ExtendableUriResolver" - ) -``` - -### Methods - -#### getUriResolvers -```ts - /** - * Get a list of URI Resolvers - * - * @param uri - the URI to query for resolvers - * @param client - a CoreClient instance that can be used to make an invocation - * @param resolutionContext - the current URI resolution context - * - * @returns a list of IUriResolver or an error - * */ - async getUriResolvers( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise[], Error>> -``` - -#### tryResolverUri -```ts - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * Attempts resolution with each the URI Resolver Extension wrappers sequentially. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> -``` - -#### getStepDescription (protected) -```ts - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @returns text describing the URI resolution step - * */ - protected getStepDescription = (): string -``` - -## UriResolverExtensionFileReader -```ts -/** An IFileReader that reads files by invoking URI Resolver Extension wrappers */ -export class UriResolverExtensionFileReader implements IFileReader -``` - -### constructor -```ts - /** - * Construct a UriResolverExtensionFileReader - * - * @param _resolverExtensionUri - URI of the URI Resolver Extension wrapper - * @param _wrapperUri - URI of the wrap package to read from - * @param _client - A CoreClient instance - * */ - constructor( - private readonly _resolverExtensionUri: Uri, - private readonly _wrapperUri: Uri, - private readonly _client: CoreClient - ) -``` - -### Methods - -#### readFile -```ts - /** - * Read a file - * - * @param filePath - the file's path from the wrap package root - * - * @returns a Result containing a buffer if successful, or an error - * */ - async readFile(filePath: string): Promise> -``` - -## UriResolverWrapper -```ts -/** - * An IUriResolver that delegates resolution to a wrapper that implements - * the URI Resolver Extension Interface - * */ -export class UriResolverWrapper extends ResolverWithHistory -``` - -### constructor -```ts - /** - * construct a UriResolverWrapper - * - * @param implementationUri - URI that resolves to a URI Resolver Extension implementation - * */ - constructor(public readonly implementationUri: Uri) -``` - -### Methods - -#### getStepDescription -```ts - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @returns text describing the URI resolution step - * */ - protected getStepDescription = (): string -``` - -#### tryResolveUriWithImplementation -```ts -/** - * Attempt to resolve a URI by invoking a URI Resolver Extension wrapper - * - * @param uri - the URI to resolve - * @param implementationUri - URI that resolves to a URI Resolver Extension implementation - * @param client - a CoreClient instance that will be used to invoke the URI Resolver Extension wrapper - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either URI or a manifest if successful - */ -const tryResolveUriWithImplementation = async ( - uri: Uri, - implementationUri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext -): Promise< - Result -> -``` - -#### _tryResolverUri (protected) -```ts - /** - * Attempt to resolve a URI by invoking a URI Resolver Extension wrapper, then - * parse the result to a wrap package, a wrapper, or a URI - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - protected async _tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> -``` - -## Development - -This package is open-source. It lives within the [Polywrap toolchain monorepo](https://github.com/polywrap/toolchain/tree/origin/packages/js/uri-resolver-extensions). Contributions from the community are welcomed! - -### Build -```bash -nvm use && yarn install && yarn build -``` - -### Test -```bash -yarn test -`` \ No newline at end of file diff --git a/packages/js/uri-resolver-extensions/examples/quickstart.ts b/packages/js/uri-resolver-extensions/examples/quickstart.ts deleted file mode 100644 index a1bc20315e..0000000000 --- a/packages/js/uri-resolver-extensions/examples/quickstart.ts +++ /dev/null @@ -1,41 +0,0 @@ -import { CoreClientConfig, Uri, UriMap } from "@polywrap/core-js"; -import { - PackageResolver, - RecursiveResolver, - RedirectResolver, - StaticResolver, -} from "@polywrap/uri-resolvers-js"; -import { ExtendableUriResolver } from "../build"; - -export function example(): CoreClientConfig { - const redirects: RedirectResolver[] = []; - // TODO: WrapperResolver is not exported. When that is fixed, change this type to WrapperResolver[] - const wrappers: PackageResolver[] = []; - const packages: PackageResolver[] = []; - // $start: quickstart-example - const clientConfig: CoreClientConfig = { - interfaces: new UriMap([ - [ - Uri.from("wrap://ens/uri-resolver.core.polywrap.eth"), - [ - Uri.from("wrap://ens/fs-resolver.polywrap.eth"), - Uri.from("wrap://ens/ipfs-resolver.polywrap.eth"), - Uri.from("wrap://ens/ens-resolver.polywrap.eth"), - ], - ], - ]), - resolver: RecursiveResolver.from( - [ - StaticResolver.from([ - ...redirects, - ...wrappers, - ...packages, - ]), - new ExtendableUriResolver(), - ] - ) - }; - // $end - - return clientConfig; -} diff --git a/packages/js/uri-resolver-extensions/examples/tsconfig.examples.json b/packages/js/uri-resolver-extensions/examples/tsconfig.examples.json deleted file mode 100644 index f37de53612..0000000000 --- a/packages/js/uri-resolver-extensions/examples/tsconfig.examples.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "extends": "../tsconfig.json", - "include": [ - "./**/*.ts" - ], -} \ No newline at end of file diff --git a/packages/js/uri-resolver-extensions/jest.config.js b/packages/js/uri-resolver-extensions/jest.config.js deleted file mode 100644 index 773225b8db..0000000000 --- a/packages/js/uri-resolver-extensions/jest.config.js +++ /dev/null @@ -1,12 +0,0 @@ -module.exports = { - collectCoverage: true, - preset: "ts-jest", - testEnvironment: "node", - testMatch: ["**/?(*.)+(spec|test).[jt]s?(x)"], - modulePathIgnorePatterns: ["./src/__tests__/wrappers"], - globals: { - "ts-jest": { - diagnostics: false, - }, - }, -}; diff --git a/packages/js/uri-resolver-extensions/package.json b/packages/js/uri-resolver-extensions/package.json deleted file mode 100644 index 98ada385c1..0000000000 --- a/packages/js/uri-resolver-extensions/package.json +++ /dev/null @@ -1,88 +0,0 @@ -{ - "name": "@polywrap/uri-resolver-extensions-js", - "description": "Polywrap URI resolver extensions", - "version": "0.10.0", - "license": "MIT", - "repository": { - "type": "git", - "url": "https://github.com/polywrap/monorepo.git" - }, - "main": "build/index.js", - "files": [ - "build" - ], - "scripts": { - "build": "yarn build:fast", - "build:docs": "yarn build:snippets && yarn build:readme", - "build:fast": "rimraf ./build && tsc --project tsconfig.build.json", - "lint": "eslint --color -c ../../../.eslintrc.js src/", - "test": "jest --passWithNoTests --runInBand --verbose", - "test:watch": "yarn test -- --watch", - "build:snippets": "tsc --project ./examples/tsconfig.examples.json", - "build:readme": "yarn doc-snippets combine" - }, - "dependencies": { - "@polywrap/core-js": "0.10.0", - "@polywrap/result": "0.10.0", - "@polywrap/uri-resolvers-js": "0.10.0", - "@polywrap/wasm-js": "0.10.0", - "@polywrap/wrap-manifest-types-js": "0.10.0" - }, - "devDependencies": { - "@polywrap/cli-js": "0.10.0", - "@polywrap/core-client-js": "0.10.0", - "@polywrap/plugin-js": "0.10.0", - "@polywrap/test-cases": "0.10.0", - "@types/jest": "26.0.8", - "base64-to-uint8array": "1.0.0", - "copyfiles": "2.4.1", - "doc-snippets": "~1.0.0", - "jest": "26.6.3", - "rimraf": "3.0.2", - "ts-jest": "26.5.4", - "ts-node": "10.9.1", - "typescript": "4.9.5" - }, - "publishConfig": { - "access": "public" - }, - "doc-snippets": { - "extract": { - "include": [ - "./src/**/*.{ts,tsx,json,yaml,txt,md,graphql,cue}", - "./examples/**/*.{ts,tsx,json,yaml,txt,md,graphql,cue}" - ], - "ignore": [ - "./**/node_modules/**", - "./**/.polywrap/**", - "./**/__tests__/**" - ], - "dir": "./" - }, - "inject": { - "dir": "./readme", - "include": "./README.md" - }, - "startTokens": [ - { - "pattern": "$start: ", - "inline": false - }, - { - "pattern": "/* $: {SNIPPET_NAME} */", - "inline": true - } - ], - "endTokens": [ - { - "pattern": "$end", - "inline": false - }, - { - "pattern": "/* $ */", - "inline": true - } - ], - "outputDir": "./" - } -} diff --git a/packages/js/uri-resolver-extensions/readme/README.md b/packages/js/uri-resolver-extensions/readme/README.md deleted file mode 100644 index 1a52edbdcd..0000000000 --- a/packages/js/uri-resolver-extensions/readme/README.md +++ /dev/null @@ -1,124 +0,0 @@ -# @polywrap/uri-resolver-extensions-js - -npm - - -
-
-Polywrap URI resolver extensions to customize resolution in the Polywrap Client. - -## Installation - -```bash -npm install --save @polywrap/uri-resolver-extensions-js -``` - -## Usage - -If you build a configuration for the Polywrap client using the `ClientConfigBuilder` in the `@polywrap/client-config-builder-js` package, the `ExtendableUriResovler` is included by default. In that case you only need to register implementations of the URI Resolver Extension interface. - -Otherwise, you must also add the `ExtendableUriResolver` to your resolver. - -```ts -$snippet: quickstart-example -``` - -# Reference - -## ExtendableUriResolver - -```ts -$snippet: ExtendableUriResolver -``` - -### Properties - -#### extInterfaceUri (static) -```ts -$snippet: ExtendableUriResolver-extInterfaceUri-static -``` - -#### extInterfaceUri -```ts -$snippet: ExtendableUriResolver-extInterfaceUri -``` - -### constructor -```ts -$snippet: ExtendableUriResolver-constructor -``` - -### Methods - -#### getUriResolvers -```ts -$snippet: ExtendableUriResolver-getUriResolvers -``` - -#### tryResolverUri -```ts -$snippet: ExtendableUriResolver-tryResolverUri -``` - -#### getStepDescription (protected) -```ts -$snippet: ExtendableUriResolver-getStepDescription -``` - -## UriResolverExtensionFileReader -```ts -$snippet: UriResolverExtensionFileReader -``` - -### constructor -```ts -$snippet: UriResolverExtensionFileReader-constructor -``` - -### Methods - -#### readFile -```ts -$snippet: UriResolverExtensionFileReader-readFile -``` - -## UriResolverWrapper -```ts -$snippet: UriResolverWrapper -``` - -### constructor -```ts -$snippet: UriResolverWrapper-constructor -``` - -### Methods - -#### getStepDescription -```ts -$snippet: UriResolverWrapper-getStepDescription -``` - -#### tryResolveUriWithImplementation -```ts -$snippet: UriResolverWrapper-tryResolveUriWithImplementation -``` - -#### _tryResolverUri (protected) -```ts -$snippet: UriResolverWrapper-_tryResolverUri -``` - -## Development - -This package is open-source. It lives within the [Polywrap toolchain monorepo](https://github.com/polywrap/toolchain/tree/origin/packages/js/uri-resolver-extensions). Contributions from the community are welcomed! - -### Build -```bash -nvm use && yarn install && yarn build -``` - -### Test -```bash -yarn test -`` \ No newline at end of file diff --git a/packages/js/uri-resolver-extensions/src/ExtendableUriResolver.ts b/packages/js/uri-resolver-extensions/src/ExtendableUriResolver.ts deleted file mode 100644 index aefdb14c81..0000000000 --- a/packages/js/uri-resolver-extensions/src/ExtendableUriResolver.ts +++ /dev/null @@ -1,134 +0,0 @@ -import { UriResolverWrapper } from "./UriResolverWrapper"; - -import { - Uri, - CoreClient, - IUriResolver, - IUriResolutionContext, - UriPackageOrWrapper, -} from "@polywrap/core-js"; -import { Result, ResultErr, ResultOk } from "@polywrap/result"; -import { - UriResolverAggregatorBase, - UriResolutionResult, -} from "@polywrap/uri-resolvers-js"; - -// $start: ExtendableUriResolver -/** - * A Uri Resolver that delegates resolution to wrappers implementing the - * URI Resolver Extension Interface. - * */ -export class ExtendableUriResolver extends UriResolverAggregatorBase< - Error, - Error -> /* $ */ { - // $start: ExtendableUriResolver-extInterfaceUri-static - /** The supported interface URIs to which resolver-ext implementations should be registered */ - public static defaultExtInterfaceUris: Uri[] = [ - Uri.from("wrap://ens/wraps.eth:uri-resolver-ext@1.1.0"), - Uri.from("wrap://ens/wraps.eth:uri-resolver-ext@1.0.0"), - ]; - // $end - - // $start: ExtendableUriResolver-extInterfaceUri - /** The active interface URIs to which implementations should be registered */ - public readonly extInterfaceUris: Uri[]; - // $end - private readonly _resolverName: string; - - // $start: ExtendableUriResolver-constructor - /** - * Create an ExtendableUriResolver - * - * @param extInterfaceUris - URI Resolver Interface URIs - * @param resolverName - Name to use in resolution history output - * */ - constructor( - extInterfaceUris: Uri[] = ExtendableUriResolver.defaultExtInterfaceUris, - resolverName = "ExtendableUriResolver" - ) /* $ */ { - super(); - this.extInterfaceUris = extInterfaceUris; - this._resolverName = resolverName; - } - - // $start: ExtendableUriResolver-getUriResolvers - /** - * Get a list of URI Resolvers - * - * @param uri - the URI to query for resolvers - * @param client - a CoreClient instance that can be used to make an invocation - * @param resolutionContext - the current URI resolution context - * - * @returns a list of IUriResolver or an error - * */ - async getUriResolvers( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise[], Error>> /* $ */ { - const uriResolverImpls: Uri[] = []; - - for (const extInterfaceUri of this.extInterfaceUris) { - const getImplementationsResult = await client.getImplementations( - extInterfaceUri, - { - resolutionContext: resolutionContext.createSubContext(), - } - ); - - if (!getImplementationsResult.ok) { - return ResultErr(getImplementationsResult.error); - } - - uriResolverImpls.push(...getImplementationsResult.value); - } - - const resolvers: UriResolverWrapper[] = uriResolverImpls - .filter((x) => !resolutionContext.isResolving(x)) - .map((implementationUri) => new UriResolverWrapper(implementationUri)); - - return ResultOk(resolvers); - } - - // $start: ExtendableUriResolver-tryResolverUri - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * Attempts resolution with each the URI Resolver Extension wrappers sequentially. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> /* $ */ { - const result = await this.getUriResolvers(uri, client, resolutionContext); - if (!result.ok) { - return UriResolutionResult.err(result.error); - } - const resolvers = result.value as UriResolverWrapper[]; - - if (resolvers.length === 0) { - return UriResolutionResult.ok(uri); - } - - return await super.tryResolveUriWithResolvers( - uri, - client, - resolvers, - resolutionContext - ); - } - - // $start: ExtendableUriResolver-getStepDescription - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @returns text describing the URI resolution step - * */ - protected getStepDescription = (): string /* $ */ => `${this._resolverName}`; -} diff --git a/packages/js/uri-resolver-extensions/src/ResolverExtensionLoader.ts b/packages/js/uri-resolver-extensions/src/ResolverExtensionLoader.ts deleted file mode 100644 index 57f36de9e4..0000000000 --- a/packages/js/uri-resolver-extensions/src/ResolverExtensionLoader.ts +++ /dev/null @@ -1,55 +0,0 @@ -import { - Uri, - CoreClient, - Wrapper, - IUriResolutionContext, -} from "@polywrap/core-js"; -import { Result, ResultErr, ResultOk } from "@polywrap/result"; - -/* - * load a URI Resolver Extension wrapper, given a URI that resolves to it - * - * @param currentUri - The URI currently being resolved - * @param resolverExtensionUri - A URI that resolves to the Resolver Extension - * @param client - A CoreClient instance - * @param resolutionContext - The current URI resolution context - * - * @returns a Result containing a Wrapper or an error - * */ -export const loadResolverExtension = async ( - currentUri: Uri, - resolverExtensionUri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext -): Promise> => { - const result = await client.tryResolveUri({ - uri: resolverExtensionUri, - resolutionContext, - }); - - if (!result.ok) { - return result; - } - - const uriPackageOrWrapper = result.value; - - if (uriPackageOrWrapper.type === "uri") { - const lastTriedUri = uriPackageOrWrapper.uri as Uri; - - return ResultErr( - `While resolving ${currentUri.uri} with URI resolver extension ${resolverExtensionUri.uri}, the extension could not be fully resolved. Last tried URI is ${lastTriedUri.uri}` - ); - } - - if (uriPackageOrWrapper.type === "package") { - const result = await uriPackageOrWrapper.package.createWrapper(); - - if (!result.ok) { - return result; - } - - return ResultOk(result.value); - } else { - return ResultOk(uriPackageOrWrapper.wrapper); - } -}; diff --git a/packages/js/uri-resolver-extensions/src/UriResolverExtensionFileReader.ts b/packages/js/uri-resolver-extensions/src/UriResolverExtensionFileReader.ts deleted file mode 100644 index 88895da8be..0000000000 --- a/packages/js/uri-resolver-extensions/src/UriResolverExtensionFileReader.ts +++ /dev/null @@ -1,66 +0,0 @@ -import { - CoreClient, - combinePaths, - InvokeOptions, - InvokeResult, - Uri, - UriResolverInterface, - Wrapper, -} from "@polywrap/core-js"; -import { IFileReader } from "@polywrap/wasm-js"; -import { Result, ResultErr } from "@polywrap/result"; - -// $start: UriResolverExtensionFileReader -/** An IFileReader that reads files by invoking URI Resolver Extension wrappers */ -export class UriResolverExtensionFileReader implements IFileReader /* $ */ { - // $start: UriResolverExtensionFileReader-constructor - /** - * Construct a UriResolverExtensionFileReader - * - * @param _resolverExtensionUri - URI of the URI Resolver Extension wrapper - * @param _wrapperUri - URI of the wrap package to read from - * @param _client - A CoreClient instance - * */ - constructor( - private readonly _resolverExtensionUri: Uri, - private readonly _wrapperUri: Uri, - private readonly _client: CoreClient - ) /* $ */ {} - - // $start: UriResolverExtensionFileReader-readFile - /** - * Read a file - * - * @param filePath - the file's path from the wrap package root - * - * @returns a Result containing a buffer if successful, or an error - * */ - async readFile(filePath: string): Promise> /* $ */ { - const path = combinePaths(this._wrapperUri.path, filePath); - const result = await UriResolverInterface.module.getFile( - { - invoke: ( - options: InvokeOptions - ): Promise> => this._client.invoke(options), - invokeWrapper: ( - options: InvokeOptions & { wrapper: Wrapper } - ): Promise> => - this._client.invokeWrapper(options), - }, - this._resolverExtensionUri, - path - ); - if (!result.ok) return result; - if (!result.value) { - return ResultErr( - new Error( - `File not found at ${path} using resolver ${this._resolverExtensionUri.uri}` - ) - ); - } - return { - value: result.value, - ok: true, - }; - } -} diff --git a/packages/js/uri-resolver-extensions/src/UriResolverWrapper.ts b/packages/js/uri-resolver-extensions/src/UriResolverWrapper.ts deleted file mode 100644 index 41d892cbc6..0000000000 --- a/packages/js/uri-resolver-extensions/src/UriResolverWrapper.ts +++ /dev/null @@ -1,139 +0,0 @@ -import { UriResolverExtensionFileReader } from "./UriResolverExtensionFileReader"; -import { loadResolverExtension } from "./ResolverExtensionLoader"; - -import { - Uri, - CoreClient, - UriResolverInterface, - IUriResolutionContext, - UriPackageOrWrapper, - getEnvFromUriHistory, -} from "@polywrap/core-js"; -import { Result, ResultOk } from "@polywrap/result"; -import { WasmPackage } from "@polywrap/wasm-js"; -import { - ResolverWithHistory, - UriResolutionResult, -} from "@polywrap/uri-resolvers-js"; - -// $start: UriResolverWrapper -/** - * An IUriResolver that delegates resolution to a wrapper that implements - * the URI Resolver Extension Interface - * */ -export class UriResolverWrapper extends ResolverWithHistory /* $ */ { - // $start: UriResolverWrapper-constructor - /** - * construct a UriResolverWrapper - * - * @param implementationUri - URI that resolves to a URI Resolver Extension implementation - * */ - constructor(public readonly implementationUri: Uri) /* $ */ { - super(); - } - - // $start: UriResolverWrapper-getStepDescription - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @returns text describing the URI resolution step - * */ - protected getStepDescription = (): string /* $ */ => - `ResolverExtension (${this.implementationUri.uri})`; - - // $start: UriResolverWrapper-_tryResolverUri - /** - * Attempt to resolve a URI by invoking a URI Resolver Extension wrapper, then - * parse the result to a wrap package, a wrapper, or a URI - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - protected async _tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> /* $ */ { - const result = await tryResolveUriWithImplementation( - uri, - this.implementationUri, - client, - resolutionContext - ); - - if (!result.ok) { - return UriResolutionResult.err(result.error); - } - - const uriOrManifest = result.value; - - if (uriOrManifest?.uri) { - return UriResolutionResult.ok(new Uri(uriOrManifest.uri)); - } else if (uriOrManifest?.manifest) { - const wrapPackage = WasmPackage.from( - uriOrManifest.manifest, - new UriResolverExtensionFileReader(this.implementationUri, uri, client) - ); - - return UriResolutionResult.ok(uri, wrapPackage); - } - - return UriResolutionResult.ok(uri); - } -} - -// $start: UriResolverWrapper-tryResolveUriWithImplementation -/** - * Attempt to resolve a URI by invoking a URI Resolver Extension wrapper - * - * @param uri - the URI to resolve - * @param implementationUri - URI that resolves to a URI Resolver Extension implementation - * @param client - a CoreClient instance that will be used to invoke the URI Resolver Extension wrapper - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either URI or a manifest if successful - */ -const tryResolveUriWithImplementation = async ( - uri: Uri, - implementationUri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext -): Promise< - Result -> /* $ */ => { - const subContext = resolutionContext.createSubContext(); - const result = await loadResolverExtension( - uri, - implementationUri, - client, - subContext - ); - - if (!result.ok) { - return result; - } - - const extensionWrapper = result.value; - - const env = getEnvFromUriHistory(subContext.getResolutionPath(), client); - const invokeResult = await client.invokeWrapper( - { - wrapper: extensionWrapper, - uri: implementationUri, - method: "tryResolveUri", - args: { - authority: uri.authority, - path: uri.path, - }, - env: env, - } - ); - - if (!invokeResult.ok) { - return invokeResult; - } - - const uriOrManifest = invokeResult.value as UriResolverInterface.MaybeUriOrManifest; - return ResultOk(uriOrManifest ?? undefined); -}; diff --git a/packages/js/uri-resolver-extensions/src/__tests__/embeds/test-resolver/wrap.info b/packages/js/uri-resolver-extensions/src/__tests__/embeds/test-resolver/wrap.info deleted file mode 100644 index fa01c3e2fd8b9ba06c1e6fd5a0d01fe192038ac5..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 2337 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 diff --git a/packages/js/uri-resolver-extensions/src/__tests__/helpers/expectHistory.ts b/packages/js/uri-resolver-extensions/src/__tests__/helpers/expectHistory.ts deleted file mode 100644 index 43522689fc..0000000000 --- a/packages/js/uri-resolver-extensions/src/__tests__/helpers/expectHistory.ts +++ /dev/null @@ -1,31 +0,0 @@ -import { buildCleanUriHistory, IUriResolutionStep } from "@polywrap/core-js"; -import { GetPathToTestWrappers } from "@polywrap/test-cases"; -import fs from "fs"; - -export const expectHistory = async ( - receivedHistory: IUriResolutionStep[] | undefined, - historyFileName: string -): Promise => { - if (!receivedHistory) { - fail("History is not defined"); - } - - const expectedCleanHistoryStr = await fs.promises.readFile( - `${__dirname}/../histories/${historyFileName}.json`, - "utf-8" - ); - const expectedCleanHistory = JSON.stringify(JSON.parse(expectedCleanHistoryStr), null, 2); - - - const receivedCleanHistory = replaceAll( - JSON.stringify(buildCleanUriHistory(receivedHistory), null, 2), - `${GetPathToTestWrappers()}`, - "$root-wrapper-dir" - ); - - expect(receivedCleanHistory).toEqual(expectedCleanHistory); -}; - -function replaceAll(str: string, strToReplace: string, replaceStr: string) { - return str.replace(new RegExp(strToReplace, "g"), replaceStr); -} diff --git a/packages/js/uri-resolver-extensions/src/__tests__/histories/can-resolve-package.json b/packages/js/uri-resolver-extensions/src/__tests__/histories/can-resolve-package.json deleted file mode 100644 index a619bfe968..0000000000 --- a/packages/js/uri-resolver-extensions/src/__tests__/histories/can-resolve-package.json +++ /dev/null @@ -1,14 +0,0 @@ -[ - "wrap://test/package => UriResolverAggregator => package (wrap://test/package)", - [ - "wrap://test/package => StaticResolver - Miss", - "wrap://test/package => ExtendableUriResolver => package (wrap://test/package)", - [ - "wrap://package/test-resolver => UriResolverAggregator => package (wrap://package/test-resolver)", - [ - "wrap://package/test-resolver => StaticResolver - Package (wrap://package/test-resolver) => package (wrap://package/test-resolver)" - ], - "wrap://test/package => ResolverExtension (wrap://package/test-resolver) => package (wrap://test/package)" - ] - ] -] diff --git a/packages/js/uri-resolver-extensions/src/__tests__/histories/can-resolve-uri.json b/packages/js/uri-resolver-extensions/src/__tests__/histories/can-resolve-uri.json deleted file mode 100644 index dc0dd43dc8..0000000000 --- a/packages/js/uri-resolver-extensions/src/__tests__/histories/can-resolve-uri.json +++ /dev/null @@ -1,26 +0,0 @@ -[ - "wrap://test/from => UriResolverAggregator => uri (wrap://test/to)", - [ - "wrap://test/from => StaticResolver - Miss", - "wrap://test/from => ExtendableUriResolver => uri (wrap://test/to)", - [ - "wrap://package/test-resolver => UriResolverAggregator => package (wrap://package/test-resolver)", - [ - "wrap://package/test-resolver => StaticResolver - Package (wrap://package/test-resolver) => package (wrap://package/test-resolver)" - ], - "wrap://test/from => ResolverExtension (wrap://package/test-resolver) => uri (wrap://test/to)" - ] - ], - "wrap://test/to => UriResolverAggregator", - [ - "wrap://test/to => StaticResolver - Miss", - "wrap://test/to => ExtendableUriResolver", - [ - "wrap://package/test-resolver => UriResolverAggregator => package (wrap://package/test-resolver)", - [ - "wrap://package/test-resolver => StaticResolver - Package (wrap://package/test-resolver) => package (wrap://package/test-resolver)" - ], - "wrap://test/to => ResolverExtension (wrap://package/test-resolver)" - ] - ] -] diff --git a/packages/js/uri-resolver-extensions/src/__tests__/histories/not-a-match.json b/packages/js/uri-resolver-extensions/src/__tests__/histories/not-a-match.json deleted file mode 100644 index 06c334e8e4..0000000000 --- a/packages/js/uri-resolver-extensions/src/__tests__/histories/not-a-match.json +++ /dev/null @@ -1,14 +0,0 @@ -[ - "wrap://test/not-a-match => UriResolverAggregator", - [ - "wrap://test/not-a-match => StaticResolver - Miss", - "wrap://test/not-a-match => ExtendableUriResolver", - [ - "wrap://package/test-resolver => UriResolverAggregator => package (wrap://package/test-resolver)", - [ - "wrap://package/test-resolver => StaticResolver - Package (wrap://package/test-resolver) => package (wrap://package/test-resolver)" - ], - "wrap://test/not-a-match => ResolverExtension (wrap://package/test-resolver)" - ] - ] -] diff --git a/packages/js/uri-resolver-extensions/src/__tests__/histories/not-found-extension.json b/packages/js/uri-resolver-extensions/src/__tests__/histories/not-found-extension.json deleted file mode 100644 index fccc0c2551..0000000000 --- a/packages/js/uri-resolver-extensions/src/__tests__/histories/not-found-extension.json +++ /dev/null @@ -1,10 +0,0 @@ -[ - "wrap://test/not-a-match => UriResolverAggregator => error (While resolving wrap://test/not-a-match with URI resolver extension wrap://test/undefined-resolver, the extension could not be fully resolved. Last tried URI is wrap://test/undefined-resolver)", - [ - "wrap://test/not-a-match => ExtendableUriResolver => error (While resolving wrap://test/not-a-match with URI resolver extension wrap://test/undefined-resolver, the extension could not be fully resolved. Last tried URI is wrap://test/undefined-resolver)", - [ - "wrap://test/undefined-resolver => UriResolverAggregator", - "wrap://test/not-a-match => ResolverExtension (wrap://test/undefined-resolver) => error (While resolving wrap://test/not-a-match with URI resolver extension wrap://test/undefined-resolver, the extension could not be fully resolved. Last tried URI is wrap://test/undefined-resolver)" - ] - ] -] diff --git a/packages/js/uri-resolver-extensions/src/__tests__/histories/shows-plugin-extension-error.json b/packages/js/uri-resolver-extensions/src/__tests__/histories/shows-plugin-extension-error.json deleted file mode 100644 index 2ac0166a01..0000000000 --- a/packages/js/uri-resolver-extensions/src/__tests__/histories/shows-plugin-extension-error.json +++ /dev/null @@ -1,14 +0,0 @@ -[ - "wrap://test/error => UriResolverAggregator => error (Test error\ncode: 51 WRAPPER INVOKE ABORTED\nuri: wrap://package/test-resolver\nmethod: tryResolveUri\nargs: {\n \"authority\": \"test\",\n \"path\": \"error\"\n} )", - [ - "wrap://test/error => StaticResolver - Miss", - "wrap://test/error => ExtendableUriResolver => error (Test error\ncode: 51 WRAPPER INVOKE ABORTED\nuri: wrap://package/test-resolver\nmethod: tryResolveUri\nargs: {\n \"authority\": \"test\",\n \"path\": \"error\"\n} )", - [ - "wrap://package/test-resolver => UriResolverAggregator => package (wrap://package/test-resolver)", - [ - "wrap://package/test-resolver => StaticResolver - Package (wrap://package/test-resolver) => package (wrap://package/test-resolver)" - ], - "wrap://test/error => ResolverExtension (wrap://package/test-resolver) => error (Test error\ncode: 51 WRAPPER INVOKE ABORTED\nuri: wrap://package/test-resolver\nmethod: tryResolveUri\nargs: {\n \"authority\": \"test\",\n \"path\": \"error\"\n} )" - ] - ] -] diff --git a/packages/js/uri-resolver-extensions/src/__tests__/histories/shows-wasm-extension-error.json b/packages/js/uri-resolver-extensions/src/__tests__/histories/shows-wasm-extension-error.json deleted file mode 100644 index dadd6e97e8..0000000000 --- a/packages/js/uri-resolver-extensions/src/__tests__/histories/shows-wasm-extension-error.json +++ /dev/null @@ -1,14 +0,0 @@ -[ - "wrap://test/error => UriResolverAggregator => error (__wrap_abort: Test error\ncode: 51 WRAPPER INVOKE ABORTED\nuri: wrap://package/test-resolver\nmethod: tryResolveUri\nargs: {\n \"authority\": \"test\",\n \"path\": \"error\"\n} \nsource: { file: \"src/wrap/module/wrapped.rs\", row: 35, col: 21 })", - [ - "wrap://test/error => StaticResolver - Miss", - "wrap://test/error => ExtendableUriResolver => error (__wrap_abort: Test error\ncode: 51 WRAPPER INVOKE ABORTED\nuri: wrap://package/test-resolver\nmethod: tryResolveUri\nargs: {\n \"authority\": \"test\",\n \"path\": \"error\"\n} \nsource: { file: \"src/wrap/module/wrapped.rs\", row: 35, col: 21 })", - [ - "wrap://package/test-resolver => UriResolverAggregator => package (wrap://package/test-resolver)", - [ - "wrap://package/test-resolver => StaticResolver - Package (wrap://package/test-resolver) => package (wrap://package/test-resolver)" - ], - "wrap://test/error => ResolverExtension (wrap://package/test-resolver) => error (__wrap_abort: Test error\ncode: 51 WRAPPER INVOKE ABORTED\nuri: wrap://package/test-resolver\nmethod: tryResolveUri\nargs: {\n \"authority\": \"test\",\n \"path\": \"error\"\n} \nsource: { file: \"src/wrap/module/wrapped.rs\", row: 35, col: 21 })" - ] - ] -] diff --git a/packages/js/uri-resolver-extensions/src/__tests__/resolver-extensions.spec.ts b/packages/js/uri-resolver-extensions/src/__tests__/resolver-extensions.spec.ts deleted file mode 100644 index 7840aae2dc..0000000000 --- a/packages/js/uri-resolver-extensions/src/__tests__/resolver-extensions.spec.ts +++ /dev/null @@ -1,455 +0,0 @@ -import { ExtendableUriResolver } from "../ExtendableUriResolver"; -import { expectHistory } from "./helpers/expectHistory"; - -import { Uri, UriMap, UriResolutionContext, IWrapPackage } from "@polywrap/core-js"; -import { PolywrapCoreClient } from "@polywrap/core-client-js"; -import { PluginPackage } from "@polywrap/plugin-js"; -import { WasmPackage } from "@polywrap/wasm-js"; -import { RecursiveResolver, StaticResolver } from "@polywrap/uri-resolvers-js"; -import { Commands } from "@polywrap/cli-js"; -import path from "path"; -import fs from "fs"; - -jest.setTimeout(60000); - -const customPluginResolverUri = Uri.from("wrap://package/test-resolver"); -const customPluginResolver = PluginPackage.from(() => ({ - tryResolveUri: async ( - args: any, - client: PolywrapCoreClient - ): Promise<{ - uri?: string | null; - manifest?: Uint8Array | null; - } | null> => { - if (args.authority !== "test") { - return null; - } - - switch (args.path) { - case "from": - return { - uri: Uri.from("test/to").uri, - }; - case "package": - return { - manifest: new Uint8Array([]), - }; - case "error": - throw new Error("Test error"); - default: - return null; - } - }, -})); - -describe("Resolver extensions", () => { - - let testResolverPackage: IWrapPackage; - - beforeAll(async () => { - const wrapDir = path.join(__dirname, "/wrappers/test-resolver"); - - // Build the test-resolver wrapper - const res = await Commands.build({}, { - cwd: wrapDir - }); - - if (res.exitCode !== 0) { - fail(`STDOUT: ${res.stdout}\nSTDERR: ${res.stderr}`); - } - - const wrapBuildDir = path.join(wrapDir, "build"); - - // Load the wrapper from disk - testResolverPackage = WasmPackage.from( - fs.readFileSync(path.join(wrapBuildDir, "wrap.info")), - fs.readFileSync(path.join(wrapBuildDir, "wrap.wasm")) - ); - }); - - it("can resolve URI with plugin extension", async () => { - const sourceUri = Uri.from(`test/from`); - const redirectedUri = Uri.from("test/to"); - - const client = new PolywrapCoreClient({ - interfaces: new UriMap([ - [ - ExtendableUriResolver.defaultExtInterfaceUris[0], - [customPluginResolverUri], - ], - ]), - resolver: RecursiveResolver.from([ - StaticResolver.from([ - { - uri: customPluginResolverUri, - package: customPluginResolver, - }, - ]), - new ExtendableUriResolver(), - ]), - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ - uri: sourceUri, - resolutionContext, - }); - - await expectHistory( - resolutionContext.getHistory(), - "can-resolve-uri" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "uri") { - fail("Expected a URI, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual(redirectedUri.uri); - }); - - it("can resolve a package with plugin extension", async () => { - const sourceUri = Uri.from(`test/package`); - const redirectedUri = Uri.from("test/package"); - - const client = new PolywrapCoreClient({ - interfaces: new UriMap([ - [ - ExtendableUriResolver.defaultExtInterfaceUris[0], - [customPluginResolverUri], - ], - ]), - resolver: RecursiveResolver.from([ - StaticResolver.from([ - { - uri: customPluginResolverUri, - package: customPluginResolver, - }, - ]), - new ExtendableUriResolver(), - ]), - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ - uri: sourceUri, - resolutionContext, - }); - - await expectHistory( - resolutionContext.getHistory(), - "can-resolve-package" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "package") { - fail("Expected a package, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual(redirectedUri.uri); - }); - - it("shows the plugin resolver extension error", async () => { - const sourceUri = Uri.from(`test/error`); - - const client = new PolywrapCoreClient({ - interfaces: new UriMap([ - [ - ExtendableUriResolver.defaultExtInterfaceUris[0], - [customPluginResolverUri], - ], - ]), - resolver: RecursiveResolver.from([ - StaticResolver.from([ - { - uri: customPluginResolverUri, - package: customPluginResolver, - }, - ]), - new ExtendableUriResolver(), - ]), - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ - uri: sourceUri, - resolutionContext, - }); - - await expectHistory( - resolutionContext.getHistory(), - "shows-plugin-extension-error" - ); - - if (result.ok) { - fail("Expected an error, received: " + result.value.type); - } - - expect((result.error as Error)?.message).toEqual( - `Test error -code: 51 WRAPPER INVOKE ABORTED -uri: wrap://package/test-resolver -method: tryResolveUri -args: { - "authority": "test", - "path": "error" -} ` - ); - }); - - it("does not resolve a URI when not a match with plugin extension", async () => { - const uri = new Uri("test/not-a-match"); - - const client = new PolywrapCoreClient({ - interfaces: new UriMap([ - [ - ExtendableUriResolver.defaultExtInterfaceUris[0], - [customPluginResolverUri], - ], - ]), - resolver: RecursiveResolver.from([ - StaticResolver.from([ - { - uri: customPluginResolverUri, - package: customPluginResolver, - }, - ]), - new ExtendableUriResolver(), - ]), - }); - - const resolutionContext = new UriResolutionContext(); - const result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "not-a-match" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "uri") { - fail("Expected a uri, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/not-a-match"); - }); - - it("can resolve URI with wasm extension", async () => { - const sourceUri = Uri.from(`test/from`); - const redirectedUri = Uri.from("test/to"); - - const client = new PolywrapCoreClient({ - interfaces: new UriMap([ - [ - ExtendableUriResolver.defaultExtInterfaceUris[0], - [customPluginResolverUri], - ], - ]), - resolver: RecursiveResolver.from([ - StaticResolver.from([ - { - uri: customPluginResolverUri, - package: testResolverPackage, - }, - ]), - new ExtendableUriResolver(), - ]), - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ - uri: sourceUri, - resolutionContext, - }); - - await expectHistory( - resolutionContext.getHistory(), - "can-resolve-uri" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "uri") { - fail("Expected a URI, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual(redirectedUri.uri); - }); - - it("can resolve a package with wasm extension", async () => { - const sourceUri = Uri.from(`test/package`); - const redirectedUri = Uri.from("test/package"); - - const client = new PolywrapCoreClient({ - interfaces: new UriMap([ - [ - ExtendableUriResolver.defaultExtInterfaceUris[0], - [customPluginResolverUri], - ], - ]), - resolver: RecursiveResolver.from([ - StaticResolver.from([ - { - uri: customPluginResolverUri, - package: testResolverPackage, - }, - ]), - new ExtendableUriResolver(), - ]), - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ - uri: sourceUri, - resolutionContext, - }); - - await expectHistory( - resolutionContext.getHistory(), - "can-resolve-package" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "package") { - fail("Expected a package, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual(redirectedUri.uri); - }); - - it("shows the wasm resolver extension error", async () => { - const sourceUri = Uri.from(`test/error`); - - const client = new PolywrapCoreClient({ - interfaces: new UriMap([ - [ - ExtendableUriResolver.defaultExtInterfaceUris[0], - [customPluginResolverUri], - ], - ]), - resolver: RecursiveResolver.from([ - StaticResolver.from([ - { - uri: customPluginResolverUri, - package: testResolverPackage, - }, - ]), - new ExtendableUriResolver(), - ]), - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ - uri: sourceUri, - resolutionContext, - }); - - await expectHistory( - resolutionContext.getHistory(), - "shows-wasm-extension-error" - ); - - if (result.ok) { - fail("Expected an error, received: " + result.value.type); - } - - expect((result.error as Error)?.message).toEqual( - `__wrap_abort: Test error -code: 51 WRAPPER INVOKE ABORTED -uri: wrap://package/test-resolver -method: tryResolveUri -args: { - "authority": "test", - "path": "error" -} -source: { file: "src/wrap/module/wrapped.rs", row: 35, col: 21 }` - ); - }); - - it("does not resolve a URI when not a match with wasm extension", async () => { - const uri = new Uri("test/not-a-match"); - - const client = new PolywrapCoreClient({ - interfaces: new UriMap([ - [ - ExtendableUriResolver.defaultExtInterfaceUris[0], - [customPluginResolverUri], - ], - ]), - resolver: RecursiveResolver.from([ - StaticResolver.from([ - { - uri: customPluginResolverUri, - package: testResolverPackage, - }, - ]), - new ExtendableUriResolver(), - ]), - }); - - const resolutionContext = new UriResolutionContext(); - const result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "not-a-match" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "uri") { - fail("Expected a uri, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/not-a-match"); - }); - - it("does not cause infinite recursion when resolved at runtime when an extension is not found", async () => { - const undefinedResolverUri = Uri.from("test/undefined-resolver"); - - const client = new PolywrapCoreClient({ - interfaces: new UriMap([ - [ - ExtendableUriResolver.defaultExtInterfaceUris[0], - [undefinedResolverUri], - ], - ]), - resolver: RecursiveResolver.from([new ExtendableUriResolver()]), - }); - - const resolutionContext = new UriResolutionContext(); - const result = await client.tryResolveUri({ - uri: Uri.from("test/not-a-match"), - resolutionContext, - }); - - await expectHistory( - resolutionContext.getHistory(), - "not-found-extension" - ); - - if (result.ok) { - fail("Resoulution should have failed"); - } - - expect(result.error).toEqual( - "While resolving wrap://test/not-a-match with URI resolver extension wrap://test/undefined-resolver, the extension could not be fully resolved. Last tried URI is wrap://test/undefined-resolver" - ); - }); -}); diff --git a/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/.gitignore b/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/.gitignore deleted file mode 100644 index ec0cd1fa68..0000000000 --- a/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/.gitignore +++ /dev/null @@ -1,6 +0,0 @@ -build -node_modules -wrap -.polywrap -target -workflows/output.json diff --git a/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/Cargo.toml b/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/Cargo.toml deleted file mode 100644 index 5e384b68a8..0000000000 --- a/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/Cargo.toml +++ /dev/null @@ -1,20 +0,0 @@ -[package] -name = "test-uri-resolver-wasm-rs" -version = "0.1.0" -description = "A URI resolver extension wrapper for testing" -authors = ["Polywrap"] -repository = "https://github.com/polywrap/monorepo" -license = "MIT" -edition = "2021" - -[dependencies] -polywrap-wasm-rs = { version = "0.10.0-pre.8" } -serde = { version = "1.0", features = ["derive"] } - -[lib] -crate-type = ["cdylib"] - -[profile.release] -opt-level = 's' -lto = true -panic = 'abort' diff --git a/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/polywrap.build.yaml b/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/polywrap.build.yaml deleted file mode 100644 index 6e5d4c2c8a..0000000000 --- a/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/polywrap.build.yaml +++ /dev/null @@ -1,4 +0,0 @@ -format: 0.2.0 -linked_packages: - - name: "polywrap-wasm-rs" - path: ../../../../../../wasm/rs/ \ No newline at end of file diff --git a/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/polywrap.graphql b/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/polywrap.graphql deleted file mode 100644 index 41ff37c506..0000000000 --- a/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/polywrap.graphql +++ /dev/null @@ -1,5 +0,0 @@ -#import { Module } into UriResolver from "wrap://ens/wraps.eth:uri-resolver-ext@1.1.0" - -type Module implements UriResolver_Module {} - -type Env {} diff --git a/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/polywrap.yaml b/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/polywrap.yaml deleted file mode 100644 index 752f451f1d..0000000000 --- a/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/polywrap.yaml +++ /dev/null @@ -1,9 +0,0 @@ -format: 0.2.0 -project: - name: test-uri-resolver-ext - type: wasm/rust -source: - module: ./Cargo.toml - schema: ./polywrap.graphql -extensions: - build: ./polywrap.build.yaml diff --git a/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/src/lib.rs b/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/src/lib.rs deleted file mode 100644 index 1a5d73bd42..0000000000 --- a/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/src/lib.rs +++ /dev/null @@ -1,39 +0,0 @@ -pub mod wrap; -use wrap::{ - *, - env::{Env}, - imported::{ - ArgsGetFile, ArgsTryResolveUri, - } -}; - -impl ModuleTrait for Module { - fn try_resolve_uri( - args: ArgsTryResolveUri, - _env: Option - ) -> Result, String> { - if args.authority != "test" { - return Ok(None); - } - - match args.path.as_str() { - "from" => Ok(Some(UriResolverMaybeUriOrManifest { - manifest: None, - uri: Some("test/to".to_string()) - })), - "package" => Ok(Some(UriResolverMaybeUriOrManifest { - manifest: Some(vec![0]), - uri: None - })), - "error" => Err("Test error".to_string()), - _ => Ok(None) - } - } - - fn get_file( - _args: ArgsGetFile, - _env: Option - ) -> Result>, String> { - return Ok(None); - } -} \ No newline at end of file diff --git a/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/tsconfig.json b/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/tsconfig.json deleted file mode 100644 index 75bfa86f2e..0000000000 --- a/packages/js/uri-resolver-extensions/src/__tests__/wrappers/test-resolver/tsconfig.json +++ /dev/null @@ -1,28 +0,0 @@ -{ - "compilerOptions": { - "lib": [ - "es2015", - "es5", - "dom" - ], - "esModuleInterop": true, - "outDir": "build", - "moduleResolution": "node", - "declaration": true, - "preserveSymlinks": true, - "preserveWatchOutput": true, - "pretty": false, - "forceConsistentCasingInFileNames": true, - "noFallthroughCasesInSwitch": true, - "noImplicitAny": true, - "noImplicitReturns": true, - "noUnusedLocals": true, - "module": "commonjs", - "sourceMap": true, - "target": "es5", - "resolveJsonModule": true, - "strictNullChecks": true, - "experimentalDecorators": true - }, - "typeAcquisition": { "include": ["jest"] } -} \ No newline at end of file diff --git a/packages/js/uri-resolver-extensions/src/index.ts b/packages/js/uri-resolver-extensions/src/index.ts deleted file mode 100644 index 7b415f8611..0000000000 --- a/packages/js/uri-resolver-extensions/src/index.ts +++ /dev/null @@ -1,3 +0,0 @@ -export * from "./ExtendableUriResolver"; -export * from "./UriResolverExtensionFileReader"; -export * from "./UriResolverWrapper"; diff --git a/packages/js/uri-resolver-extensions/tsconfig.build.json b/packages/js/uri-resolver-extensions/tsconfig.build.json deleted file mode 100644 index 77aadfdd2f..0000000000 --- a/packages/js/uri-resolver-extensions/tsconfig.build.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "extends": "./tsconfig.json", - "include": [ - "./src/**/*.ts" - ], - "exclude": [ - "./src/**/__tests__" - ] -} diff --git a/packages/js/uri-resolver-extensions/tsconfig.json b/packages/js/uri-resolver-extensions/tsconfig.json deleted file mode 100644 index 5d37204c00..0000000000 --- a/packages/js/uri-resolver-extensions/tsconfig.json +++ /dev/null @@ -1,10 +0,0 @@ -{ - "extends": "../../../tsconfig", - "compilerOptions": { - "outDir": "build" - }, - "include": [ - "./src/**/*.ts" - ], - "exclude": [] -} diff --git a/packages/js/uri-resolvers/.gitignore b/packages/js/uri-resolvers/.gitignore deleted file mode 100644 index 24fcff1e7b..0000000000 --- a/packages/js/uri-resolvers/.gitignore +++ /dev/null @@ -1,4 +0,0 @@ -readme/sub-sections/injected -/examples/**/*.d.ts -/examples/**/*.js -/examples/**/*.js.map diff --git a/packages/js/uri-resolvers/README.md b/packages/js/uri-resolvers/README.md deleted file mode 100644 index 5ccdd0eb14..0000000000 --- a/packages/js/uri-resolvers/README.md +++ /dev/null @@ -1,889 +0,0 @@ -# @polywrap/uri-resolvers - -npm - - -
-
-URI resolvers to customize URI resolution in the Polywrap Client. - -## Installation - -```bash -npm install --save @polywrap/uri-resolvers-js -``` - -## Usage - -This example is similar to the default resolver used by the ClientConfigBuilder in the @polywrap/client-config-builder-js package. - -```ts - const resolver = RecursiveResolver.from( - WrapperCacheResolver.from( - [ - StaticResolver.from([ - ...redirects, - ...wrappers, - ...packages, - ]), - ], - new WrapperCache() - ) - ); -``` - -# Reference - -## UriResolverAggregatorBase -```ts -/** - * Abstract class for IUriResolver implementations that aggregate multiple resolvers. - * The UriResolverAggregatorBase class attempts to resolve a URI by sequentially - * attempting resolution with each of its composite resolvers. - * */ -export abstract class UriResolverAggregatorBase< - TResolutionError = undefined, - TGetResolversError = undefined -> implements IUriResolver -``` - -### Methods - -#### getUriResolvers -```ts - /** - * Get a list of URI Resolvers - * - * @param uri - the URI to query for resolvers - * @param client - a CoreClient instance that can be used to make an invocation - * @param resolutionContext - a resolution context to update when resolving URIs - * - * @returns a list of IUriResolver or an error - * */ - abstract getUriResolvers( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise[], TGetResolversError>>; -``` - -#### tryResolveUri -```ts - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * Attempts to resolve the URI using each of the aggregated resolvers sequentially. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise< - Result - > -``` - -#### getStepDescription (protected) -```ts - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @param uri - the URI being resolved - * @param result - the result of a resolution attempt - * - * @returns text describing the URI resolution step - * */ - protected abstract getStepDescription( - uri: Uri, - result: Result - ): string; -``` - -#### tryResolveUriWithResolvers (protected) -```ts - /** - * Using each of the aggregated resolvers, attempt to resolve a URI - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that can be used to make an invocation - * @param resolvers - a list of IUriResolver implementations - * @param resolutionContext - a resolution context to update when resolving URIs - * - * @returns a URI, a Wrap Package, or a Wrapper (or an error) - * */ - protected async tryResolveUriWithResolvers( - uri: Uri, - client: CoreClient, - resolvers: IUriResolver[], - resolutionContext: IUriResolutionContext - ): Promise> -``` - -## UriResolverAggregator -```ts -/** - * An implementation of UriResolverAggregatorBase - */ -export class UriResolverAggregator< - TResolutionError = undefined, - TGetResolversError = undefined -> extends UriResolverAggregatorBase< - TResolutionError, - TGetResolversError -> -``` - -### Types - -#### GetResolversFunc -```ts -/** - * A function that returns a list of resolvers - * - * @param uri - the URI to query - * @param client - a CoreClient instance - * */ -export type GetResolversFunc = ( - uri: Uri, - client: CoreClient -) => Promise[]>; -``` - -#### GetResolversWithErrorFunc -```ts -/** - * A function that returns a list of resolvers or an error - * - * @param uri - the URI to query - * @param client - a CoreClient instance - * */ -export type GetResolversWithErrorFunc = ( - uri: Uri, - client: CoreClient -) => Promise[], TError>>; -``` - -### Methods - -#### constructor -```ts - /** - * Creates a UriResolverAggregator from a list of resolvers, or from a function - * that returns a list of resolvers - * */ - constructor(resolvers: UriResolverLike[], resolverName?: string); - constructor( - resolvers: ( - uri: Uri, - client: CoreClient - ) => Promise[], TGetResolversError>>, - resolverName?: string - ); - constructor(resolvers: GetResolversFunc, resolverName?: string); - constructor( - resolvers: - | UriResolverLike[] - | GetResolversFunc - | GetResolversWithErrorFunc, - private _resolverName?: string - ) -``` - -#### getUriResolvers -```ts - /** - * Get a list of URI Resolvers - * - * @param uri - the URI to query for resolvers - * @param client - a CoreClient instance that can be used to make an invocation - * - * @returns a list of IUriResolver or an error - * */ - async getUriResolvers( - uri: Uri, - client: CoreClient - ): Promise[], TGetResolversError>> -``` - -#### getStepDescription (protected) -```ts - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @returns text describing the URI resolution step - * */ - protected getStepDescription = (): string -``` - -## IWrapperCache -```ts -/** A Wrapper cache */ -export interface IWrapperCache { - /** get a Wrapper from the cache, given its URI index */ - get(uri: Uri): MaybeAsync; - - /** add a Wrapper to the cache, indexed by a URI */ - set(uri: Uri, wrapper: Wrapper): MaybeAsync; -} -``` - -## WrapperCache -```ts -/** - * A minimal implementation of IWrapperCache - * */ -export class WrapperCache implements IWrapperCache -``` - -### Methods - -#### get -```ts - /** get a Wrapper from the cache, given its URI index */ - get(uri: Uri): Wrapper | undefined -``` - -#### set -```ts - /** add a Wrapper to the cache, indexed by a URI */ - set(uris: Uri, wrapper: Wrapper): void -``` - -## WrapperCacheResolver -```ts -/** - * An IUriResolver implementation that caches wrappers once they are resolved. - * As it is a wrapper cache resolver, URI and package caching is outside of the scope for this resolver - * and can be achieved through other resolvers if necessary. - * The WrapperCacheResolver wraps an IUriResolver implementation and delegates resolution to it. - * */ -export class WrapperCacheResolver - implements IUriResolver -``` - -### constructor -```ts - /** - * Creates a WrapperCacheResolver - * - * @param _innerResolver - a resolver to delegate resolution to - * @param _cache - a wrapper cache - * */ - constructor( - private _innerResolver: IUriResolver, - private _cache: IWrapperCache - ) -``` - -### Methods - -#### from -```ts - /** - * Creates a WrapperCacheResolver from a resolver-like object - * - * @param innerResolver - a resolver-like item to delegate resolution to - * @param cache - a wrapper cache - * @param options - control wrapper manifest deserialization - * - * @returns a WrapperCacheResolver - * */ - static from( - innerResolver: UriResolverLike, - cache: IWrapperCache - ): WrapperCacheResolver -``` - -#### tryResolveUri -```ts - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * If successful, cache the result. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> -``` - -## getUriResolutionPath -```ts -/** - * Get a resolution path from the history of a URI resolution attempt - * - * @param history - the resolution context - * @returns the URI's resolution path - * */ -export const getUriResolutionPath = ( - history: IUriResolutionStep[] -): IUriResolutionStep[] -``` - -## InfiniteLoopError -```ts -/** - * Error used if the URI resolution path contains an infinite loop - * */ -export class InfiniteLoopError extends Error -``` - -### constructor -```ts - /** - * Create an InfiniteLoopError - * - * @param _uri - URI being resolved - * @param _history - URI resolution history - * */ - constructor( - private readonly _uri: Uri, - private readonly _history: IUriResolutionStep[] - ) -``` - -## ResolverWithHistory -```ts -/** An abstract IUriResolver implementation that updates the resolution context */ -export abstract class ResolverWithHistory - implements IUriResolver -``` - -### Methods - -#### tryResolveUri -```ts - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * Updates the resolution context with the result. - * - * @remarks - * This method calls the internal abstract method _tryResolveUri before - * updating the resolution context. Implementations are expect to place - * resolution logic in _tryResolveUri. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> -``` - -#### getStepDescription (protected) -```ts - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @param uri - the URI being resolved - * @param result - the result of a resolution attempt - * - * @returns text describing the URI resolution step - * */ - protected abstract getStepDescription( - uri: Uri, - result: Result - ): string; -``` - -#### _tryResolveUri (protected) -```ts - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * Updates the resolution context with the result. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - protected abstract _tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise>; -``` - -## ResolverWithLoopGuard -```ts -/** An IUriResolver implementation that prevents infinite loops in the resolution path. */ -export class ResolverWithLoopGuard - implements IUriResolver -``` - -### constructor -```ts - /** - * Construct a ResolverWithLoopGuard - * - * @param _resolver - a resolution to delegate resolution to - * */ - constructor(private _resolver: IUriResolver) -``` - -### Methods - -#### from -```ts - /** - * Create a ResolverWithLoopGuard from a resolver-like object - * - * @param resolver - a resolver-like item to delegate resolution to - * - * @returns a ResolverWithLoopGuard - * */ - static from( - resolver: UriResolverLike - ): ResolverWithLoopGuard -``` - -#### tryResolveUri -```ts - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * Ensures the URI is not caught in an infinite loop by checking if it is already resolving. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> -``` - -## PackageToWrapperResolver -```ts -/** - * An IUriResolver implementation that initalizes wrappers from resolved packages. - * The PackageToWrapperResolver wraps an IUriResolver implementation and delegates resolution to it. - * */ -export class PackageToWrapperResolver - implements IUriResolver -``` - -### constructor -```ts - /** - * Creates a PackageToWrapperResolver - * - * @param _innerResolver - a resolver to delegate resolution to - * @param _options - control wrapper manifest deserialization - * */ - constructor( - private _innerResolver: IUriResolver, - private _options?: { - deserializeManifestOptions?: DeserializeManifestOptions; - } - ) -``` - -### Methods - -#### from -```ts - /** - * Creates a PackageToWrapperResolver from a resolver-like object - * - * @param innerResolver - a resolver-like item to delegate resolution to - * @param options - control wrapper manifest deserialization - * - * @returns a PackageToWrapperResolver - * */ - static from( - innerResolver: UriResolverLike, - options?: { deserializeManifestOptions?: DeserializeManifestOptions } - ): PackageToWrapperResolver -``` - -#### tryResolveUri -```ts - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * If successful, cache the result. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> -``` - -## UriResolutionResult -```ts -/** Factory for creating Result from URI resolution output */ -export class UriResolutionResult -``` - -### Methods - -#### ok -```ts - /** Returns a Result with `ok` set to true */ - static ok(uri: Uri): Result; - static ok( - uri: Uri, - wrapPackage: IWrapPackage - ): Result; - static ok( - uri: Uri, - wrapper: Wrapper - ): Result; - static ok( - uriPackageOrWrapper: UriPackageOrWrapper - ): Result; - static ok( - uriPackageOrWrapper: Uri | UriPackageOrWrapper, - packageOrWrapper?: IWrapPackage | Wrapper - ): Result -``` - -#### err -```ts - /** Returns a Result with `ok` set to false */ - static err( - error: TError - ): Result -``` - -## UriResolver -```ts -/** An IUriResolver factory */ -export class UriResolver -``` - -### Methods - -#### from -```ts - /** - * Create an IUriResolver instance - * - * @param resolverLike - an object that can be transformed into a resolver - * @param resolverName - a name to assign to the resolver in resolution history output - * */ - static from( - resolverLike: UriResolverLike, - resolverName?: string - ): IUriResolver -``` - -## UriResolverLike -```ts -/** An UriResolverLike can be one of three things: - * - An IUriResolver - * - An object that can be transformed into a static IUriResolver - * - An array of UriResolverLike - * */ -export type UriResolverLike = - | IUriResolver - | IUriRedirect - | IUriPackage - | IUriWrapper - | UriResolverLike[]; -``` - -## PackageResolver -```ts -/** - * A Uri Resolver that resolves to an embedded wrap package and correctly updates - * the resolution history. - * */ -export class PackageResolver extends ResolverWithHistory -``` - -### constructor -```ts - /** - * Construct a PackageResolver - * - * @param _uri - the URI to redirect to the wrap package - * @param wrapPackage - a wrap package - * */ - constructor(private _uri: Uri, private wrapPackage: IWrapPackage) -``` - -### Methods - -#### getStepDescription (protected) -```ts - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @returns text describing the URI resolution step - * */ - protected getStepDescription = (): string -``` - -#### _tryResolveUri (protected) -```ts - /** - * Resolve a URI to a wrap package - * - * @param uri - the URI to resolve - * @returns A Promise with a Result containing a wrap package if successful - */ - protected async _tryResolveUri( - uri: Uri - ): Promise> -``` - -## RedirectResolver -```ts -/** - * A Uri Resolver that resolves to a new URI and correctly updates the - * resolution history. - * */ -export class RedirectResolver< - TUri extends string | Uri = string -> extends ResolverWithHistory -``` - -### constructor -```ts - /** - * Construct a RedirectResolver - * - * @param from - the URI to redirect from - * @param to - the URI to redirect to - * */ - constructor(from: TUri, to: TUri) -``` - -### Methods - -#### getStepDescription (protected) -```ts - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @returns text describing the URI resolution step - * */ - protected getStepDescription = (): string -``` - -#### _tryResolveUri (protected) -```ts - /** - * Resolve a URI to a new URI - * - * @param uri - the URI to resolve - * @returns A Promise with a Result containing a URI if successful - */ - protected async _tryResolveUri( - uri: Uri - ): Promise> -``` - -## WrapperResolver -```ts -/** - * A Uri Resolver that resolves to an embedded wrapper and correctly updates - * the resolution history. - * */ -export class WrapperResolver extends ResolverWithHistory -``` - -### constructor -```ts - /** - * Construct a WrapperResolver - * - * @param _uri - the URI to redirect to the wrapper instance - * @param _wrapper - a wrapper - * */ - constructor(private _uri: Uri, private _wrapper: Wrapper) -``` - -### Methods - -#### getStepDescription (protected) -```ts - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @returns text describing the URI resolution step - * */ - protected getStepDescription = (): string -``` - -#### _tryResolveUri -```ts - /** - * Resolve a URI to a wrapper - * - * @param uri - the URI to resolve - * @returns A Promise with a Result containing a wrapper if successful - */ - protected async _tryResolveUri( - uri: Uri - ): Promise> -``` - -## StaticResolver -```ts -/** - * An IUriResolver implementation that efficiently delegates URI resolution to - * static resolvers--i.e. those that resolve to embedded URIs, Wrappers, and Packages - * */ -export class StaticResolver - implements IUriResolver -``` - -### constructor -```ts - /** - * Construct a Static Resolver - * - * @param uriMap - a mapping of URI to embedded URI, package, or wrapper - * */ - constructor(public uriMap: Map) -``` - -### Methods - -#### from -```ts - /** - * Create a StaticResolver from a static-resolver-like object - * - * @param staticResolverLikes - an array of resolver-like objects to delegate resolution to - * - * @returns a StaticResolver - * */ - static from( - staticResolverLikes: UriResolverLike[] - ): StaticResolver -``` - -#### tryResolveUri -```ts - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * - * @param uri - the URI to resolve - * @param _ - not used - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - _: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> -``` - -## StaticResolverLike -```ts -/** A StaticResolverLike can be one of two things: - * - An object that can be transformed into a static IUriResolver - * - An array of StaticResolverLike - * */ -export type StaticResolverLike = - | IUriRedirect - | IUriPackage - | IUriWrapper - | StaticResolverLike[]; -``` - -## RequestSynchronizerResolver -```ts -/* Uri resolver that synchronizes requests to the same URI - * Multiple requests to the same URI will be resolved only once - * and the result will be cached for subsequent requests (only for the duration of that first request) - * Can use the `shouldIgnoreCache` option to determine whether to ignore the cached request in case of an error - * (default is to use the cache) - */ -export class RequestSynchronizerResolver - implements IUriResolver -``` - -### constructor -```ts - /** - * Construct a RequestSynchronizerResolver - * - * @param resolverToSynchronize - the inner resolve whose resolution will be synchronized - * @param options - the optional options containing the `shouldIgnoreCache` error handler - * */ - constructor( - private resolverToSynchronize: IUriResolver, - private options?: { - shouldIgnoreCache?: (error: TError | undefined) => boolean; - } - ) -``` - -### Methods - -#### from -```ts - /** - * Create a RequestSynchronizerResolver from a static-resolver-like object - * - * @param resolver - a resolver-like object whose resolution will be synchronized - * @param options - the optional options containing the `shouldIgnoreCache` error handler - * - * @returns a RequestSynchronizerResolver - * */ - static from( - resolver: UriResolverLike, - options?: { - shouldIgnoreCache?: (error: TResolverError | undefined) => boolean; - } - ): RequestSynchronizerResolver -``` - -#### tryResolveUri -```ts - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * Attempts to resolve the URI using each of the aggregated resolvers sequentially. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> -``` - - -## Development - -This package is open-source. It lives within the [Polywrap toolchain monorepo](https://github.com/polywrap/toolchain/tree/origin/packages/js/uri-resolvers). Contributions from the community are welcomed! - -### Build -```bash -nvm use && yarn install && yarn build -``` - -### Test -```bash -yarn test -`` \ No newline at end of file diff --git a/packages/js/uri-resolvers/examples/quickstart.ts b/packages/js/uri-resolvers/examples/quickstart.ts deleted file mode 100644 index 4f70ac377c..0000000000 --- a/packages/js/uri-resolvers/examples/quickstart.ts +++ /dev/null @@ -1,32 +0,0 @@ -import { IUriResolver } from "@polywrap/core-js"; -import { - PackageResolver, - WrapperCacheResolver, - RecursiveResolver, - RedirectResolver, - StaticResolver, - WrapperCache, -} from "../build"; -import { WrapperResolver } from "../build/wrappers"; - -export function example(): IUriResolver { - const redirects: RedirectResolver[] = []; - const wrappers: WrapperResolver[] = []; - const packages: PackageResolver[] = []; - // $start: quickstart-example - const resolver = RecursiveResolver.from( - WrapperCacheResolver.from( - [ - StaticResolver.from([ - ...redirects, - ...wrappers, - ...packages, - ]), - ], - new WrapperCache() - ) - ); - // $end - - return resolver; -} diff --git a/packages/js/uri-resolvers/examples/tsconfig.examples.json b/packages/js/uri-resolvers/examples/tsconfig.examples.json deleted file mode 100644 index f37de53612..0000000000 --- a/packages/js/uri-resolvers/examples/tsconfig.examples.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "extends": "../tsconfig.json", - "include": [ - "./**/*.ts" - ], -} \ No newline at end of file diff --git a/packages/js/uri-resolvers/jest.config.js b/packages/js/uri-resolvers/jest.config.js deleted file mode 100644 index b156259895..0000000000 --- a/packages/js/uri-resolvers/jest.config.js +++ /dev/null @@ -1,12 +0,0 @@ -module.exports = { - collectCoverage: true, - preset: 'ts-jest', - testEnvironment: 'node', - testMatch: ["**/?(*.)+(spec|test).[jt]s?(x)"], - modulePathIgnorePatterns: ['./src/__tests__/apis'], - globals: { - 'ts-jest': { - diagnostics: false - } - } -}; diff --git a/packages/js/uri-resolvers/package.json b/packages/js/uri-resolvers/package.json deleted file mode 100644 index c2decb9e27..0000000000 --- a/packages/js/uri-resolvers/package.json +++ /dev/null @@ -1,46 +0,0 @@ -{ - "name": "@polywrap/uri-resolvers-js", - "description": "Polywrap URI resolvers", - "version": "0.10.0", - "license": "MIT", - "repository": { - "type": "git", - "url": "https://github.com/polywrap/monorepo.git" - }, - "main": "build/index.js", - "files": [ - "build" - ], - "scripts": { - "build": "yarn build:fast", - "build:docs": "yarn build:snippets && yarn build:readme", - "build:fast": "rimraf ./build && tsc --project tsconfig.build.json", - "lint": "eslint --color -c ../../../.eslintrc.js src/", - "test": "jest --passWithNoTests --runInBand --verbose", - "test:watch": "yarn test -- --watch", - "build:snippets": "tsc --project ./examples/tsconfig.examples.json", - "build:readme:subsections": "yarn doc-snippets combine -c ./readme/config/sub-sections.json", - "build:readme:final": "yarn doc-snippets combine -c ./readme/config/final.json", - "build:readme": "yarn build:readme:subsections && yarn build:readme:final" - }, - "dependencies": { - "@polywrap/core-js": "0.10.0", - "@polywrap/result": "0.10.0", - "@polywrap/wrap-manifest-types-js": "0.10.0" - }, - "devDependencies": { - "@polywrap/client-config-builder-js": "0.10.0", - "@polywrap/core-client-js": "0.10.0", - "@polywrap/plugin-js": "0.10.0", - "@types/jest": "26.0.8", - "doc-snippets": "~1.0.0", - "jest": "26.6.3", - "rimraf": "3.0.2", - "ts-jest": "26.5.4", - "ts-node": "10.9.1", - "typescript": "4.9.5" - }, - "publishConfig": { - "access": "public" - } -} diff --git a/packages/js/uri-resolvers/readme/README.md b/packages/js/uri-resolvers/readme/README.md deleted file mode 100644 index ae7c2d188d..0000000000 --- a/packages/js/uri-resolvers/readme/README.md +++ /dev/null @@ -1,46 +0,0 @@ -# @polywrap/uri-resolvers - -npm - - -
-
-URI resolvers to customize URI resolution in the Polywrap Client. - -## Installation - -```bash -npm install --save @polywrap/uri-resolvers-js -``` - -## Usage - -This example is similar to the default resolver used by the ClientConfigBuilder in the @polywrap/client-config-builder-js package. - -```ts -$snippet: quickstart-example -``` - -# Reference - -$snippet: aggregator.md - -$snippet: cache.md - -$snippet: helpers.md - -$snippet: static.md - -## Development - -This package is open-source. It lives within the [Polywrap toolchain monorepo](https://github.com/polywrap/toolchain/tree/origin/packages/js/uri-resolvers). Contributions from the community are welcomed! - -### Build -```bash -nvm use && yarn install && yarn build -``` - -### Test -```bash -yarn test -`` \ No newline at end of file diff --git a/packages/js/uri-resolvers/readme/config/final.json b/packages/js/uri-resolvers/readme/config/final.json deleted file mode 100644 index 3aa6fd6080..0000000000 --- a/packages/js/uri-resolvers/readme/config/final.json +++ /dev/null @@ -1,42 +0,0 @@ -{ - "doc-snippets": { - "extract": { - "include": [ - "./src/**/*.{ts,tsx,json,yaml,txt,md,graphql,cue}", - "./examples/**/*.{ts,tsx,json,yaml,txt,md,graphql,cue}", - "./readme/sub-sections/injected/**/*.{ts,tsx,json,yaml,txt,md,graphql,cue}" - ], - "ignore": [ - "./**/node_modules/**", - "./**/.polywrap/**", - "./**/__tests__/**" - ], - "dir": "./" - }, - "inject": { - "dir": "./readme", - "include": "./README.md" - }, - "startTokens": [ - { - "pattern": "$start: ", - "inline": false - }, - { - "pattern": "/* $: {SNIPPET_NAME} */", - "inline": true - } - ], - "endTokens": [ - { - "pattern": "$end", - "inline": false - }, - { - "pattern": "/* $ */", - "inline": true - } - ], - "outputDir": "./" - } -} \ No newline at end of file diff --git a/packages/js/uri-resolvers/readme/config/sub-sections.json b/packages/js/uri-resolvers/readme/config/sub-sections.json deleted file mode 100644 index cfde3d90eb..0000000000 --- a/packages/js/uri-resolvers/readme/config/sub-sections.json +++ /dev/null @@ -1,38 +0,0 @@ -{ - "doc-snippets": { - "extract": { - "include": "./**/*.{ts,tsx,json,yaml,txt,md,graphql,cue}", - "ignore": [ - "./**/node_modules/**", - "./**/.polywrap/**", - "./**/__tests__/**" - ], - "dir": "./src" - }, - "inject": { - "dir": "./readme/sub-sections/base", - "include": "./**/*.md" - }, - "startTokens": [ - { - "pattern": "$start: ", - "inline": false - }, - { - "pattern": "/* $: {SNIPPET_NAME} */", - "inline": true - } - ], - "endTokens": [ - { - "pattern": "$end", - "inline": false - }, - { - "pattern": "/* $ */", - "inline": true - } - ], - "outputDir": "./readme/sub-sections/injected" - } -} \ No newline at end of file diff --git a/packages/js/uri-resolvers/readme/sub-sections/base/aggregator.md b/packages/js/uri-resolvers/readme/sub-sections/base/aggregator.md deleted file mode 100644 index d685309743..0000000000 --- a/packages/js/uri-resolvers/readme/sub-sections/base/aggregator.md +++ /dev/null @@ -1,62 +0,0 @@ -$start: aggregator.md -## UriResolverAggregatorBase -```ts -$snippet: UriResolverAggregatorBase -``` - -### Methods - -#### getUriResolvers -```ts -$snippet: UriResolverAggregatorBase-getUriResolvers -``` - -#### tryResolveUri -```ts -$snippet: UriResolverAggregatorBase-tryResolveUri -``` - -#### getStepDescription (protected) -```ts -$snippet: UriResolverAggregatorBase-getStepDescription -``` - -#### tryResolveUriWithResolvers (protected) -```ts -$snippet: UriResolverAggregatorBase-tryResolveUriWithResolvers -``` - -## UriResolverAggregator -```ts -$snippet: UriResolverAggregator -``` - -### Types - -#### GetResolversFunc -```ts -$snippet: UriResolverAggregator-GetResolversFunc -``` - -#### GetResolversWithErrorFunc -```ts -$snippet: UriResolverAggregator-GetResolversWithErrorFunc -``` - -### Methods - -#### constructor -```ts -$snippet: UriResolverAggregator-constructor -``` - -#### getUriResolvers -```ts -$snippet: UriResolverAggregator-getUriResolvers -``` - -#### getStepDescription (protected) -```ts -$snippet: UriResolverAggregator-getStepDescription -``` -$end \ No newline at end of file diff --git a/packages/js/uri-resolvers/readme/sub-sections/base/cache.md b/packages/js/uri-resolvers/readme/sub-sections/base/cache.md deleted file mode 100644 index 1102ce92a7..0000000000 --- a/packages/js/uri-resolvers/readme/sub-sections/base/cache.md +++ /dev/null @@ -1,45 +0,0 @@ -$start: cache.md -## IWrapperCache -```ts -$snippet: IWrapperCache -``` - -## WrapperCache -```ts -$snippet: WrapperCache -``` - -### Methods - -#### get -```ts -$snippet: WrapperCache-get -``` - -#### set -```ts -$snippet: WrapperCache-set -``` - -## WrapperCacheResolver -```ts -$snippet: WrapperCacheResolver -``` - -### constructor -```ts -$snippet: WrapperCacheResolver-constructor -``` - -### Methods - -#### from -```ts -$snippet: WrapperCacheResolver-from -``` - -#### tryResolveUri -```ts -$snippet: WrapperCacheResolver-tryResolveUri -``` -$end diff --git a/packages/js/uri-resolvers/readme/sub-sections/base/helpers.md b/packages/js/uri-resolvers/readme/sub-sections/base/helpers.md deleted file mode 100644 index cc1dcd997b..0000000000 --- a/packages/js/uri-resolvers/readme/sub-sections/base/helpers.md +++ /dev/null @@ -1,116 +0,0 @@ -$start: helpers.md -## getUriResolutionPath -```ts -$snippet: getUriResolutionPath -``` - -## InfiniteLoopError -```ts -$snippet: InfiniteLoopError -``` - -### constructor -```ts -$snippet: InfiniteLoopError-constructor -``` - -## ResolverWithHistory -```ts -$snippet: ResolverWithHistory -``` - -### Methods - -#### tryResolveUri -```ts -$snippet: ResolverWithHistory-tryResolveUri -``` - -#### getStepDescription (protected) -```ts -$snippet: ResolverWithHistory-getStepDescription -``` - -#### _tryResolveUri (protected) -```ts -$snippet: ResolverWithHistory-_tryResolveUri -``` - -## ResolverWithLoopGuard -```ts -$snippet: ResolverWithLoopGuard -``` - -### constructor -```ts -$snippet: ResolverWithLoopGuard-constructor -``` - -### Methods - -#### from -```ts -$snippet: ResolverWithLoopGuard-from -``` - -#### tryResolveUri -```ts -$snippet: ResolverWithLoopGuard-tryResolveUri -``` - -## PackageToWrapperResolver -```ts -$snippet: PackageToWrapperResolver -``` - -### constructor -```ts -$snippet: PackageToWrapperResolver-constructor -``` - -### Methods - -#### from -```ts -$snippet: PackageToWrapperResolver-from -``` - -#### tryResolveUri -```ts -$snippet: PackageToWrapperResolver-tryResolveUri -``` - -## UriResolutionResult -```ts -$snippet: UriResolutionResult -``` - -### Methods - -#### ok -```ts -$snippet: UriResolutionResult-ok -``` - -#### err -```ts -$snippet: UriResolutionResult-err -``` - -## UriResolver -```ts -$snippet: UriResolver -``` - -### Methods - -#### from -```ts -$snippet: UriResolver-from -``` - -## UriResolverLike -```ts -$snippet: UriResolverLike -``` -$end \ No newline at end of file diff --git a/packages/js/uri-resolvers/readme/sub-sections/base/static.md b/packages/js/uri-resolvers/readme/sub-sections/base/static.md deleted file mode 100644 index 830d275bd9..0000000000 --- a/packages/js/uri-resolvers/readme/sub-sections/base/static.md +++ /dev/null @@ -1,117 +0,0 @@ -$start: static.md -## PackageResolver -```ts -$snippet: PackageResolver -``` - -### constructor -```ts -$snippet: PackageResolver-constructor -``` - -### Methods - -#### getStepDescription (protected) -```ts -$snippet: PackageResolver-getStepDescription -``` - -#### _tryResolveUri (protected) -```ts -$snippet: PackageResolver-_tryResolveUri -``` - -## RedirectResolver -```ts -$snippet: RedirectResolver -``` - -### constructor -```ts -$snippet: RedirectResolver-constructor -``` - -### Methods - -#### getStepDescription (protected) -```ts -$snippet: RedirectResolver-getStepDescription -``` - -#### _tryResolveUri (protected) -```ts -$snippet: RedirectResolver-_tryResolveUri -``` - -## WrapperResolver -```ts -$snippet: WrapperResolver -``` - -### constructor -```ts -$snippet: WrapperResolver-constructor -``` - -### Methods - -#### getStepDescription (protected) -```ts -$snippet: WrapperResolver-getStepDescription -``` - -#### _tryResolveUri -```ts -$snippet: WrapperResolver-_tryResolveUri -``` - -## StaticResolver -```ts -$snippet: StaticResolver -``` - -### constructor -```ts -$snippet: StaticResolver-constructor -``` - -### Methods - -#### from -```ts -$snippet: StaticResolver-from -``` - -#### tryResolveUri -```ts -$snippet: StaticResolver-tryResolveUri -``` - -## StaticResolverLike -```ts -$snippet: StaticResolverLike -``` - -## RequestSynchronizerResolver -```ts -$snippet: RequestSynchronizerResolver -``` - -### constructor -```ts -$snippet: RequestSynchronizerResolver-constructor -``` - -### Methods - -#### from -```ts -$snippet: RequestSynchronizerResolver-from -``` - -#### tryResolveUri -```ts -$snippet: RequestSynchronizerResolver-tryResolveUri -``` - -$end diff --git a/packages/js/uri-resolvers/src/__tests__/helpers/expectHistory.ts b/packages/js/uri-resolvers/src/__tests__/helpers/expectHistory.ts deleted file mode 100644 index d90afdb969..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/helpers/expectHistory.ts +++ /dev/null @@ -1,22 +0,0 @@ -import { buildCleanUriHistory, IUriResolutionStep } from "@polywrap/core-js"; -import fs from "fs"; - -export const expectHistory = async ( - receivedHistory: IUriResolutionStep[] | undefined, - directory: string, - historyFileName: string -): Promise => { - if (!receivedHistory) { - fail("History is not defined"); - } - - const expectedCleanHistoryStr = await fs.promises.readFile( - `${__dirname}/../${directory}/histories/${historyFileName}.json`, - "utf-8" - ); - const expectedCleanHistory = JSON.stringify(JSON.parse(expectedCleanHistoryStr), null, 2); - - const receivedCleanHistory = JSON.stringify(buildCleanUriHistory(receivedHistory), null, 2); - - expect(receivedCleanHistory).toEqual(expectedCleanHistory); -}; \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/package-resolver/histories/can-resolve-a-package.json b/packages/js/uri-resolvers/src/__tests__/package-resolver/histories/can-resolve-a-package.json deleted file mode 100644 index 2b12faed7d..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/package-resolver/histories/can-resolve-a-package.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/package => Package (wrap://test/package) => package (wrap://test/package)" -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/package-resolver/histories/not-a-match.json b/packages/js/uri-resolvers/src/__tests__/package-resolver/histories/not-a-match.json deleted file mode 100644 index 5f57469959..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/package-resolver/histories/not-a-match.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/not-a-match => Package (wrap://test/package)" -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/package-resolver/package-resolver.spec.ts b/packages/js/uri-resolvers/src/__tests__/package-resolver/package-resolver.spec.ts deleted file mode 100644 index 923a5781d2..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/package-resolver/package-resolver.spec.ts +++ /dev/null @@ -1,72 +0,0 @@ -import { - Uri, - UriResolutionContext, -} from "@polywrap/core-js"; -import { expectHistory } from "../helpers/expectHistory"; -import { PolywrapCoreClient } from "@polywrap/core-client-js"; -import { PackageResolver } from "../../packages"; -import { PluginPackage } from "@polywrap/plugin-js"; - -jest.setTimeout(20000); - -describe("PackageResolver", () => { - it("can resolve a package", async () => { - const uri = new Uri("test/package"); - - const client = new PolywrapCoreClient({ - resolver: new PackageResolver( - Uri.from("test/package"), - PluginPackage.from(() => ({})) - ) - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "package-resolver", - "can-resolve-a-package", - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "package") { - fail("Expected a package, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/package"); - }); - - it("does not resolve a package when not a match", async () => { - const uri = new Uri("test/not-a-match"); - - const client = new PolywrapCoreClient({ - resolver: new PackageResolver( - Uri.from("test/package"), - PluginPackage.from(() => ({})) - ) - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "package-resolver", - "not-a-match", - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "uri") { - fail("Expected a uri, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/not-a-match"); - }); -}); diff --git a/packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/histories/package-to-wrapper.json b/packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/histories/package-to-wrapper.json deleted file mode 100644 index 56efd38f1a..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/histories/package-to-wrapper.json +++ /dev/null @@ -1,6 +0,0 @@ -[ - "wrap://test/package => PackageToWrapperResolver => wrapper (wrap://test/package)", - [ - "wrap://test/package => SimplePackageResolver => package (wrap://test/package)" - ] -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/histories/uri-to-uri.json b/packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/histories/uri-to-uri.json deleted file mode 100644 index 821bcddd07..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/histories/uri-to-uri.json +++ /dev/null @@ -1,6 +0,0 @@ -[ - "wrap://test/from => PackageToWrapperResolver => uri (wrap://test/to)", - [ - "wrap://test/from => SimplePackageResolver => uri (wrap://test/to)" - ] -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/histories/wrapper-to-wrapper.json b/packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/histories/wrapper-to-wrapper.json deleted file mode 100644 index 2b57ca4971..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/histories/wrapper-to-wrapper.json +++ /dev/null @@ -1,6 +0,0 @@ -[ - "wrap://test/wrapper => PackageToWrapperResolver => wrapper (wrap://test/wrapper)", - [ - "wrap://test/wrapper => SimplePackageResolver => wrapper (wrap://test/wrapper)" - ] -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/package-to-wrapper.spec.ts b/packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/package-to-wrapper.spec.ts deleted file mode 100644 index b19209bc39..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/package-to-wrapper-resolver/package-to-wrapper.spec.ts +++ /dev/null @@ -1,144 +0,0 @@ -import { - CoreClient, - IUriResolutionContext, - IUriResolver, - Result, - Uri, - UriPackageOrWrapper, - UriResolutionContext, -} from "@polywrap/core-js"; -import { expectHistory } from "../helpers/expectHistory"; -import { PolywrapCoreClient } from "@polywrap/core-client-js"; -import { PluginPackage } from "@polywrap/plugin-js"; -import { UriResolutionResult } from "../../helpers"; -import { PackageToWrapperResolver } from "../../packages"; - -jest.setTimeout(20000); - -class SimplePackageResolver implements IUriResolver { - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> { - let result: Result; - - switch (uri.uri) { - case "wrap://test/package": - result = UriResolutionResult.ok( - Uri.from("test/package"), - PluginPackage.from(() => ({})) - ); - break; - case "wrap://test/wrapper": - let wrapperResult = await PluginPackage.from( - () => ({}) - ).createWrapper(); - if (!wrapperResult.ok) { - throw wrapperResult.error; - } - - result = UriResolutionResult.ok( - Uri.from("test/wrapper"), - wrapperResult.value - ); - break; - case "wrap://test/from": - result = UriResolutionResult.ok(Uri.from("test/to")); - break; - default: - throw new Error(`Unexpected URI: ${uri.uri}`); - } - - resolutionContext.trackStep({ - sourceUri: uri, - result, - description: "SimplePackageResolver", - }); - - return result; - } -} - -describe("PackageToWrapperResolver", () => { - it("resolves a package to a wrapper", async () => { - const uri = new Uri("test/package"); - - const client = new PolywrapCoreClient({ - resolver: PackageToWrapperResolver.from(new SimplePackageResolver()), - }); - - let resolutionContext = new UriResolutionContext(); - const result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "package-to-wrapper-resolver", - "package-to-wrapper" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "wrapper") { - fail("Expected a wrapper, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/package"); - }); - - it("resolves a wrapper to a wrapper", async () => { - const uri = new Uri("test/wrapper"); - - const client = new PolywrapCoreClient({ - resolver: PackageToWrapperResolver.from(new SimplePackageResolver()), - }); - - let resolutionContext = new UriResolutionContext(); - const result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "package-to-wrapper-resolver", - "wrapper-to-wrapper" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "wrapper") { - fail("Expected a wrapper, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/wrapper"); - }); - - it("resolves a URI to a URI", async () => { - const uri = new Uri("test/from"); - - const client = new PolywrapCoreClient({ - resolver: PackageToWrapperResolver.from(new SimplePackageResolver()), - }); - - let resolutionContext = new UriResolutionContext(); - const result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "package-to-wrapper-resolver", - "uri-to-uri" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "uri") { - fail("Expected a URI, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/to"); - }); -}); diff --git a/packages/js/uri-resolvers/src/__tests__/recursive-resolver/histories/can-recursively-resolve-uri.json b/packages/js/uri-resolvers/src/__tests__/recursive-resolver/histories/can-recursively-resolve-uri.json deleted file mode 100644 index d982686b17..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/recursive-resolver/histories/can-recursively-resolve-uri.json +++ /dev/null @@ -1,6 +0,0 @@ -[ - "wrap://test/1 => SimpleRedirectResolver => uri (wrap://test/2)", - "wrap://test/2 => SimpleRedirectResolver => uri (wrap://test/3)", - "wrap://test/3 => SimpleRedirectResolver => uri (wrap://test/4)", - "wrap://test/4 => SimpleRedirectResolver" -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/recursive-resolver/histories/not-a-match.json b/packages/js/uri-resolvers/src/__tests__/recursive-resolver/histories/not-a-match.json deleted file mode 100644 index fa72a2d7d4..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/recursive-resolver/histories/not-a-match.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/not-a-match => SimpleRedirectResolver" -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/recursive-resolver/recursive-resolver.spec.ts b/packages/js/uri-resolvers/src/__tests__/recursive-resolver/recursive-resolver.spec.ts deleted file mode 100644 index 1b844881c1..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/recursive-resolver/recursive-resolver.spec.ts +++ /dev/null @@ -1,112 +0,0 @@ -import { - CoreClient, - IUriResolutionContext, - IUriResolver, - Result, - Uri, - UriPackageOrWrapper, - UriResolutionContext, -} from "@polywrap/core-js"; -import { expectHistory } from "../helpers/expectHistory"; -import { PolywrapCoreClient } from "@polywrap/core-client-js"; -import { RecursiveResolver, UriResolutionResult } from "../../helpers"; - -jest.setTimeout(20000); - -class SimpleRedirectResolver implements IUriResolver { - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> { - let result: Result; - - switch (uri.uri) { - case "wrap://test/1": - result = UriResolutionResult.ok( - Uri.from("test/2"), - ); - break; - case "wrap://test/2": - result = UriResolutionResult.ok( - Uri.from("test/3"), - ); - break; - case "wrap://test/3": - result = UriResolutionResult.ok( - Uri.from("test/4"), - ); - break; - default: - result = UriResolutionResult.ok(uri); - } - - resolutionContext.trackStep({ - sourceUri: uri, - result, - description: "SimpleRedirectResolver", - }); - - return result; - } -} - -describe("RecursiveResolver", () => { - it("can recursively resolve a URI", async () => { - const uri = new Uri("test/1"); - - const client = new PolywrapCoreClient({ - resolver: RecursiveResolver.from( - new SimpleRedirectResolver() - ) - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "recursive-resolver", - "can-recursively-resolve-uri", - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "uri") { - fail("Expected a URI, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/4"); - }); - - it("does not resolve a uri when not a match", async () => { - const uri = new Uri("test/not-a-match"); - - const client = new PolywrapCoreClient({ - resolver: RecursiveResolver.from( - new SimpleRedirectResolver() - ) - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "recursive-resolver", - "not-a-match", - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "uri") { - fail("Expected a uri, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/not-a-match"); - }); -}); diff --git a/packages/js/uri-resolvers/src/__tests__/redirect-resolver/histories/can-redirect-a-uri.json b/packages/js/uri-resolvers/src/__tests__/redirect-resolver/histories/can-redirect-a-uri.json deleted file mode 100644 index 9cdbce37f1..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/redirect-resolver/histories/can-redirect-a-uri.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/from => Redirect (wrap://test/from - wrap://test/to) => uri (wrap://test/to)" -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/redirect-resolver/histories/not-a-match.json b/packages/js/uri-resolvers/src/__tests__/redirect-resolver/histories/not-a-match.json deleted file mode 100644 index 3d119281e3..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/redirect-resolver/histories/not-a-match.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/not-a-match => Redirect (wrap://test/from - wrap://test/to)" -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/redirect-resolver/redirect-resolver.spec.ts b/packages/js/uri-resolvers/src/__tests__/redirect-resolver/redirect-resolver.spec.ts deleted file mode 100644 index 1bc996f5db..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/redirect-resolver/redirect-resolver.spec.ts +++ /dev/null @@ -1,71 +0,0 @@ -import { - Uri, - UriResolutionContext, -} from "@polywrap/core-js"; -import { expectHistory } from "../helpers/expectHistory"; -import { PolywrapCoreClient } from "@polywrap/core-client-js"; -import { RedirectResolver } from "../../redirects"; - -jest.setTimeout(20000); - -describe("RedirectResolver", () => { - it("can redirect a URI", async () => { - const uri = new Uri("test/from"); - - const client = new PolywrapCoreClient({ - resolver: new RedirectResolver( - Uri.from("test/from"), - Uri.from("test/to"), - ) - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "redirect-resolver", - "can-redirect-a-uri", - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "uri") { - fail("Expected a uri, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/to"); - }); - - it("does not redirect a URI when not a match", async () => { - const uri = new Uri("test/not-a-match"); - - const client = new PolywrapCoreClient({ - resolver: new RedirectResolver( - Uri.from("test/from"), - Uri.from("test/to"), - ) - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "redirect-resolver", - "not-a-match", - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "uri") { - fail("Expected a uri, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/not-a-match"); - }); -}); diff --git a/packages/js/uri-resolvers/src/__tests__/redirects.spec.ts b/packages/js/uri-resolvers/src/__tests__/redirects.spec.ts deleted file mode 100644 index acd4bc301b..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/redirects.spec.ts +++ /dev/null @@ -1,166 +0,0 @@ -import { - Uri, - CoreClient, - UriResolutionContext, -} from "@polywrap/core-js"; -import { InfiniteLoopError, RecursiveResolver, UriResolver } from "../helpers"; -import { StaticResolver } from "../static"; - -describe("redirects", () => { - it("sanity - UriResolver", async () => { - const uri1 = Uri.from("wrap://ens/some-uri1.eth"); - const uri2 = Uri.from("wrap://ens/some-uri2.eth"); - const resolver = UriResolver.from([ - { from: uri1, to: uri2 } - ]); - - const redirectsResult = await resolver.tryResolveUri(uri1, {} as CoreClient, new UriResolutionContext()); - - if (!redirectsResult.ok) { - fail(redirectsResult.error); - } - - if (redirectsResult.value.type !== "uri") { - console.error(`Expected URI, received: `, redirectsResult.value); - fail(); - } - - expect(redirectsResult.value.uri.uri).toEqual(uri2.uri); - }); - - it("sanity - StaticResolver", async () => { - const uri1 = Uri.from("wrap://ens/some-uri1.eth"); - const uri2 = Uri.from("wrap://ens/some-uri2.eth"); - const resolver = StaticResolver.from([ - { from: uri1, to: uri2 } - ]); - - const redirectsResult = await resolver.tryResolveUri(uri1, {} as CoreClient, new UriResolutionContext()); - - if (!redirectsResult.ok) { - fail(redirectsResult.error); - } - - if (redirectsResult.value.type !== "uri") { - console.log(`Expected URI, received: `, redirectsResult.value); - fail(); - } - - expect(redirectsResult.value.uri.uri).toEqual(uri2.uri); - }); - - it("works with the redirect stack overrides - RecursiveResolver", async () => { - const uri1 = Uri.from("wrap://ens/some-uri1.eth"); - const uri2 = Uri.from("wrap://ens/some-uri2.eth"); - const uri3 = Uri.from("wrap://ens/some-uri3.eth"); - - const resolver = RecursiveResolver.from([ - { - from: uri1, - to: uri2 - }, - { - from: uri2, - to: uri3 - } - ]); - - const redirectsResult = await resolver.tryResolveUri(uri1, {} as CoreClient, new UriResolutionContext()); - - if (!redirectsResult.ok) { - fail(redirectsResult.error); - } - - if (redirectsResult.value.type !== "uri") { - console.error(`Expected URI, received: `, redirectsResult.value); - fail(); - } - - expect(redirectsResult.value.uri.uri).toEqual(uri3.uri); - }); - - it("works with the redirect stack overrides - RecursiveResolver with StaticResolver", async () => { - const uri1 = Uri.from("wrap://ens/some-uri1.eth"); - const uri2 = Uri.from("wrap://ens/some-uri2.eth"); - const uri3 = Uri.from("wrap://ens/some-uri3.eth"); - - const resolver = RecursiveResolver.from( - StaticResolver.from([ - { - from: uri1, - to: uri2 - }, - { - from: uri2, - to: uri3 - } - ]) - ); - - const redirectsResult = await resolver.tryResolveUri(uri1, {} as CoreClient, new UriResolutionContext()); - - if (!redirectsResult.ok) { - fail(redirectsResult.error); - } - - if (redirectsResult.value.type !== "uri") { - console.log(`Expected URI, received: `, redirectsResult.value); - fail(); - } - - expect(redirectsResult.value.uri.uri).toEqual(uri3.uri); - }); - - it("can not redirect to self - RecursiveResolver", async () => { - const uri1 = Uri.from("wrap://ens/some-uri1.eth"); - const uri2 = Uri.from("wrap://ens/some-uri2.eth"); - - const resolver = RecursiveResolver.from([ - { - from: uri1, - to: uri2 - }, - { - from: uri2, - to: uri1 - }, - ]); - - const redirectsResult = await resolver.tryResolveUri(uri1, {} as CoreClient, new UriResolutionContext()); - - if (redirectsResult.ok) { - console.error(`Expected error`, redirectsResult.value); - fail(); - } - - expect((redirectsResult.error as InfiniteLoopError).message).toContain("An infinite loop was detected while resolving the URI"); - }); - - - it("can not redirect to self - RecursiveResolver with StaticResolver", async () => { - const uri1 = Uri.from("wrap://ens/some-uri1.eth"); - const uri2 = Uri.from("wrap://ens/some-uri2.eth"); - - const resolver = RecursiveResolver.from( - StaticResolver.from([ - { - from: uri1, - to: uri2 - }, - { - from: uri2, - to: uri1 - }, - ] - )); - - const redirectsResult = await resolver.tryResolveUri(uri1, {} as CoreClient, new UriResolutionContext()); - - if (redirectsResult.ok) { - console.log(`Expected error`, redirectsResult.value); - fail(); - } - - expect((redirectsResult.error as InfiniteLoopError).message).toContain("An infinite loop was detected while resolving the URI"); - }); -}); diff --git a/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-cache.json b/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-cache.json deleted file mode 100644 index e3d787a316..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-cache.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/should-redirect => RequestSynchronizerResolver (Cache) => uri (wrap://test/redirected)" -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-and-cache.json b/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-and-cache.json deleted file mode 100644 index 20500f3edf..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-and-cache.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/should-error => RequestSynchronizerResolver (Cache) => error (Test resolution error)" -] diff --git a/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-without-cache-2.json b/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-without-cache-2.json deleted file mode 100644 index f442a52efe..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-without-cache-2.json +++ /dev/null @@ -1,9 +0,0 @@ -[ - "wrap://test/should-error => RequestSynchronizerResolver => error (Test resolution error)", - [ - "wrap://test/should-error => RequestSynchronizerResolver => error (Test resolution error)", - [ - "wrap://test/should-error => SimpleAsyncRedirectResolver => error (Test resolution error)" - ] - ] -] diff --git a/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-without-cache-3.json b/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-without-cache-3.json deleted file mode 100644 index 56ca9542bc..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-without-cache-3.json +++ /dev/null @@ -1,12 +0,0 @@ -[ - "wrap://test/should-error => RequestSynchronizerResolver => error (Test resolution error)", - [ - "wrap://test/should-error => RequestSynchronizerResolver => error (Test resolution error)", - [ - "wrap://test/should-error => RequestSynchronizerResolver => error (Test resolution error)", - [ - "wrap://test/should-error => SimpleAsyncRedirectResolver => error (Test resolution error)" - ] - ] - ] -] diff --git a/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-without-cache.json b/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-without-cache.json deleted file mode 100644 index 50cbb7a39f..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-with-error-without-cache.json +++ /dev/null @@ -1,6 +0,0 @@ -[ - "wrap://test/should-error => RequestSynchronizerResolver => error (Test resolution error)", - [ - "wrap://test/should-error => SimpleAsyncRedirectResolver => error (Test resolution error)" - ] -] diff --git a/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-without-cache.json b/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-without-cache.json deleted file mode 100644 index 8213123d61..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/histories/synchronizer-without-cache.json +++ /dev/null @@ -1,6 +0,0 @@ -[ - "wrap://test/should-redirect => RequestSynchronizerResolver => uri (wrap://test/redirected)", - [ - "wrap://test/should-redirect => SimpleAsyncRedirectResolver => uri (wrap://test/redirected)" - ] -] diff --git a/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/request-synchronizer-resolver.spec.ts b/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/request-synchronizer-resolver.spec.ts deleted file mode 100644 index 320fb1d9ce..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/request-synchronizer-resolver/request-synchronizer-resolver.spec.ts +++ /dev/null @@ -1,343 +0,0 @@ -import { - CoreClient, - IUriResolutionContext, - IUriResolver, - Result, - Uri, - UriPackageOrWrapper, - UriResolutionContext, -} from "@polywrap/core-js"; -import { expectHistory } from "../helpers/expectHistory"; -import { RequestSynchronizerResolver } from "../../cache"; -import { UriResolutionResult } from "../../helpers"; -import { PolywrapCoreClient } from "@polywrap/core-client-js"; - -jest.setTimeout(20000); - -class SimpleAsyncRedirectResolver implements IUriResolver { - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> { - switch (uri.uri) { - case "wrap://test/should-redirect": - return new Promise>((resolve) => { - setTimeout(() => { - const result = UriResolutionResult.ok( - new Uri("wrap://test/redirected") - ); - - resolutionContext.trackStep({ - sourceUri: uri, - result, - description: "SimpleAsyncRedirectResolver", - }); - - resolve(result); - }, 100); - }); - case "wrap://test/should-error": - return new Promise>((resolve) => { - setTimeout(() => { - const result = UriResolutionResult.err( - new Error("Test resolution error") - ); - - resolutionContext.trackStep({ - sourceUri: uri, - result, - description: "SimpleAsyncRedirectResolver", - }); - - resolve(result); - }, 100); - }); - case "wrap://test/should-error-2": - return new Promise>((resolve) => { - setTimeout(() => { - const result = UriResolutionResult.err( - new Error("Test resolution error 2") - ); - - resolutionContext.trackStep({ - sourceUri: uri, - result, - description: "SimpleAsyncRedirectResolver", - }); - - resolve(result); - }, 100); - }); - case "wrap://test/should-throw": - return new Promise>((_, reject) => { - setTimeout(() => { - reject(new Error("Test thrown exception")); - }, 100); - }); - default: - throw new Error(`Unexpected URI: ${uri.uri}`); - } - } -} - -describe("RequestSynchronizerResolver", () => { - it("parallel requests with same uri trigger only one network request", async () => { - const uri = new Uri("wrap://test/should-redirect"); - - const client = new PolywrapCoreClient({ - resolver: RequestSynchronizerResolver.from( - new SimpleAsyncRedirectResolver() - ), - }); - - const invocations: Promise>[] = []; - const resolutionContexts: IUriResolutionContext[] = []; - - for (let i = 0; i < 3; i++) { - const resolutionContext = new UriResolutionContext(); - const result = client.tryResolveUri({ uri, resolutionContext }); - invocations.push(result); - resolutionContexts.push(resolutionContext); - } - - const resolutionResults = await Promise.all(invocations); - - let foundFirst = false; - - for (let i = 0; i < invocations.length; i++) { - const result = resolutionResults[i]; - const resolutionContext = resolutionContexts[i]; - - if (!result.ok) throw result.error; - - if (!foundFirst) { - await expectHistory( - resolutionContext.getHistory(), - "request-synchronizer-resolver", - "synchronizer-without-cache" - ); - expect(result.value.type).toEqual("uri"); - foundFirst = true; - continue; - } - - await expectHistory( - resolutionContext.getHistory(), - "request-synchronizer-resolver", - "synchronizer-with-cache" - ); - - expect(result.value.type).toEqual("uri"); - } - }); - - it("serial requests trigger multiple network requests", async () => { - const uri = new Uri("wrap://test/should-redirect"); - - const client = new PolywrapCoreClient({ - resolver: RequestSynchronizerResolver.from( - new SimpleAsyncRedirectResolver() - ), - }); - - const resolutionResults: Result[] = []; - const resolutionContexts: IUriResolutionContext[] = []; - - for (let i = 0; i < 3; i++) { - const resolutionContext = new UriResolutionContext(); - const result = await client.tryResolveUri({ uri, resolutionContext }); - resolutionResults.push(result); - resolutionContexts.push(resolutionContext); - } - - for (let i = 0; i < resolutionResults.length; i++) { - const result = resolutionResults[i]; - const resolutionContext = resolutionContexts[i]; - - if (!result.ok) throw result.error; - - await expectHistory( - resolutionContext.getHistory(), - "request-synchronizer-resolver", - "synchronizer-without-cache" - ); - expect(result.value.type).toEqual("uri"); - } - }); - - it("parallel requests resulting in a thrown exception also throw", async () => { - const uri = new Uri("wrap://test/should-throw"); - - const client = new PolywrapCoreClient({ - resolver: RequestSynchronizerResolver.from( - new SimpleAsyncRedirectResolver() - ), - }); - - const invocations: Promise[] = []; - const resolutionContexts: IUriResolutionContext[] = []; - - for (let i = 0; i < 3; i++) { - const resolutionContext = new UriResolutionContext(); - const result = client.tryResolveUri({ uri, resolutionContext }); - invocations.push( - new Promise((resolve) => { - result.then( - (r: unknown) => { - throw new Error("Should not have resolved"); - }, - (e: Error) => { - expect(e.message).toEqual("Test thrown exception"); - resolve(); - } - ); - }) - ); - resolutionContexts.push(resolutionContext); - } - - await Promise.all(invocations); - }); - - it("parallel requests resulting in a resolution error return cached error by default", async () => { - const uri = new Uri("wrap://test/should-error"); - - const client = new PolywrapCoreClient({ - resolver: RequestSynchronizerResolver.from( - new SimpleAsyncRedirectResolver() - ), - }); - - const invocations: Promise>[] = []; - const resolutionContexts: IUriResolutionContext[] = []; - - for (let i = 0; i < 3; i++) { - const resolutionContext = new UriResolutionContext(); - const result = client.tryResolveUri({ uri, resolutionContext }); - invocations.push(result); - resolutionContexts.push(resolutionContext); - } - - const resolutionResults = await Promise.all(invocations); - - let foundFirst = false; - - for (let i = 0; i < invocations.length; i++) { - const result = resolutionResults[i]; - const resolutionContext = resolutionContexts[i]; - - if (!foundFirst) { - await expectHistory( - resolutionContext.getHistory(), - "request-synchronizer-resolver", - "synchronizer-with-error-without-cache" - ); - expect(result.ok).toBeFalsy(); - foundFirst = true; - continue; - } - - await expectHistory( - resolutionContext.getHistory(), - "request-synchronizer-resolver", - "synchronizer-with-error-and-cache" - ); - expect(result.ok).toBeFalsy(); - } - }); - - it("parallel requests resulting in a resolution error respect shouldIgnoreCache", async () => { - const client = new PolywrapCoreClient({ - resolver: RequestSynchronizerResolver.from( - new SimpleAsyncRedirectResolver(), - { - shouldIgnoreCache: (error: Error) => { - if (error.message === "Test resolution error") return true; - return true; - }, - } - ), - }); - - // shouldIgnoreCache is true, so this should retry (act without using cache) - const uri = new Uri("wrap://test/should-error"); - const invocations: Promise>[] = []; - const resolutionContexts: IUriResolutionContext[] = []; - - for (let i = 0; i < 3; i++) { - const resolutionContext = new UriResolutionContext(); - const result = client.tryResolveUri({ uri, resolutionContext }); - invocations.push(result); - resolutionContexts.push(resolutionContext); - } - - const resolutionResults = await Promise.all(invocations); - - for (let i = 0; i < invocations.length; i++) { - const result = resolutionResults[i]; - const resolutionContext = resolutionContexts[i]; - - if (i === 0) { - await expectHistory( - resolutionContext.getHistory(), - "request-synchronizer-resolver", - "synchronizer-with-error-without-cache" - ); - } else if (i === 1) { - await expectHistory( - resolutionContext.getHistory(), - "request-synchronizer-resolver", - "synchronizer-with-error-without-cache-2" - ); - } else { - await expectHistory( - resolutionContext.getHistory(), - "request-synchronizer-resolver", - "synchronizer-with-error-without-cache-3" - ); - } - - expect(result.ok).toBeFalsy(); - } - - // shouldIgnoreCache is falsy, so this should not retry (use the error from cache) - const uri2 = new Uri("wrap://test/should-error-2"); - const invocations2: Promise>[] = []; - const resolutionContexts2: IUriResolutionContext[] = []; - - for (let i = 0; i < 3; i++) { - const resolutionContext = new UriResolutionContext(); - const result = client.tryResolveUri({ uri: uri2, resolutionContext }); - invocations.push(result); - resolutionContexts.push(resolutionContext); - } - - const resolutionResults2 = await Promise.all(invocations); - - let foundFirst = false; - - for (let i = 0; i < invocations2.length; i++) { - const result = resolutionResults2[i]; - const resolutionContext = resolutionContexts2[i]; - - if (!foundFirst) { - await expectHistory( - resolutionContext.getHistory(), - "request-synchronizer-resolver", - "synchronizer-with-error-without-cache" - ); - expect(result.ok).toBeFalsy(); - foundFirst = true; - continue; - } - - await expectHistory( - resolutionContext.getHistory(), - "request-synchronizer-resolver", - "synchronizer-with-error-and-cache" - ); - expect(result.ok).toBeFalsy(); - } - }); -}); diff --git a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/error-with-cache.json b/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/error-with-cache.json deleted file mode 100644 index ec603e0800..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/error-with-cache.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/error => ResolutionResultCacheResolver (Cache) => error (A test error)" -] diff --git a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/error-without-cache.json b/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/error-without-cache.json deleted file mode 100644 index 2706a26a91..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/error-without-cache.json +++ /dev/null @@ -1,4 +0,0 @@ -[ - "wrap://test/error => ResolutionResultCacheResolver => error (A test error)", - ["wrap://test/error => TestResolver => error (A test error)"] -] diff --git a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/package-with-cache.json b/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/package-with-cache.json deleted file mode 100644 index 5a40f65c50..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/package-with-cache.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/package => ResolutionResultCacheResolver (Cache) => package (wrap://test/package)" -] diff --git a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/package-without-cache.json b/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/package-without-cache.json deleted file mode 100644 index 0769d25f08..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/package-without-cache.json +++ /dev/null @@ -1,6 +0,0 @@ -[ - "wrap://test/package => ResolutionResultCacheResolver => package (wrap://test/package)", - [ - "wrap://test/package => TestResolver => package (wrap://test/package)" - ] -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/uri-with-cache.json b/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/uri-with-cache.json deleted file mode 100644 index daa3562605..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/uri-with-cache.json +++ /dev/null @@ -1 +0,0 @@ -["wrap://test/from => ResolutionResultCacheResolver (Cache) => uri (wrap://test/to)"] diff --git a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/uri-without-cache.json b/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/uri-without-cache.json deleted file mode 100644 index b1017e1c5a..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/uri-without-cache.json +++ /dev/null @@ -1,6 +0,0 @@ -[ - "wrap://test/from => ResolutionResultCacheResolver => uri (wrap://test/to)", - [ - "wrap://test/from => TestResolver => uri (wrap://test/to)" - ] -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/wrapper-with-cache.json b/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/wrapper-with-cache.json deleted file mode 100644 index fb197949f2..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/wrapper-with-cache.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/wrapper => ResolutionResultCacheResolver (Cache) => wrapper (wrap://test/wrapper)" -] diff --git a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/wrapper-without-cache.json b/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/wrapper-without-cache.json deleted file mode 100644 index d4453b8ced..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/histories/wrapper-without-cache.json +++ /dev/null @@ -1,4 +0,0 @@ -[ - "wrap://test/wrapper => ResolutionResultCacheResolver => wrapper (wrap://test/wrapper)", - ["wrap://test/wrapper => TestResolver => wrapper (wrap://test/wrapper)"] -] diff --git a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/resolution-result-cache-resolver.spec.ts b/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/resolution-result-cache-resolver.spec.ts deleted file mode 100644 index a37a4c393a..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/resolution-result-cache-resolver/resolution-result-cache-resolver.spec.ts +++ /dev/null @@ -1,350 +0,0 @@ -import { - CoreClient, - IUriResolutionContext, - IUriResolver, - Result, - Uri, - UriPackageOrWrapper, - UriResolutionContext, -} from "@polywrap/core-js"; -import { expectHistory } from "../helpers/expectHistory"; -import { RecursiveResolver, UriResolutionResult } from "../../helpers"; -import { PolywrapCoreClient } from "@polywrap/core-client-js"; -import { PluginPackage } from "@polywrap/plugin-js"; -import { ResolutionResultCacheResolver } from "../../cache/ResolutionResultCacheResolver"; -import { ResolutionResultCache } from "../../cache/ResolutionResultCache"; - -jest.setTimeout(20000); - -class TestResolver implements IUriResolver { - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> { - let result: Result; - - switch (uri.uri) { - case "wrap://test/package": - result = UriResolutionResult.ok( - Uri.from("test/package"), - PluginPackage.from(() => ({})) - ); - break; - case "wrap://test/wrapper": - let wrapperResult = await PluginPackage.from( - () => ({}) - ).createWrapper(); - if (!wrapperResult.ok) { - throw wrapperResult.error; - } - - result = UriResolutionResult.ok( - Uri.from("test/wrapper"), - wrapperResult.value - ); - break; - case "wrap://test/from": - result = UriResolutionResult.ok(Uri.from("test/to")); - break; - case "wrap://test/A": - result = UriResolutionResult.ok(Uri.from("test/B")); - break; - case "wrap://test/B": - result = UriResolutionResult.ok(Uri.from("test/wrapper")); - break; - case "wrap://test/error": - result = UriResolutionResult.err(new Error("A test error")); - break; - default: - throw new Error(`Unexpected URI: ${uri.uri}`); - } - - resolutionContext.trackStep({ - sourceUri: uri, - result, - description: "TestResolver", - }); - - return result; - } -} - -describe("ResolutionResultCacheResolver", () => { - it("caches a resolved wrapper", async () => { - const uri = new Uri("test/wrapper"); - - const client = new PolywrapCoreClient({ - resolver: ResolutionResultCacheResolver.from( - new TestResolver(), - new ResolutionResultCache() - ), - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "resolution-result-cache-resolver", - "wrapper-without-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "wrapper") { - fail("Expected a wrapper, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/wrapper"); - - resolutionContext = new UriResolutionContext(); - result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "resolution-result-cache-resolver", - "wrapper-with-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "wrapper") { - fail("Expected a wrapper, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/wrapper"); - }); - - it("caches a resolved URI", async () => { - const uri = new Uri("test/from"); - - const client = new PolywrapCoreClient({ - resolver: ResolutionResultCacheResolver.from( - new TestResolver(), - new ResolutionResultCache() - ), - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "resolution-result-cache-resolver", - "uri-without-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "uri") { - fail("Expected a uri, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/to"); - - resolutionContext = new UriResolutionContext(); - result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "resolution-result-cache-resolver", - "uri-with-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "uri") { - fail("Expected a uri, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/to"); - }); - - it("caches a resolved package", async () => { - const uri = new Uri("test/package"); - - const client = new PolywrapCoreClient({ - resolver: ResolutionResultCacheResolver.from( - new TestResolver(), - new ResolutionResultCache() - ), - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "resolution-result-cache-resolver", - "package-without-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "package") { - fail("Expected a package, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/package"); - - resolutionContext = new UriResolutionContext(); - result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "resolution-result-cache-resolver", - "package-with-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "package") { - fail("Expected a package, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/package"); - }); - - it("does not cache error by default", async () => { - const client = new PolywrapCoreClient({ - resolver: ResolutionResultCacheResolver.from( - new TestResolver(), - new ResolutionResultCache() - ), - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ - uri: Uri.from("test/error"), - resolutionContext, - }); - - await expectHistory( - resolutionContext.getHistory(), - "resolution-result-cache-resolver", - "error-without-cache" - ); - - if (result.ok) { - fail("Expected an error, received: " + result.value.type); - } - expect((result.error as Error)?.message).toEqual("A test error"); - - resolutionContext = new UriResolutionContext(); - result = await client.tryResolveUri({ - uri: Uri.from("test/error"), - resolutionContext, - }); - - await expectHistory( - resolutionContext.getHistory(), - "resolution-result-cache-resolver", - "error-without-cache" - ); - - if (result.ok) { - fail("Expected an error, received: " + result.value.type); - } - expect((result.error as Error)?.message).toEqual("A test error"); - }); - - it("caches error if configured", async () => { - const client = new PolywrapCoreClient({ - resolver: ResolutionResultCacheResolver.from( - new TestResolver(), - new ResolutionResultCache(), - { - cacheErrors: true, - } - ), - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ - uri: Uri.from("test/error"), - resolutionContext, - }); - - await expectHistory( - resolutionContext.getHistory(), - "resolution-result-cache-resolver", - "error-without-cache" - ); - - if (result.ok) { - fail("Expected an error, received: " + result.value.type); - } - expect((result.error as Error)?.message).toEqual("A test error"); - - resolutionContext = new UriResolutionContext(); - result = await client.tryResolveUri({ - uri: Uri.from("test/error"), - resolutionContext, - }); - - await expectHistory( - resolutionContext.getHistory(), - "resolution-result-cache-resolver", - "error-with-cache" - ); - - if (result.ok) { - fail("Expected an error, received: " + result.value.type); - } - expect((result.error as Error)?.message).toEqual("A test error"); - }); - - it("keeps the same resolution path after caching", async () => { - const uri = new Uri("test/A"); - - const client = new PolywrapCoreClient({ - resolver: RecursiveResolver.from([ - ResolutionResultCacheResolver.from( - [ - { - from: Uri.from("test/A"), - to: Uri.from("test/B"), - }, - { - from: Uri.from("test/B"), - to: Uri.from("test/wrapper"), - }, - new TestResolver(), - ], - new ResolutionResultCache() - ), - ]), - }); - - let resolutionContext = new UriResolutionContext(); - await client.tryResolveUri({ uri, resolutionContext }); - - expect(resolutionContext.getResolutionPath().map((x) => x.uri)).toEqual([ - "wrap://test/A", - "wrap://test/B", - "wrap://test/wrapper", - ]); - - resolutionContext = new UriResolutionContext(); - await client.tryResolveUri({ uri, resolutionContext }); - - expect(resolutionContext.getResolutionPath().map((x) => x.uri)).toEqual([ - "wrap://test/A", - "wrap://test/B", - "wrap://test/wrapper", - ]); - }); -}); diff --git a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/package-without-cache.json b/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/package-without-cache.json deleted file mode 100644 index 38ac85c4b1..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/package-without-cache.json +++ /dev/null @@ -1,6 +0,0 @@ -[ - "wrap://test/package => WrapperCacheResolver => package (wrap://test/package)", - [ - "wrap://test/package => TestResolver => package (wrap://test/package)" - ] -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-A-with-cache.json b/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-A-with-cache.json deleted file mode 100644 index 2d32f4ed51..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-A-with-cache.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/A => WrapperCacheResolver (Cache) => wrapper (wrap://test/A)" -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-B-with-cache.json b/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-B-with-cache.json deleted file mode 100644 index da9e5277d5..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-B-with-cache.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/B => WrapperCacheResolver (Cache) => wrapper (wrap://test/B)" -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-without-cache.json b/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-without-cache.json deleted file mode 100644 index f112738ae3..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-without-cache.json +++ /dev/null @@ -1,14 +0,0 @@ -[ - "wrap://test/A => WrapperCacheResolver => uri (wrap://test/B)", - [ - "wrap://test/A => TestResolver => uri (wrap://test/B)" - ], - "wrap://test/B => WrapperCacheResolver => uri (wrap://test/wrapper)", - [ - "wrap://test/B => TestResolver => uri (wrap://test/wrapper)" - ], - "wrap://test/wrapper => WrapperCacheResolver => wrapper (wrap://test/wrapper)", - [ - "wrap://test/wrapper => TestResolver => wrapper (wrap://test/wrapper)" - ] -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-wrapper-with-cache.json b/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-wrapper-with-cache.json deleted file mode 100644 index 84db5052c2..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/resolution-path-wrapper-with-cache.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/wrapper => WrapperCacheResolver (Cache) => wrapper (wrap://test/wrapper)" -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/uri-without-cache.json b/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/uri-without-cache.json deleted file mode 100644 index 61afebed1e..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/uri-without-cache.json +++ /dev/null @@ -1,6 +0,0 @@ -[ - "wrap://test/from => WrapperCacheResolver => uri (wrap://test/to)", - [ - "wrap://test/from => TestResolver => uri (wrap://test/to)" - ] -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/wrapper-with-cache.json b/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/wrapper-with-cache.json deleted file mode 100644 index 84db5052c2..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/wrapper-with-cache.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/wrapper => WrapperCacheResolver (Cache) => wrapper (wrap://test/wrapper)" -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/wrapper-without-cache.json b/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/wrapper-without-cache.json deleted file mode 100644 index 48c852d067..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/histories/wrapper-without-cache.json +++ /dev/null @@ -1,6 +0,0 @@ -[ - "wrap://test/wrapper => WrapperCacheResolver => wrapper (wrap://test/wrapper)", - [ - "wrap://test/wrapper => TestResolver => wrapper (wrap://test/wrapper)" - ] -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/wrapper-cache-resolver.spec.ts b/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/wrapper-cache-resolver.spec.ts deleted file mode 100644 index 91912d122e..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/wrapper-cache-resolver/wrapper-cache-resolver.spec.ts +++ /dev/null @@ -1,311 +0,0 @@ -import { - CoreClient, - IUriResolutionContext, - IUriResolver, - Result, - Uri, - UriPackageOrWrapper, - UriResolutionContext, -} from "@polywrap/core-js"; -import { expectHistory } from "../helpers/expectHistory"; -import { RecursiveResolver, UriResolutionResult } from "../../helpers"; -import { PolywrapCoreClient } from "@polywrap/core-client-js"; -import { PluginPackage } from "@polywrap/plugin-js"; -import { WrapperCache, WrapperCacheResolver } from "../../cache"; - -jest.setTimeout(20000); - -class TestResolver implements IUriResolver { - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> { - let result: Result; - - switch (uri.uri) { - case "wrap://test/package": - result = UriResolutionResult.ok( - Uri.from("test/package"), - PluginPackage.from(() => ({})) - ); - break; - case "wrap://test/wrapper": - let wrapperResult = await PluginPackage.from( - () => ({}) - ).createWrapper(); - if (!wrapperResult.ok) { - throw wrapperResult.error; - } - - result = UriResolutionResult.ok( - Uri.from("test/wrapper"), - wrapperResult.value - ); - break; - case "wrap://test/from": - result = UriResolutionResult.ok(Uri.from("test/to")); - break; - case "wrap://test/A": - result = UriResolutionResult.ok(Uri.from("test/B")); - break; - case "wrap://test/B": - result = UriResolutionResult.ok(Uri.from("test/wrapper")); - break; - default: - throw new Error(`Unexpected URI: ${uri.uri}`); - } - - resolutionContext.trackStep({ - sourceUri: uri, - result, - description: "TestResolver", - }); - - return result; - } -} - -describe("WrapperCacheResolver", () => { - it("caches a resolved wrapper", async () => { - const uri = new Uri("test/wrapper"); - - const cache = new WrapperCache(); - const client = new PolywrapCoreClient({ - resolver: WrapperCacheResolver.from(new TestResolver(), cache), - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "wrapper-cache-resolver", - "wrapper-without-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "wrapper") { - fail("Expected a wrapper, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/wrapper"); - - resolutionContext = new UriResolutionContext(); - result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "wrapper-cache-resolver", - "wrapper-with-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "wrapper") { - fail("Expected a wrapper, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/wrapper"); - }); - - it("does not cache a URI", async () => { - const uri = new Uri("test/from"); - - const client = new PolywrapCoreClient({ - resolver: WrapperCacheResolver.from( - new TestResolver(), - new WrapperCache() - ), - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "wrapper-cache-resolver", - "uri-without-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "uri") { - fail("Expected a uri, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/to"); - - resolutionContext = new UriResolutionContext(); - result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "wrapper-cache-resolver", - "uri-without-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "uri") { - fail("Expected a uri, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/to"); - }); - - it("does not cache a package", async () => { - const uri = new Uri("test/package"); - - const client = new PolywrapCoreClient({ - resolver: WrapperCacheResolver.from( - new TestResolver(), - new WrapperCache() - ), - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "wrapper-cache-resolver", - "package-without-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "package") { - fail("Expected a package, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/package"); - - resolutionContext = new UriResolutionContext(); - result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "wrapper-cache-resolver", - "package-without-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "package") { - fail("Expected a package, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/package"); - }); - - it("caches the whole resolution path", async () => { - const cache = new WrapperCache(); - const client = new PolywrapCoreClient({ - resolver: RecursiveResolver.from( - WrapperCacheResolver.from(new TestResolver(), cache) - ), - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ - uri: Uri.from("test/A"), - resolutionContext, - }); - - await expectHistory( - resolutionContext.getHistory(), - "wrapper-cache-resolver", - "resolution-path-without-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "wrapper") { - fail("Expected a wrapper, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/wrapper"); - - resolutionContext = new UriResolutionContext(); - result = await client.tryResolveUri({ - uri: Uri.from("test/A"), - resolutionContext, - }); - - await expectHistory( - resolutionContext.getHistory(), - "wrapper-cache-resolver", - "resolution-path-A-with-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "wrapper") { - fail("Expected a wrapper, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/A"); - - resolutionContext = new UriResolutionContext(); - result = await client.tryResolveUri({ - uri: Uri.from("test/B"), - resolutionContext, - }); - - await expectHistory( - resolutionContext.getHistory(), - "wrapper-cache-resolver", - "resolution-path-B-with-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "wrapper") { - fail("Expected a wrapper, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/B"); - - resolutionContext = new UriResolutionContext(); - result = await client.tryResolveUri({ - uri: Uri.from("test/wrapper"), - resolutionContext, - }); - - await expectHistory( - resolutionContext.getHistory(), - "wrapper-cache-resolver", - "resolution-path-wrapper-with-cache" - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "wrapper") { - fail("Expected a wrapper, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/wrapper"); - }); -}); diff --git a/packages/js/uri-resolvers/src/__tests__/wrapper-resolver/histories/can-resolve-a-wrapper.json b/packages/js/uri-resolvers/src/__tests__/wrapper-resolver/histories/can-resolve-a-wrapper.json deleted file mode 100644 index 99abca8e45..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/wrapper-resolver/histories/can-resolve-a-wrapper.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/wrapper => Wrapper (wrap://test/wrapper) => wrapper (wrap://test/wrapper)" -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/wrapper-resolver/histories/not-a-match.json b/packages/js/uri-resolvers/src/__tests__/wrapper-resolver/histories/not-a-match.json deleted file mode 100644 index fccd3dce2a..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/wrapper-resolver/histories/not-a-match.json +++ /dev/null @@ -1,3 +0,0 @@ -[ - "wrap://test/not-a-match => Wrapper (wrap://test/wrapper)" -] \ No newline at end of file diff --git a/packages/js/uri-resolvers/src/__tests__/wrapper-resolver/wrapper-resolver.spec.ts b/packages/js/uri-resolvers/src/__tests__/wrapper-resolver/wrapper-resolver.spec.ts deleted file mode 100644 index 599eb0d005..0000000000 --- a/packages/js/uri-resolvers/src/__tests__/wrapper-resolver/wrapper-resolver.spec.ts +++ /dev/null @@ -1,82 +0,0 @@ -import { - Uri, - UriResolutionContext, -} from "@polywrap/core-js"; -import { expectHistory } from "../helpers/expectHistory"; -import { PolywrapCoreClient } from "@polywrap/core-client-js"; -import { PluginPackage } from "@polywrap/plugin-js"; -import { WrapperResolver } from "../../wrappers"; - -jest.setTimeout(20000); - -describe("WrapperResolver", () => { - it("can resolve a wrapper", async () => { - const uri = new Uri("test/wrapper"); - - let wrapperResult = await PluginPackage.from(() => ({})).createWrapper(); - if (!wrapperResult.ok) { - throw wrapperResult.error; - } - - const client = new PolywrapCoreClient({ - resolver: new WrapperResolver( - Uri.from("test/wrapper"), - wrapperResult.value - ) - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "wrapper-resolver", - "can-resolve-a-wrapper", - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "wrapper") { - fail("Expected a wrapper, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/wrapper"); - }); - - it("does not resolve a wrapper when not a match", async () => { - const uri = new Uri("test/not-a-match"); - - let wrapperResult = await PluginPackage.from(() => ({})).createWrapper(); - if (!wrapperResult.ok) { - throw wrapperResult.error; - } - - const client = new PolywrapCoreClient({ - resolver: new WrapperResolver( - Uri.from("test/wrapper"), - wrapperResult.value - ) - }); - - let resolutionContext = new UriResolutionContext(); - let result = await client.tryResolveUri({ uri, resolutionContext }); - - await expectHistory( - resolutionContext.getHistory(), - "wrapper-resolver", - "not-a-match", - ); - - if (!result.ok) { - fail(result.error); - } - - if (result.value.type !== "uri") { - fail("Expected a uri, received: " + result.value.type); - } - - expect(result.value.uri.uri).toEqual("wrap://test/not-a-match"); - }); -}); diff --git a/packages/js/uri-resolvers/src/aggregator/UriResolverAggregator.ts b/packages/js/uri-resolvers/src/aggregator/UriResolverAggregator.ts deleted file mode 100644 index d48821527b..0000000000 --- a/packages/js/uri-resolvers/src/aggregator/UriResolverAggregator.ts +++ /dev/null @@ -1,112 +0,0 @@ -import { UriResolverAggregatorBase } from "./UriResolverAggregatorBase"; -import { UriResolver, UriResolverLike } from "../helpers"; - -import { Result, ResultOk } from "@polywrap/result"; -import { IUriResolver, Uri, CoreClient } from "@polywrap/core-js"; - -// $start: UriResolverAggregator-GetResolversFunc -/** - * A function that returns a list of resolvers - * - * @param uri - the URI to query - * @param client - a CoreClient instance - * */ -export type GetResolversFunc = ( - uri: Uri, - client: CoreClient -) => Promise[]>; -// $end - -// $start: UriResolverAggregator-GetResolversWithErrorFunc -/** - * A function that returns a list of resolvers or an error - * - * @param uri - the URI to query - * @param client - a CoreClient instance - * */ -export type GetResolversWithErrorFunc = ( - uri: Uri, - client: CoreClient -) => Promise[], TError>>; -// $end - -// $start: UriResolverAggregator -/** - * An implementation of UriResolverAggregatorBase - */ -export class UriResolverAggregator< - TResolutionError = undefined, - TGetResolversError = undefined -> extends UriResolverAggregatorBase< - TResolutionError, - TGetResolversError -> /* $ */ { - private _resolvers: - | IUriResolver[] - | GetResolversFunc - | GetResolversWithErrorFunc; - - // $start: UriResolverAggregator-constructor - /** - * Creates a UriResolverAggregator from a list of resolvers, or from a function - * that returns a list of resolvers - * */ - constructor(resolvers: UriResolverLike[], resolverName?: string); - constructor( - resolvers: ( - uri: Uri, - client: CoreClient - ) => Promise[], TGetResolversError>>, - resolverName?: string - ); - constructor(resolvers: GetResolversFunc, resolverName?: string); - constructor( - resolvers: - | UriResolverLike[] - | GetResolversFunc - | GetResolversWithErrorFunc, - private _resolverName?: string - ) /* $ */ { - super(); - if (Array.isArray(resolvers)) { - this._resolvers = resolvers.map((x) => UriResolver.from(x)); - } else { - this._resolvers = resolvers; - } - } - - // $start: UriResolverAggregator-getUriResolvers - /** - * Get a list of URI Resolvers - * - * @param uri - the URI to query for resolvers - * @param client - a CoreClient instance that can be used to make an invocation - * - * @returns a list of IUriResolver or an error - * */ - async getUriResolvers( - uri: Uri, - client: CoreClient - ): Promise[], TGetResolversError>> /* $ */ { - if (Array.isArray(this._resolvers)) { - return ResultOk(this._resolvers); - } else { - const result = await this._resolvers(uri, client); - - if (Array.isArray(result)) { - return ResultOk(result); - } else { - return result; - } - } - } - - // $start: UriResolverAggregator-getStepDescription - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @returns text describing the URI resolution step - * */ - protected getStepDescription = (): string /* $ */ => - `${this._resolverName ?? "UriResolverAggregator"}`; -} diff --git a/packages/js/uri-resolvers/src/aggregator/UriResolverAggregatorBase.ts b/packages/js/uri-resolvers/src/aggregator/UriResolverAggregatorBase.ts deleted file mode 100644 index d33deef845..0000000000 --- a/packages/js/uri-resolvers/src/aggregator/UriResolverAggregatorBase.ts +++ /dev/null @@ -1,144 +0,0 @@ -import { UriResolutionResult } from "../helpers"; - -import { - IUriResolver, - Uri, - CoreClient, - IUriResolutionContext, - UriPackageOrWrapper, -} from "@polywrap/core-js"; -import { Result } from "@polywrap/result"; - -// $start: UriResolverAggregatorBase -/** - * Abstract class for IUriResolver implementations that aggregate multiple resolvers. - * The UriResolverAggregatorBase class attempts to resolve a URI by sequentially - * attempting resolution with each of its composite resolvers. - * */ -export abstract class UriResolverAggregatorBase< - TResolutionError = undefined, - TGetResolversError = undefined -> implements IUriResolver /* $ */ { - // $start: UriResolverAggregatorBase-getUriResolvers - /** - * Get a list of URI Resolvers - * - * @param uri - the URI to query for resolvers - * @param client - a CoreClient instance that can be used to make an invocation - * @param resolutionContext - a resolution context to update when resolving URIs - * - * @returns a list of IUriResolver or an error - * */ - abstract getUriResolvers( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise[], TGetResolversError>>; - // $end - - // $start: UriResolverAggregatorBase-tryResolveUri - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * Attempts to resolve the URI using each of the aggregated resolvers sequentially. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise< - Result - > /* $ */ { - const resolverResult = await this.getUriResolvers( - uri, - client, - resolutionContext - ); - - if (!resolverResult.ok) { - return resolverResult; - } - - const resolvers = resolverResult.value as IUriResolver[]; - - return await this.tryResolveUriWithResolvers( - uri, - client, - resolvers, - resolutionContext - ); - } - - // $start: UriResolverAggregatorBase-getStepDescription - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @param uri - the URI being resolved - * @param result - the result of a resolution attempt - * - * @returns text describing the URI resolution step - * */ - protected abstract getStepDescription( - uri: Uri, - result: Result - ): string; - // $end - - // $start: UriResolverAggregatorBase-tryResolveUriWithResolvers - /** - * Using each of the aggregated resolvers, attempt to resolve a URI - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that can be used to make an invocation - * @param resolvers - a list of IUriResolver implementations - * @param resolutionContext - a resolution context to update when resolving URIs - * - * @returns a URI, a Wrap Package, or a Wrapper (or an error) - * */ - protected async tryResolveUriWithResolvers( - uri: Uri, - client: CoreClient, - resolvers: IUriResolver[], - resolutionContext: IUriResolutionContext - ): Promise> /* $ */ { - const subContext = resolutionContext.createSubHistoryContext(); - - for (const resolver of resolvers) { - const typeResolver = resolver as IUriResolver; - - const result = await typeResolver.tryResolveUri(uri, client, subContext); - - if ( - !( - result.ok && - result.value.type === "uri" && - result.value.uri.uri === uri.uri - ) - ) { - resolutionContext.trackStep({ - sourceUri: uri, - result, - subHistory: subContext.getHistory(), - description: this.getStepDescription(uri, result), - }); - - return result; - } - } - - const result = UriResolutionResult.ok(uri); - - resolutionContext.trackStep({ - sourceUri: uri, - result, - subHistory: subContext.getHistory(), - description: this.getStepDescription(uri, result), - }); - - return result; - } -} diff --git a/packages/js/uri-resolvers/src/aggregator/index.ts b/packages/js/uri-resolvers/src/aggregator/index.ts deleted file mode 100644 index 4e65a3d8a6..0000000000 --- a/packages/js/uri-resolvers/src/aggregator/index.ts +++ /dev/null @@ -1,2 +0,0 @@ -export * from "./UriResolverAggregator"; -export * from "./UriResolverAggregatorBase"; diff --git a/packages/js/uri-resolvers/src/cache/IResolutionResultCache.ts b/packages/js/uri-resolvers/src/cache/IResolutionResultCache.ts deleted file mode 100644 index 9f532dfdc0..0000000000 --- a/packages/js/uri-resolvers/src/cache/IResolutionResultCache.ts +++ /dev/null @@ -1,17 +0,0 @@ -import { - MaybeAsync, - Result, - Uri, - UriPackageOrWrapper, -} from "@polywrap/core-js"; - -// $start: IResolutionResultCache -/** A ResolutionResultCache cache */ -export interface IResolutionResultCache { - /** get a Result from the cache, given its URI index */ - get(uri: Uri): MaybeAsync | undefined>; - - /** add a Result to the cache, indexed by a URI */ - set(uri: Uri, result: Result): MaybeAsync; -} -// $end diff --git a/packages/js/uri-resolvers/src/cache/IWrapperCache.ts b/packages/js/uri-resolvers/src/cache/IWrapperCache.ts deleted file mode 100644 index 54e5ff83fe..0000000000 --- a/packages/js/uri-resolvers/src/cache/IWrapperCache.ts +++ /dev/null @@ -1,12 +0,0 @@ -import { MaybeAsync, Uri, Wrapper } from "@polywrap/core-js"; - -// $start: IWrapperCache -/** A Wrapper cache */ -export interface IWrapperCache { - /** get a Wrapper from the cache, given its URI index */ - get(uri: Uri): MaybeAsync; - - /** add a Wrapper to the cache, indexed by a URI */ - set(uri: Uri, wrapper: Wrapper): MaybeAsync; -} -// $end diff --git a/packages/js/uri-resolvers/src/cache/RequestSynchronizerResolver.ts b/packages/js/uri-resolvers/src/cache/RequestSynchronizerResolver.ts deleted file mode 100644 index 9b40413051..0000000000 --- a/packages/js/uri-resolvers/src/cache/RequestSynchronizerResolver.ts +++ /dev/null @@ -1,166 +0,0 @@ -import { UriResolver, UriResolverLike } from "../helpers"; - -import { - IUriResolver, - Uri, - CoreClient, - IUriResolutionContext, - UriPackageOrWrapper, -} from "@polywrap/core-js"; -import { Result } from "@polywrap/result"; - -// $start: RequestSynchronizerResolver -/* Uri resolver that synchronizes requests to the same URI - * Multiple requests to the same URI will be resolved only once - * and the result will be cached for subsequent requests (only for the duration of that first request) - * Can use the `shouldIgnoreCache` option to determine whether to ignore the cached request in case of an error - * (default is to use the cache) - */ -export class RequestSynchronizerResolver - implements IUriResolver /* $ */ { - private requestCache: Map< - string, - Promise> - > = new Map(); - - // $start: RequestSynchronizerResolver-constructor - /** - * Construct a RequestSynchronizerResolver - * - * @param resolverToSynchronize - the inner resolve whose resolution will be synchronized - * @param options - the optional options containing the `shouldIgnoreCache` error handler - * */ - constructor( - private resolverToSynchronize: IUriResolver, - private options?: { - shouldIgnoreCache?: (error: TError | undefined) => boolean; - } - ) /* $ */ {} - - // $start: RequestSynchronizerResolver-from - /** - * Create a RequestSynchronizerResolver from a static-resolver-like object - * - * @param resolver - a resolver-like object whose resolution will be synchronized - * @param options - the optional options containing the `shouldIgnoreCache` error handler - * - * @returns a RequestSynchronizerResolver - * */ - static from( - resolver: UriResolverLike, - options?: { - shouldIgnoreCache?: (error: TResolverError | undefined) => boolean; - } - ): RequestSynchronizerResolver /* $ */ { - return new RequestSynchronizerResolver( - UriResolver.from(resolver), - options - ); - } - - // $start: RequestSynchronizerResolver-tryResolveUri - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * Attempts to resolve the URI using each of the aggregated resolvers sequentially. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> /* $ */ { - const subContext = resolutionContext.createSubHistoryContext(); - - const existingRequest = this.requestCache.get(uri.uri); - - if (existingRequest) { - return existingRequest.then( - (result) => { - // In case of an error and the shouldIgnoreCache error handler returns true, we try to resolve the URI again. - if ( - !result.ok && - this.options?.shouldIgnoreCache && - this.options.shouldIgnoreCache(result.error) - ) { - return this.tryResolveUri(uri, client, subContext).then( - trackStep(uri, resolutionContext, subContext) - ); - } - - // Otherwise, we use the cached result. - resolutionContext.trackStep({ - sourceUri: uri, - result, - description: "RequestSynchronizerResolver (Cache)", - }); - - return result; - }, - (error: unknown) => { - // In case of a promise error (not a resolution one) we throw for all of the listeners - throw error; - } - ); - } - - return this.resolveAndCacheRequest(uri, client, subContext).then( - trackStep(uri, resolutionContext, subContext) - ); - } - - /** - * A function that resolves a URI and caches the promise of that resolution for subsequent requests - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - * */ - private resolveAndCacheRequest( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> { - const resolutionRequest = new Promise>( - (resolve, reject) => { - this.resolverToSynchronize - .tryResolveUri(uri, client, resolutionContext) - .then( - (data) => { - // Delete from cache before resolve, so that retries don't get the same promise (that ended) - this.requestCache.delete(uri.uri); - resolve(data); - }, - (error) => { - // Delete from cache before reject, so that retries don't get the same promise (that ended) - this.requestCache.delete(uri.uri); - reject(error); - } - ); - } - ); - - this.requestCache.set(uri.uri, resolutionRequest); - - return resolutionRequest; - } -} - -const trackStep = ( - uri: Uri, - resolutionContext: IUriResolutionContext, - subContext: IUriResolutionContext -) => (result: Result) => { - resolutionContext.trackStep({ - sourceUri: uri, - result, - subHistory: subContext.getHistory(), - description: "RequestSynchronizerResolver", - }); - - return result; -}; diff --git a/packages/js/uri-resolvers/src/cache/ResolutionResultCache.ts b/packages/js/uri-resolvers/src/cache/ResolutionResultCache.ts deleted file mode 100644 index e0d43f0b30..0000000000 --- a/packages/js/uri-resolvers/src/cache/ResolutionResultCache.ts +++ /dev/null @@ -1,24 +0,0 @@ -import { IResolutionResultCache } from "./IResolutionResultCache"; - -import { Uri, Result, UriPackageOrWrapper } from "@polywrap/core-js"; - -// $start: ResolutionResultCache -/** - * A minimal implementation of IResolutionResultCache - * */ -export class ResolutionResultCache - implements IResolutionResultCache /* $ */ { - private _map: Map> = new Map(); - - // $start: ResolutionResultCache-get - /** get a Result from the cache, given its URI index */ - get(uri: Uri): Result | undefined /* $ */ { - return this._map.get(uri.uri); - } - - // $start: ResolutionResultCache-set - /** add a Result to the cache, indexed by a URI */ - set(uris: Uri, result: Result): void /* $ */ { - this._map.set(uris.uri, result); - } -} diff --git a/packages/js/uri-resolvers/src/cache/ResolutionResultCacheResolver.ts b/packages/js/uri-resolvers/src/cache/ResolutionResultCacheResolver.ts deleted file mode 100644 index 077242ed90..0000000000 --- a/packages/js/uri-resolvers/src/cache/ResolutionResultCacheResolver.ts +++ /dev/null @@ -1,106 +0,0 @@ -import { IResolutionResultCache } from "./IResolutionResultCache"; -import { UriResolver, UriResolverLike } from "../helpers"; - -import { - IUriResolver, - Uri, - CoreClient, - IUriResolutionContext, - UriPackageOrWrapper, -} from "@polywrap/core-js"; -import { Result } from "@polywrap/result"; - -// $start: ResolutionResultCacheResolver -/** - * An IUriResolver implementation that caches the URI resolution result. - * The URI resolution result can be a URI, IWrapPackage, Wrapper or Error. - * Errors are not cached by default and can be cached by setting the cacheErrors option to true. - * The ResolutionResultCacheResolver wraps an IUriResolver implementation and delegates resolution to it. - * */ -export class ResolutionResultCacheResolver - implements IUriResolver /* $ */ { - // $start: ResolutionResultCacheResolver-constructor - /** - * Creates a ResolutionResultCacheResolver - * - * @param _innerResolver - a resolver to delegate resolution to - * @param _cache - a resolution result cache - * @param options - cacheErrors (default: false) - * */ - constructor( - private _innerResolver: IUriResolver, - private _cache: IResolutionResultCache, - private _options: { cacheErrors: boolean } = { cacheErrors: false } - ) /* $ */ {} - - // $start: ResolutionResultCacheResolver-from - /** - * Creates a ResolutionResultCacheResolver from a resolver-like object - * - * @param innerResolver - a resolver-like item to delegate resolution to - * @param cache - a resolution result cache - * @param options - cacheErrors (default: false) - * - * @returns a ResolutionResultCacheResolver - * */ - static from( - innerResolver: UriResolverLike, - cache: IResolutionResultCache, - options: { cacheErrors: boolean } = { cacheErrors: false } - ): ResolutionResultCacheResolver /* $ */ { - return new ResolutionResultCacheResolver( - UriResolver.from(innerResolver), - cache, - options - ); - } - - // $start: ResolutionResultCacheResolver-tryResolveUri - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * If successful, cache the result. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> /* $ */ { - const cachedResult = await this._cache.get(uri); - - // Return from cache if available - if (cachedResult) { - resolutionContext.trackStep({ - sourceUri: uri, - result: cachedResult, - description: "ResolutionResultCacheResolver (Cache)", - }); - return cachedResult; - } - - // Resolve URI if not in cache - const subContext = resolutionContext.createSubHistoryContext(); - - const result = await this._innerResolver.tryResolveUri( - uri, - client, - subContext - ); - - if (result.ok || this._options.cacheErrors) { - await this._cache.set(uri, result); - } - - resolutionContext.trackStep({ - sourceUri: uri, - result, - subHistory: subContext.getHistory(), - description: "ResolutionResultCacheResolver", - }); - return result; - } -} diff --git a/packages/js/uri-resolvers/src/cache/WrapperCache.ts b/packages/js/uri-resolvers/src/cache/WrapperCache.ts deleted file mode 100644 index 2f84a2a982..0000000000 --- a/packages/js/uri-resolvers/src/cache/WrapperCache.ts +++ /dev/null @@ -1,23 +0,0 @@ -import { IWrapperCache } from "./IWrapperCache"; - -import { Wrapper, Uri } from "@polywrap/core-js"; - -// $start: WrapperCache -/** - * A minimal implementation of IWrapperCache - * */ -export class WrapperCache implements IWrapperCache /* $ */ { - private _map: Map = new Map(); - - // $start: WrapperCache-get - /** get a Wrapper from the cache, given its URI index */ - get(uri: Uri): Wrapper | undefined /* $ */ { - return this._map.get(uri.uri); - } - - // $start: WrapperCache-set - /** add a Wrapper to the cache, indexed by a URI */ - set(uris: Uri, wrapper: Wrapper): void /* $ */ { - this._map.set(uris.uri, wrapper); - } -} diff --git a/packages/js/uri-resolvers/src/cache/WrapperCacheResolver.ts b/packages/js/uri-resolvers/src/cache/WrapperCacheResolver.ts deleted file mode 100644 index e7128caaeb..0000000000 --- a/packages/js/uri-resolvers/src/cache/WrapperCacheResolver.ts +++ /dev/null @@ -1,111 +0,0 @@ -import { IWrapperCache } from "./IWrapperCache"; -import { UriResolutionResult, UriResolver, UriResolverLike } from "../helpers"; - -import { - IUriResolver, - Uri, - CoreClient, - IUriResolutionContext, - UriPackageOrWrapper, -} from "@polywrap/core-js"; -import { Result } from "@polywrap/result"; - -// $start: WrapperCacheResolver -/** - * An IUriResolver implementation that caches wrappers once they are resolved. - * As it is a wrapper cache resolver, URI and package caching is outside of the scope for this resolver - * and can be achieved through other resolvers if necessary. - * The WrapperCacheResolver wraps an IUriResolver implementation and delegates resolution to it. - * */ -export class WrapperCacheResolver - implements IUriResolver /* $ */ { - // $start: WrapperCacheResolver-constructor - /** - * Creates a WrapperCacheResolver - * - * @param _innerResolver - a resolver to delegate resolution to - * @param _cache - a wrapper cache - * */ - constructor( - private _innerResolver: IUriResolver, - private _cache: IWrapperCache - ) /* $ */ {} - - // $start: WrapperCacheResolver-from - /** - * Creates a WrapperCacheResolver from a resolver-like object - * - * @param innerResolver - a resolver-like item to delegate resolution to - * @param cache - a wrapper cache - * @param options - control wrapper manifest deserialization - * - * @returns a WrapperCacheResolver - * */ - static from( - innerResolver: UriResolverLike, - cache: IWrapperCache - ): WrapperCacheResolver /* $ */ { - return new WrapperCacheResolver( - UriResolver.from(innerResolver), - cache - ); - } - - // $start: WrapperCacheResolver-tryResolveUri - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * If successful, cache the result. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> /* $ */ { - const wrapper = await this._cache.get(uri); - - // Return from cache if available - if (wrapper) { - const result = UriResolutionResult.ok(uri, wrapper); - - resolutionContext.trackStep({ - sourceUri: uri, - result, - description: "WrapperCacheResolver (Cache)", - }); - return result; - } - - // Resolve URI if not in cache - const subContext = resolutionContext.createSubHistoryContext(); - - const result = await this._innerResolver.tryResolveUri( - uri, - client, - subContext - ); - - if (result.ok && result.value.type === "wrapper") { - const wrapper = result.value.wrapper; - const resolutionPath: Uri[] = subContext.getResolutionPath(); - - for (const uri of resolutionPath) { - await this._cache.set(uri, wrapper); - } - - await this._cache.set(result.value.uri, wrapper); - } - - resolutionContext.trackStep({ - sourceUri: uri, - result, - subHistory: subContext.getHistory(), - description: "WrapperCacheResolver", - }); - return result; - } -} diff --git a/packages/js/uri-resolvers/src/cache/index.ts b/packages/js/uri-resolvers/src/cache/index.ts deleted file mode 100644 index 11f00c5a64..0000000000 --- a/packages/js/uri-resolvers/src/cache/index.ts +++ /dev/null @@ -1,7 +0,0 @@ -export * from "./WrapperCacheResolver"; -export * from "./RequestSynchronizerResolver"; -export * from "./IWrapperCache"; -export * from "./WrapperCache"; -export * from "./ResolutionResultCacheResolver"; -export * from "./IResolutionResultCache"; -export * from "./ResolutionResultCache"; diff --git a/packages/js/uri-resolvers/src/helpers/InfiniteLoopError.ts b/packages/js/uri-resolvers/src/helpers/InfiniteLoopError.ts deleted file mode 100644 index fbf87b47d8..0000000000 --- a/packages/js/uri-resolvers/src/helpers/InfiniteLoopError.ts +++ /dev/null @@ -1,27 +0,0 @@ -import { getUriResolutionPath } from "./getUriResolutionPath"; - -import { Uri, IUriResolutionStep } from "@polywrap/core-js"; - -// $start: InfiniteLoopError -/** - * Error used if the URI resolution path contains an infinite loop - * */ -export class InfiniteLoopError extends Error /* $ */ { - // $start: InfiniteLoopError-constructor - /** - * Create an InfiniteLoopError - * - * @param _uri - URI being resolved - * @param _history - URI resolution history - * */ - constructor( - private readonly _uri: Uri, - private readonly _history: IUriResolutionStep[] - ) /* $ */ { - super(); - } - - message = `An infinite loop was detected while resolving the URI: ${ - this._uri.uri - }\nHistory: ${JSON.stringify(getUriResolutionPath(this._history), null, 2)}`; -} diff --git a/packages/js/uri-resolvers/src/helpers/RecursiveResolver.ts b/packages/js/uri-resolvers/src/helpers/RecursiveResolver.ts deleted file mode 100644 index e111d0fafb..0000000000 --- a/packages/js/uri-resolvers/src/helpers/RecursiveResolver.ts +++ /dev/null @@ -1,102 +0,0 @@ -import { InfiniteLoopError } from "./InfiniteLoopError"; -import { UriResolverLike } from "./UriResolverLike"; -import { UriResolutionResult } from "./UriResolutionResult"; -import { UriResolver } from "./UriResolver"; - -import { Result } from "@polywrap/result"; -import { - IUriResolver, - Uri, - CoreClient, - IUriResolutionContext, - UriPackageOrWrapper, -} from "@polywrap/core-js"; - -// $start: RecursiveResolver -/** - * An IUriResolver implementation that makes the URI resolution process recursive. - * It allows the resolution process to restart when URI redirects are encountered. - * The RecursiveResolver wraps one or more resolvers and delegates resolution to them. - * */ -export class RecursiveResolver - implements IUriResolver /* $ */ { - // $start: RecursiveResolver-constructor - /** - * Construct a RecursiveResolver - * - * @param _resolver - a resolver to delegate resolution to - * */ - constructor(private _resolver: IUriResolver) /* $ */ {} - - // $start: RecursiveResolver-from - /** - * Create a RecursiveResolver from a resolver-like object - * - * @param resolver - a resolver-like item to delegate resolution to - * - * @returns a RecursiveResolver - * */ - static from( - resolver: UriResolverLike - ): RecursiveResolver /* $ */ { - return new RecursiveResolver(UriResolver.from(resolver)); - } - - // $start: RecursiveResolver-tryResolveUri - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * If the URI resolves to a new URI, attempt to resolve thew new URI. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> /* $ */ { - if (resolutionContext.isResolving(uri)) { - return UriResolutionResult.err( - new InfiniteLoopError(uri, resolutionContext.getHistory()) - ); - } - - resolutionContext.startResolving(uri); - - const resolverResult = await this._resolver.tryResolveUri( - uri, - client, - resolutionContext - ); - - const result = await this._tryResolveAgainIfRedirect( - resolverResult, - uri, - client, - resolutionContext - ); - - resolutionContext.stopResolving(uri); - - return result; - } - - private async _tryResolveAgainIfRedirect( - result: Result, - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> { - if (result.ok && result.value.type === "uri") { - const resultUri = result.value.uri; - - if (resultUri.uri !== uri.uri) { - result = await this.tryResolveUri(resultUri, client, resolutionContext); - } - } - - return result; - } -} diff --git a/packages/js/uri-resolvers/src/helpers/ResolverWithHistory.ts b/packages/js/uri-resolvers/src/helpers/ResolverWithHistory.ts deleted file mode 100644 index 95ec58a9e4..0000000000 --- a/packages/js/uri-resolvers/src/helpers/ResolverWithHistory.ts +++ /dev/null @@ -1,76 +0,0 @@ -import { - IUriResolver, - Uri, - CoreClient, - IUriResolutionContext, - UriPackageOrWrapper, -} from "@polywrap/core-js"; -import { Result } from "@polywrap/result"; - -// $start: ResolverWithHistory -/** An abstract IUriResolver implementation that updates the resolution context */ -export abstract class ResolverWithHistory - implements IUriResolver /* $ */ { - // $start: ResolverWithHistory-tryResolveUri - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * Updates the resolution context with the result. - * - * @remarks - * This method calls the internal abstract method _tryResolveUri before - * updating the resolution context. Implementations are expect to place - * resolution logic in _tryResolveUri. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> /* $ */ { - const result = await this._tryResolveUri(uri, client, resolutionContext); - - resolutionContext.trackStep({ - sourceUri: uri, - result, - description: this.getStepDescription(uri, result), - }); - - return result; - } - - // $start: ResolverWithHistory-getStepDescription - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @param uri - the URI being resolved - * @param result - the result of a resolution attempt - * - * @returns text describing the URI resolution step - * */ - protected abstract getStepDescription( - uri: Uri, - result: Result - ): string; - // $end - - // $start: ResolverWithHistory-_tryResolveUri - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * Updates the resolution context with the result. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - protected abstract _tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise>; - // $end -} diff --git a/packages/js/uri-resolvers/src/helpers/ResolverWithLoopGuard.ts b/packages/js/uri-resolvers/src/helpers/ResolverWithLoopGuard.ts deleted file mode 100644 index c1af045c43..0000000000 --- a/packages/js/uri-resolvers/src/helpers/ResolverWithLoopGuard.ts +++ /dev/null @@ -1,76 +0,0 @@ -import { InfiniteLoopError } from "./InfiniteLoopError"; -import { UriResolverLike } from "./UriResolverLike"; -import { UriResolutionResult } from "./UriResolutionResult"; -import { UriResolver } from "./UriResolver"; - -import { - IUriResolver, - Uri, - CoreClient, - IUriResolutionContext, - UriPackageOrWrapper, -} from "@polywrap/core-js"; -import { Result } from "@polywrap/result"; - -// $start: ResolverWithLoopGuard -/** An IUriResolver implementation that prevents infinite loops in the resolution path. */ -export class ResolverWithLoopGuard - implements IUriResolver /* $ */ { - // $start: ResolverWithLoopGuard-constructor - /** - * Construct a ResolverWithLoopGuard - * - * @param _resolver - a resolution to delegate resolution to - * */ - constructor(private _resolver: IUriResolver) /* $ */ {} - - // $start: ResolverWithLoopGuard-from - /** - * Create a ResolverWithLoopGuard from a resolver-like object - * - * @param resolver - a resolver-like item to delegate resolution to - * - * @returns a ResolverWithLoopGuard - * */ - static from( - resolver: UriResolverLike - ): ResolverWithLoopGuard /* $ */ { - return new ResolverWithLoopGuard( - UriResolver.from(resolver) - ); - } - - // $start: ResolverWithLoopGuard-tryResolveUri - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * Ensures the URI is not caught in an infinite loop by checking if it is already resolving. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> /* $ */ { - if (resolutionContext.isResolving(uri)) { - return UriResolutionResult.err( - new InfiniteLoopError(uri, resolutionContext.getHistory()) - ); - } - - resolutionContext.startResolving(uri); - - const result = await this._resolver.tryResolveUri( - uri, - client, - resolutionContext - ); - - resolutionContext.stopResolving(uri); - - return result; - } -} diff --git a/packages/js/uri-resolvers/src/helpers/UriResolutionResult.ts b/packages/js/uri-resolvers/src/helpers/UriResolutionResult.ts deleted file mode 100644 index af836bcc7b..0000000000 --- a/packages/js/uri-resolvers/src/helpers/UriResolutionResult.ts +++ /dev/null @@ -1,78 +0,0 @@ -import { - UriPackageOrWrapper, - IUriResolutionStep, - Uri, - IWrapPackage, - Wrapper, -} from "@polywrap/core-js"; -import { Result, ResultOk, ResultErr } from "@polywrap/result"; - -// $start: UriResolutionResult -/** Factory for creating Result from URI resolution output */ -export class UriResolutionResult /* $ */ { - // TODO: are the result and history fields ever assigned or used? - public result: Result; - public history?: IUriResolutionStep[]; - - // $start: UriResolutionResult-ok - /** Returns a Result with `ok` set to true */ - static ok(uri: Uri): Result; - static ok( - uri: Uri, - wrapPackage: IWrapPackage - ): Result; - static ok( - uri: Uri, - wrapper: Wrapper - ): Result; - static ok( - uriPackageOrWrapper: UriPackageOrWrapper - ): Result; - static ok( - uriPackageOrWrapper: Uri | UriPackageOrWrapper, - packageOrWrapper?: IWrapPackage | Wrapper - ): Result /* $ */ { - if (!packageOrWrapper) { - if ((uriPackageOrWrapper as UriPackageOrWrapper).type) { - return ResultOk(uriPackageOrWrapper as UriPackageOrWrapper); - } else { - return ResultOk({ - type: "uri", - uri: uriPackageOrWrapper as Uri, - } as UriPackageOrWrapper); - } - } - - const uri = uriPackageOrWrapper as Uri; - - const wrapPackage = packageOrWrapper as Partial; - - if (wrapPackage.createWrapper) { - return ResultOk({ - type: "package", - uri, - package: wrapPackage as IWrapPackage, - } as UriPackageOrWrapper); - } - - const wrapper = packageOrWrapper as Partial; - - if (wrapper.invoke) { - return ResultOk({ - type: "wrapper", - uri, - wrapper: wrapper as Wrapper, - } as UriPackageOrWrapper); - } - - throw new Error("Unexpected type when creating UriResolutionResponse"); - } - - // $start: UriResolutionResult-err - /** Returns a Result with `ok` set to false */ - static err( - error: TError - ): Result /* $ */ { - return ResultErr(error); - } -} diff --git a/packages/js/uri-resolvers/src/helpers/UriResolver.ts b/packages/js/uri-resolvers/src/helpers/UriResolver.ts deleted file mode 100644 index a87fdcb513..0000000000 --- a/packages/js/uri-resolvers/src/helpers/UriResolver.ts +++ /dev/null @@ -1,79 +0,0 @@ -import { UriResolverAggregator } from "../aggregator"; -import { PackageResolver } from "../packages"; -import { WrapperResolver } from "../wrappers"; -import { UriResolverLike } from "."; -import { RedirectResolver } from "../redirects"; - -import { Result } from "@polywrap/result"; -import { - IUriResolver, - Uri, - CoreClient, - IUriRedirect, - IUriPackage, - IUriWrapper, -} from "@polywrap/core-js"; - -// $start: UriResolver -/** An IUriResolver factory */ -export class UriResolver /* $ */ { - // $start: UriResolver-from - /** - * Create an IUriResolver instance - * - * @param resolverLike - an object that can be transformed into a resolver - * @param resolverName - a name to assign to the resolver in resolution history output - * */ - static from( - resolverLike: UriResolverLike, - resolverName?: string - ): IUriResolver /* $ */ { - if (Array.isArray(resolverLike)) { - return new UriResolverAggregator( - (resolverLike as UriResolverLike[]).map((x) => - UriResolver.from(x, resolverName) - ), - resolverName - ) as IUriResolver; - } else if (typeof resolverLike === "function") { - return new UriResolverAggregator( - resolverLike as ( - uri: Uri, - client: CoreClient - ) => Promise>, - resolverName - ) as IUriResolver; - } else if ((resolverLike as IUriResolver).tryResolveUri !== undefined) { - return resolverLike as IUriResolver; - } else if ( - (resolverLike as IUriRedirect).from !== undefined && - (resolverLike as IUriRedirect).to !== undefined - ) { - const uriRedirect = resolverLike as IUriRedirect; - return (new RedirectResolver( - uriRedirect.from, - uriRedirect.to - ) as unknown) as IUriResolver; - } else if ( - (resolverLike as IUriPackage).uri !== undefined && - (resolverLike as IUriPackage).package !== undefined - ) { - const uriPackage = resolverLike as IUriPackage; - return (new PackageResolver( - Uri.from(uriPackage.uri), - uriPackage.package - ) as unknown) as IUriResolver; - } else if ( - (resolverLike as IUriWrapper).uri !== undefined && - (resolverLike as IUriWrapper).wrapper !== undefined - ) { - const uriWrapper = resolverLike as IUriWrapper; - return (new WrapperResolver( - Uri.from(uriWrapper.uri), - uriWrapper.wrapper - ) as unknown) as IUriResolver; - } else { - throw new Error("Unknown resolver-like type"); - } - } -} diff --git a/packages/js/uri-resolvers/src/helpers/UriResolverLike.ts b/packages/js/uri-resolvers/src/helpers/UriResolverLike.ts deleted file mode 100644 index ef8b818aa2..0000000000 --- a/packages/js/uri-resolvers/src/helpers/UriResolverLike.ts +++ /dev/null @@ -1,20 +0,0 @@ -import { - IUriResolver, - IUriRedirect, - IUriPackage, - IUriWrapper, -} from "@polywrap/core-js"; - -// $start: UriResolverLike -/** An UriResolverLike can be one of three things: - * - An IUriResolver - * - An object that can be transformed into a static IUriResolver - * - An array of UriResolverLike - * */ -export type UriResolverLike = - | IUriResolver - | IUriRedirect - | IUriPackage - | IUriWrapper - | UriResolverLike[]; -// $end diff --git a/packages/js/uri-resolvers/src/helpers/getUriResolutionPath.ts b/packages/js/uri-resolvers/src/helpers/getUriResolutionPath.ts deleted file mode 100644 index 8509892cba..0000000000 --- a/packages/js/uri-resolvers/src/helpers/getUriResolutionPath.ts +++ /dev/null @@ -1,49 +0,0 @@ -import { IUriResolutionStep } from "@polywrap/core-js"; - -// $start: getUriResolutionPath -/** - * Get a resolution path from the history of a URI resolution attempt - * - * @param history - the resolution context - * @returns the URI's resolution path - * */ -export const getUriResolutionPath = ( - history: IUriResolutionStep[] -): IUriResolutionStep[] /* $ */ => { - // Get all non-empty items from the resolution history - return ( - history - .filter((x) => { - // If a failure happened - if (!x.result.ok) { - return true; - } - - const uriPackageOrWrapper = x.result.value; - - if (uriPackageOrWrapper.type === "uri") { - // If a redirect has occured - return uriPackageOrWrapper.uri.uri !== x.sourceUri.uri; - } else if (uriPackageOrWrapper.type === "package") { - // If a package was returned - return true; - } else if (uriPackageOrWrapper.type === "wrapper") { - // If a wrapper was returned - return true; - } - - return false; - }) - // Filter all sub-history - .map((x) => { - if (x.subHistory && x.subHistory.length) { - return { - ...x, - subHistory: getUriResolutionPath(x.subHistory), - }; - } else { - return x; - } - }) - ); -}; diff --git a/packages/js/uri-resolvers/src/helpers/index.ts b/packages/js/uri-resolvers/src/helpers/index.ts deleted file mode 100644 index def176891b..0000000000 --- a/packages/js/uri-resolvers/src/helpers/index.ts +++ /dev/null @@ -1,8 +0,0 @@ -export * from "./UriResolutionResult"; -export * from "./UriResolverLike"; -export * from "./ResolverWithHistory"; -export * from "./InfiniteLoopError"; -export * from "./RecursiveResolver"; -export * from "./ResolverWithLoopGuard"; -export * from "./UriResolver"; -export * from "./getUriResolutionPath"; diff --git a/packages/js/uri-resolvers/src/index.ts b/packages/js/uri-resolvers/src/index.ts deleted file mode 100644 index 91de24cf22..0000000000 --- a/packages/js/uri-resolvers/src/index.ts +++ /dev/null @@ -1,7 +0,0 @@ -export * from "./aggregator"; -export * from "./cache"; -export * from "./redirects"; -export * from "./packages"; -export * from "./wrappers"; -export * from "./helpers"; -export * from "./static"; diff --git a/packages/js/uri-resolvers/src/packages/PackageResolver.ts b/packages/js/uri-resolvers/src/packages/PackageResolver.ts deleted file mode 100644 index 396d72d797..0000000000 --- a/packages/js/uri-resolvers/src/packages/PackageResolver.ts +++ /dev/null @@ -1,48 +0,0 @@ -import { ResolverWithHistory, UriResolutionResult } from "../helpers"; - -import { Uri, IWrapPackage, UriPackageOrWrapper } from "@polywrap/core-js"; -import { Result } from "@polywrap/result"; - -// $start: PackageResolver -/** - * A Uri Resolver that resolves to an embedded wrap package and correctly updates - * the resolution history. - * */ -export class PackageResolver extends ResolverWithHistory /* $ */ { - // $start: PackageResolver-constructor - /** - * Construct a PackageResolver - * - * @param _uri - the URI to redirect to the wrap package - * @param wrapPackage - a wrap package - * */ - constructor(private _uri: Uri, private wrapPackage: IWrapPackage) /* $ */ { - super(); - } - - // $start: PackageResolver-getStepDescription - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @returns text describing the URI resolution step - * */ - protected getStepDescription = (): string /* $ */ => - `Package (${this._uri.uri})`; - - // $start: PackageResolver-_tryResolveUri - /** - * Resolve a URI to a wrap package - * - * @param uri - the URI to resolve - * @returns A Promise with a Result containing a wrap package if successful - */ - protected async _tryResolveUri( - uri: Uri - ): Promise> /* $ */ { - if (uri.uri !== this._uri.uri) { - return UriResolutionResult.ok(uri); - } - - return UriResolutionResult.ok(uri, this.wrapPackage); - } -} diff --git a/packages/js/uri-resolvers/src/packages/PackageToWrapperResolver.ts b/packages/js/uri-resolvers/src/packages/PackageToWrapperResolver.ts deleted file mode 100644 index b22ba74992..0000000000 --- a/packages/js/uri-resolvers/src/packages/PackageToWrapperResolver.ts +++ /dev/null @@ -1,100 +0,0 @@ -import { UriResolutionResult, UriResolver, UriResolverLike } from "../helpers"; - -import { - IUriResolver, - Uri, - CoreClient, - IUriResolutionContext, - UriPackageOrWrapper, -} from "@polywrap/core-js"; -import { DeserializeManifestOptions } from "@polywrap/wrap-manifest-types-js"; -import { Result } from "@polywrap/result"; - -// $start: PackageToWrapperResolver -/** - * An IUriResolver implementation that initalizes wrappers from resolved packages. - * The PackageToWrapperResolver wraps an IUriResolver implementation and delegates resolution to it. - * */ -export class PackageToWrapperResolver - implements IUriResolver /* $ */ { - // $start: PackageToWrapperResolver-constructor - /** - * Creates a PackageToWrapperResolver - * - * @param _innerResolver - a resolver to delegate resolution to - * @param _options - control wrapper manifest deserialization - * */ - constructor( - private _innerResolver: IUriResolver, - private _options?: { - deserializeManifestOptions?: DeserializeManifestOptions; - } - ) /* $ */ {} - - // $start: PackageToWrapperResolver-from - /** - * Creates a PackageToWrapperResolver from a resolver-like object - * - * @param innerResolver - a resolver-like item to delegate resolution to - * @param options - control wrapper manifest deserialization - * - * @returns a PackageToWrapperResolver - * */ - static from( - innerResolver: UriResolverLike, - options?: { deserializeManifestOptions?: DeserializeManifestOptions } - ): PackageToWrapperResolver /* $ */ { - return new PackageToWrapperResolver( - UriResolver.from(innerResolver), - options - ); - } - - // $start: PackageToWrapperResolver-tryResolveUri - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * If successful, cache the result. - * - * @param uri - the URI to resolve - * @param client - a CoreClient instance that may be used to invoke a wrapper that implements the UriResolver interface - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - client: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> /* $ */ { - const subContext = resolutionContext.createSubHistoryContext(); - - let result = await this._innerResolver.tryResolveUri( - uri, - client, - subContext - ); - - if (result.ok && result.value.type === "package") { - const wrapPackage = result.value.package; - - const createResult = await wrapPackage.createWrapper({ - noValidate: this._options?.deserializeManifestOptions?.noValidate, - }); - - if (!createResult.ok) { - return createResult; - } - - const wrapper = createResult.value; - - result = UriResolutionResult.ok(result.value.uri, wrapper); - } - - resolutionContext.trackStep({ - sourceUri: uri, - result, - subHistory: subContext.getHistory(), - description: "PackageToWrapperResolver", - }); - return result; - } -} diff --git a/packages/js/uri-resolvers/src/packages/index.ts b/packages/js/uri-resolvers/src/packages/index.ts deleted file mode 100644 index 3f5e5c0fad..0000000000 --- a/packages/js/uri-resolvers/src/packages/index.ts +++ /dev/null @@ -1,2 +0,0 @@ -export * from "./PackageResolver"; -export * from "./PackageToWrapperResolver"; diff --git a/packages/js/uri-resolvers/src/redirects/RedirectResolver.ts b/packages/js/uri-resolvers/src/redirects/RedirectResolver.ts deleted file mode 100644 index 4124b625a9..0000000000 --- a/packages/js/uri-resolvers/src/redirects/RedirectResolver.ts +++ /dev/null @@ -1,55 +0,0 @@ -import { ResolverWithHistory, UriResolutionResult } from "../helpers"; - -import { Uri, UriPackageOrWrapper } from "@polywrap/core-js"; -import { Result } from "@polywrap/result"; - -// $start: RedirectResolver -/** - * A Uri Resolver that resolves to a new URI and correctly updates the - * resolution history. - * */ -export class RedirectResolver< - TUri extends string | Uri = string -> extends ResolverWithHistory /* $ */ { - from: Uri; - to: Uri; - - // $start: RedirectResolver-constructor - /** - * Construct a RedirectResolver - * - * @param from - the URI to redirect from - * @param to - the URI to redirect to - * */ - constructor(from: TUri, to: TUri) /* $ */ { - super(); - this.from = Uri.from(from); - this.to = Uri.from(to); - } - - // $start: RedirectResolver-getStepDescription - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @returns text describing the URI resolution step - * */ - protected getStepDescription = (): string /* $ */ => - `Redirect (${this.from.uri} - ${this.to.uri})`; - - // $start: RedirectResolver-_tryResolveUri - /** - * Resolve a URI to a new URI - * - * @param uri - the URI to resolve - * @returns A Promise with a Result containing a URI if successful - */ - protected async _tryResolveUri( - uri: Uri - ): Promise> /* $ */ { - if (uri.uri !== this.from.uri) { - return UriResolutionResult.ok(uri); - } - - return UriResolutionResult.ok(this.to); - } -} diff --git a/packages/js/uri-resolvers/src/redirects/index.ts b/packages/js/uri-resolvers/src/redirects/index.ts deleted file mode 100644 index f0cb134361..0000000000 --- a/packages/js/uri-resolvers/src/redirects/index.ts +++ /dev/null @@ -1 +0,0 @@ -export * from "./RedirectResolver"; diff --git a/packages/js/uri-resolvers/src/static/StaticResolver.ts b/packages/js/uri-resolvers/src/static/StaticResolver.ts deleted file mode 100644 index d185940743..0000000000 --- a/packages/js/uri-resolvers/src/static/StaticResolver.ts +++ /dev/null @@ -1,136 +0,0 @@ -import { UriResolutionResult, UriResolverLike } from "../helpers"; - -import { - CoreClient, - IUriResolutionContext, - IUriResolver, - Uri, - UriPackageOrWrapper, - IUriRedirect, - IUriPackage, - IUriWrapper, -} from "@polywrap/core-js"; -import { Result } from "@polywrap/result"; - -// $start: StaticResolver -/** - * An IUriResolver implementation that efficiently delegates URI resolution to - * static resolvers--i.e. those that resolve to embedded URIs, Wrappers, and Packages - * */ -export class StaticResolver - implements IUriResolver /* $ */ { - // $start: StaticResolver-constructor - /** - * Construct a Static Resolver - * - * @param uriMap - a mapping of URI to embedded URI, package, or wrapper - * */ - constructor(public uriMap: Map) /* $ */ {} - - // $start: StaticResolver-from - /** - * Create a StaticResolver from a static-resolver-like object - * - * @param staticResolverLikes - an array of resolver-like objects to delegate resolution to - * - * @returns a StaticResolver - * */ - static from( - staticResolverLikes: UriResolverLike[] - ): StaticResolver /* $ */ { - const uriMap = new Map(); - for (const staticResolverLike of staticResolverLikes) { - if (Array.isArray(staticResolverLike)) { - const resolver = StaticResolver.from(staticResolverLike); - for (const [uri, uriPackageOrWrapper] of resolver.uriMap) { - uriMap.set(uri, uriPackageOrWrapper); - } - } else if ( - (staticResolverLike as IUriRedirect).from !== undefined && - (staticResolverLike as IUriRedirect).to !== undefined - ) { - const uriRedirect = staticResolverLike as IUriRedirect; - const from = Uri.from(uriRedirect.from); - - uriMap.set(from.uri, { - type: "uri", - uri: Uri.from(uriRedirect.to), - }); - } else if ( - (staticResolverLike as IUriPackage).uri !== undefined && - (staticResolverLike as IUriPackage).package !== undefined - ) { - const uriPackage = staticResolverLike as IUriPackage; - const uri = Uri.from(uriPackage.uri); - - uriMap.set(uri.uri, { - type: "package", - uri, - package: uriPackage.package, - }); - } else if ( - (staticResolverLike as IUriWrapper).uri !== undefined && - (staticResolverLike as IUriWrapper).wrapper !== undefined - ) { - const uriWrapper = staticResolverLike as IUriWrapper; - const uri = Uri.from(uriWrapper.uri); - - uriMap.set(uri.uri, { - type: "wrapper", - uri, - wrapper: uriWrapper.wrapper, - }); - } else { - throw new Error("Unknown static-resolver-like type provided."); - } - } - - return new StaticResolver(uriMap); - } - - // $start: StaticResolver-tryResolveUri - /** - * Resolve a URI to a wrap package, a wrapper, or a URI. - * - * @param uri - the URI to resolve - * @param _ - not used - * @param resolutionContext - the current URI resolution context - * @returns A Promise with a Result containing either a wrap package, a wrapper, or a URI if successful - */ - async tryResolveUri( - uri: Uri, - _: CoreClient, - resolutionContext: IUriResolutionContext - ): Promise> /* $ */ { - const uriPackageOrWrapper = this.uriMap.get(uri.uri); - - let result: Result; - let description = ""; - - if (uriPackageOrWrapper) { - result = UriResolutionResult.ok(uriPackageOrWrapper); - switch (uriPackageOrWrapper.type) { - case "package": - description = `StaticResolver - Package (${uri.uri})`; - break; - case "wrapper": - description = `StaticResolver - Wrapper (${uri.uri})`; - break; - case "uri": - description = `StaticResolver - Redirect (${uri.uri} - ${uriPackageOrWrapper.uri.uri})`; - break; - } - } else { - result = UriResolutionResult.ok(uri); - description = `StaticResolver - Miss`; - } - - resolutionContext.trackStep({ - sourceUri: uri, - result, - description, - }); - - return result; - } -} diff --git a/packages/js/uri-resolvers/src/static/StaticResolverLike.ts b/packages/js/uri-resolvers/src/static/StaticResolverLike.ts deleted file mode 100644 index 88dacf7978..0000000000 --- a/packages/js/uri-resolvers/src/static/StaticResolverLike.ts +++ /dev/null @@ -1,13 +0,0 @@ -import { IUriRedirect, IUriPackage, IUriWrapper } from "@polywrap/core-js"; - -// $start: StaticResolverLike -/** A StaticResolverLike can be one of two things: - * - An object that can be transformed into a static IUriResolver - * - An array of StaticResolverLike - * */ -export type StaticResolverLike = - | IUriRedirect - | IUriPackage - | IUriWrapper - | StaticResolverLike[]; -// $end diff --git a/packages/js/uri-resolvers/src/static/index.ts b/packages/js/uri-resolvers/src/static/index.ts deleted file mode 100644 index 391b4bf950..0000000000 --- a/packages/js/uri-resolvers/src/static/index.ts +++ /dev/null @@ -1,2 +0,0 @@ -export * from "./StaticResolver"; -export * from "./StaticResolverLike"; diff --git a/packages/js/uri-resolvers/src/wrappers/WrapperResolver.ts b/packages/js/uri-resolvers/src/wrappers/WrapperResolver.ts deleted file mode 100644 index 3820a7a844..0000000000 --- a/packages/js/uri-resolvers/src/wrappers/WrapperResolver.ts +++ /dev/null @@ -1,48 +0,0 @@ -import { ResolverWithHistory, UriResolutionResult } from "../helpers"; - -import { Uri, UriPackageOrWrapper, Wrapper } from "@polywrap/core-js"; -import { Result } from "@polywrap/result"; - -// $start: WrapperResolver -/** - * A Uri Resolver that resolves to an embedded wrapper and correctly updates - * the resolution history. - * */ -export class WrapperResolver extends ResolverWithHistory /* $ */ { - // $start: WrapperResolver-constructor - /** - * Construct a WrapperResolver - * - * @param _uri - the URI to redirect to the wrapper instance - * @param _wrapper - a wrapper - * */ - constructor(private _uri: Uri, private _wrapper: Wrapper) /* $ */ { - super(); - } - - // $start: WrapperResolver-getStepDescription - /** - * A utility function for generating step descriptions to facilitate resolution context updates - * - * @returns text describing the URI resolution step - * */ - protected getStepDescription = (): string /* $ */ => - `Wrapper (${this._uri.uri})`; - - // $start: WrapperResolver-_tryResolveUri - /** - * Resolve a URI to a wrapper - * - * @param uri - the URI to resolve - * @returns A Promise with a Result containing a wrapper if successful - */ - protected async _tryResolveUri( - uri: Uri - ): Promise> /* $ */ { - if (uri.uri !== this._uri.uri) { - return UriResolutionResult.ok(uri); - } - - return UriResolutionResult.ok(uri, this._wrapper); - } -} diff --git a/packages/js/uri-resolvers/src/wrappers/index.ts b/packages/js/uri-resolvers/src/wrappers/index.ts deleted file mode 100644 index e2b4876d3b..0000000000 --- a/packages/js/uri-resolvers/src/wrappers/index.ts +++ /dev/null @@ -1 +0,0 @@ -export * from "./WrapperResolver"; diff --git a/packages/js/uri-resolvers/tsconfig.build.json b/packages/js/uri-resolvers/tsconfig.build.json deleted file mode 100644 index 77aadfdd2f..0000000000 --- a/packages/js/uri-resolvers/tsconfig.build.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "extends": "./tsconfig.json", - "include": [ - "./src/**/*.ts" - ], - "exclude": [ - "./src/**/__tests__" - ] -} diff --git a/packages/js/uri-resolvers/tsconfig.json b/packages/js/uri-resolvers/tsconfig.json deleted file mode 100644 index 5d37204c00..0000000000 --- a/packages/js/uri-resolvers/tsconfig.json +++ /dev/null @@ -1,10 +0,0 @@ -{ - "extends": "../../../tsconfig", - "compilerOptions": { - "outDir": "build" - }, - "include": [ - "./src/**/*.ts" - ], - "exclude": [] -} diff --git a/packages/js/wasm/README.md b/packages/js/wasm/README.md deleted file mode 100644 index 9a2a87b0f2..0000000000 --- a/packages/js/wasm/README.md +++ /dev/null @@ -1,5 +0,0 @@ -# @polywrap/wasm-js - -## Description - -Wasm wrappers diff --git a/packages/js/wasm/jest.config.js b/packages/js/wasm/jest.config.js deleted file mode 100644 index b156259895..0000000000 --- a/packages/js/wasm/jest.config.js +++ /dev/null @@ -1,12 +0,0 @@ -module.exports = { - collectCoverage: true, - preset: 'ts-jest', - testEnvironment: 'node', - testMatch: ["**/?(*.)+(spec|test).[jt]s?(x)"], - modulePathIgnorePatterns: ['./src/__tests__/apis'], - globals: { - 'ts-jest': { - diagnostics: false - } - } -}; diff --git a/packages/js/wasm/package.json b/packages/js/wasm/package.json deleted file mode 100644 index e787490ae6..0000000000 --- a/packages/js/wasm/package.json +++ /dev/null @@ -1,43 +0,0 @@ -{ - "name": "@polywrap/wasm-js", - "description": "Polywrap WASM wrappers", - "version": "0.10.0", - "license": "MIT", - "repository": { - "type": "git", - "url": "https://github.com/polywrap/monorepo.git" - }, - "main": "build/index.js", - "files": [ - "build" - ], - "scripts": { - "build": "rimraf ./build && tsc --project tsconfig.build.json", - "lint": "eslint --color -c ../../../.eslintrc.js src/", - "test": "jest --passWithNoTests --runInBand --verbose", - "test:watch": "yarn test -- --watch" - }, - "dependencies": { - "@polywrap/asyncify-js": "0.10.0", - "@polywrap/core-js": "0.10.0", - "@polywrap/msgpack-js": "0.10.0", - "@polywrap/result": "0.10.0", - "@polywrap/tracing-js": "0.10.0", - "@polywrap/wrap-manifest-types-js": "0.10.0" - }, - "peerDependencies": { - "@polywrap/core-js": "0.10.x" - }, - "devDependencies": { - "@polywrap/cli-js": "0.10.0", - "@types/jest": "26.0.8", - "jest": "26.6.3", - "rimraf": "3.0.2", - "ts-jest": "26.5.4", - "ts-node": "10.9.1", - "typescript": "4.9.5" - }, - "publishConfig": { - "access": "public" - } -} diff --git a/packages/js/wasm/src/IFileReader.ts b/packages/js/wasm/src/IFileReader.ts deleted file mode 100644 index 3d7f868337..0000000000 --- a/packages/js/wasm/src/IFileReader.ts +++ /dev/null @@ -1,5 +0,0 @@ -import { Result } from "@polywrap/result"; - -export interface IFileReader { - readFile(filePath: string): Promise>; -} diff --git a/packages/js/wasm/src/IWasmPackage.ts b/packages/js/wasm/src/IWasmPackage.ts deleted file mode 100644 index d534f69b16..0000000000 --- a/packages/js/wasm/src/IWasmPackage.ts +++ /dev/null @@ -1,6 +0,0 @@ -import { IWrapPackage } from "@polywrap/core-js"; -import { Result } from "@polywrap/result"; - -export interface IWasmPackage extends IWrapPackage { - getWasmModule(): Promise>; -} diff --git a/packages/js/wasm/src/InMemoryFileReader.ts b/packages/js/wasm/src/InMemoryFileReader.ts deleted file mode 100644 index 1546db06ea..0000000000 --- a/packages/js/wasm/src/InMemoryFileReader.ts +++ /dev/null @@ -1,55 +0,0 @@ -import { WRAP_MANIFEST_PATH, WRAP_MODULE_PATH } from "./constants"; -import { IFileReader } from "./IFileReader"; - -import { Result, ResultErr, ResultOk } from "@polywrap/result"; - -export class InMemoryFileReader { - static fromManifest( - manifest: Uint8Array, - baseFileReader: IFileReader - ): IFileReader { - return { - async readFile(filePath: string): Promise> { - if (filePath === WRAP_MANIFEST_PATH) { - return ResultOk(manifest); - } else { - return baseFileReader.readFile(filePath); - } - }, - } as IFileReader; - } - - static fromWasmModule( - wasmModule: Uint8Array, - baseFileReader: IFileReader - ): IFileReader { - return { - async readFile(filePath: string): Promise> { - if (filePath === WRAP_MODULE_PATH) { - return ResultOk(wasmModule); - } else { - return baseFileReader.readFile(filePath); - } - }, - }; - } - static from( - manifest: Uint8Array, - wasmModule: Uint8Array, - baseFileReader?: IFileReader - ): IFileReader { - return { - async readFile(filePath: string): Promise> { - if (filePath === WRAP_MANIFEST_PATH) { - return ResultOk(manifest); - } else if (filePath === WRAP_MODULE_PATH) { - return ResultOk(wasmModule); - } else if (baseFileReader) { - return baseFileReader.readFile(filePath); - } else { - return ResultErr(Error(`File not found at ${filePath}.`)); - } - }, - }; - } -} diff --git a/packages/js/wasm/src/WasmPackage.ts b/packages/js/wasm/src/WasmPackage.ts deleted file mode 100644 index 5e138cfe5a..0000000000 --- a/packages/js/wasm/src/WasmPackage.ts +++ /dev/null @@ -1,80 +0,0 @@ -import { IFileReader } from "./IFileReader"; -import { IWasmPackage } from "./IWasmPackage"; -import { WasmWrapper } from "./WasmWrapper"; -import { WRAP_MODULE_PATH, WRAP_MANIFEST_PATH } from "./constants"; -import { createWasmPackage } from "./helpers/createWasmPackage"; - -import { - deserializeWrapManifest, - WrapManifest, -} from "@polywrap/wrap-manifest-types-js"; -import { GetManifestOptions, Wrapper } from "@polywrap/core-js"; -import { Result, ResultErr, ResultOk } from "@polywrap/result"; - -export class WasmPackage implements IWasmPackage { - constructor(private readonly _fileReader: IFileReader) {} - - static from(manifestBuffer: Uint8Array, wasmModule: Uint8Array): WasmPackage; - static from( - manifestBuffer: Uint8Array, - wasmModule: Uint8Array, - fileReader: IFileReader - ): WasmPackage; - static from(manifestBuffer: Uint8Array, fileReader: IFileReader): WasmPackage; - static from(fileReader: IFileReader): WasmPackage; - static from( - manifestBufferOrFileReader: Uint8Array | IFileReader, - wasmModuleOrFileReader?: Uint8Array | IFileReader, - fileReader?: IFileReader - ): WasmPackage { - return createWasmPackage( - manifestBufferOrFileReader, - wasmModuleOrFileReader, - fileReader - ); - } - - async getManifest( - options?: GetManifestOptions - ): Promise> { - const result = await this._fileReader.readFile(WRAP_MANIFEST_PATH); - - if (!result.ok) { - return result; - } - - const wrapManifest = result.value; - - try { - return ResultOk(await deserializeWrapManifest(wrapManifest, options)); - } catch (e) { - return ResultErr(e); - } - } - - async getWasmModule(): Promise> { - const result = await this._fileReader.readFile(WRAP_MODULE_PATH); - - if (!result.ok) { - return ResultErr( - new Error( - `WasmPackage: Wrapper does not contain a wasm module. ${result.error}` - ) - ); - } - - return result; - } - - async createWrapper( - options?: GetManifestOptions - ): Promise> { - const result = await this.getManifest(options); - - if (!result.ok) { - return result; - } - - return ResultOk(new WasmWrapper(result.value, this._fileReader)); - } -} diff --git a/packages/js/wasm/src/WasmWrapper.ts b/packages/js/wasm/src/WasmWrapper.ts deleted file mode 100644 index ebcc1a35ef..0000000000 --- a/packages/js/wasm/src/WasmWrapper.ts +++ /dev/null @@ -1,277 +0,0 @@ -/* eslint-disable @typescript-eslint/naming-convention */ -import { WrapExports } from "./types"; -import { createImports } from "./imports"; -import { IFileReader } from "./IFileReader"; -import { WRAP_MODULE_PATH } from "./constants"; -import { createWasmWrapper } from "./helpers/createWasmWrapper"; - -import { WrapManifest } from "@polywrap/wrap-manifest-types-js"; -import { msgpackDecode, msgpackEncode } from "@polywrap/msgpack-js"; -import { AsyncWasmInstance } from "@polywrap/asyncify-js"; -import { - CoreClient, - GetFileOptions, - GetManifestOptions, - InvocableResult, - InvokeOptions, - isBuffer, - Wrapper, - WrapError, - WrapErrorCode, - ErrorSource, - typesHandler, -} from "@polywrap/core-js"; -import { Result, ResultErr, ResultOk } from "@polywrap/result"; - -export interface State { - method: string; - args: Uint8Array; - invoke: { - result?: Uint8Array; - error?: string; - }; - subinvoke: { - result?: Uint8Array; - error?: string; - args: unknown[]; - }; - subinvokeImplementation: { - result?: Uint8Array; - error?: string; - args: unknown[]; - }; - invokeResult?: Result; - getImplementationsResult?: Uint8Array; - env: Uint8Array; -} - -const EMPTY_ENCODED_OBJECT = msgpackEncode({}); - -export class WasmWrapper implements Wrapper { - public static requiredExports: readonly string[] = ["_wrap_invoke"]; - - private _wasmModule?: Uint8Array; - - constructor( - private _manifest: WrapManifest, - private _fileReader: IFileReader - ) {} - - static async from( - manifestBuffer: Uint8Array, - wasmModule: Uint8Array, - options?: GetManifestOptions - ): Promise; - static async from( - manifestBuffer: Uint8Array, - wasmModule: Uint8Array, - fileReader: IFileReader, - options?: GetManifestOptions - ): Promise; - static async from( - manifestBuffer: Uint8Array, - fileReader: IFileReader, - options?: GetManifestOptions - ): Promise; - static async from( - fileReader: IFileReader, - options?: GetManifestOptions - ): Promise; - static async from( - manifestBufferOrFileReader: Uint8Array | IFileReader, - wasmModuleOrFileReaderOrManifestOptions?: - | Uint8Array - | IFileReader - | GetManifestOptions, - fileReaderOrManifestOptions?: IFileReader | GetManifestOptions, - manifestOptions?: GetManifestOptions - ): Promise { - return createWasmWrapper( - manifestBufferOrFileReader, - wasmModuleOrFileReaderOrManifestOptions, - fileReaderOrManifestOptions, - manifestOptions - ); - } - - public async getFile( - options: GetFileOptions - ): Promise> { - const { path, encoding } = options; - - const dataResult = await this._fileReader.readFile(path); - - // If nothing is returned, the file was not found - if (!dataResult.ok) { - return ResultErr( - Error(`WasmWrapper: File was not found.\nSubpath: ${path}`) - ); - } - - const data = dataResult.value; - - if (encoding) { - const decoder = new TextDecoder(encoding); - const text = decoder.decode(data); - - if (!text) { - const error = Error( - `WasmWrapper: Decoding the file's bytes array failed.\nBytes: ${data}` - ); - return ResultErr(error); - } - return ResultOk(text); - } - return ResultOk(data); - } - - public getManifest(): WrapManifest { - return this._manifest; - } - - public async invoke( - options: InvokeOptions, - client: CoreClient - ): Promise> { - try { - const { method } = options; - const args = options.args || {}; - const wasmResult = await this._getWasmModule(); - if (!wasmResult.ok) { - const error = new WrapError(wasmResult.error, { - code: WrapErrorCode.WRAPPER_READ_FAIL, - uri: options.uri.uri, - method, - args: JSON.stringify(WasmWrapper._decodeArgs(args), typesHandler, 2), - }); - return ResultErr(error); - } - const wasm = wasmResult.value; - - const state: State = { - invoke: {}, - subinvoke: { - args: [], - }, - subinvokeImplementation: { - args: [], - }, - method, - args: args - ? isBuffer(args) - ? args - : msgpackEncode(args) - : EMPTY_ENCODED_OBJECT, - env: options.env ? msgpackEncode(options.env) : EMPTY_ENCODED_OBJECT, - }; - - const abortWithInvokeAborted = ( - message: string, - source?: ErrorSource - ) => { - const prev = WrapError.parse(message); - const text = prev ? "SubInvocation exception encountered" : message; - throw new WrapError(text, { - code: WrapErrorCode.WRAPPER_INVOKE_ABORTED, - uri: options.uri.uri, - method, - args: JSON.stringify(WasmWrapper._decodeArgs(args), typesHandler, 2), - source, - innerError: prev, - }); - }; - - const abortWithInternalError = (message: string) => { - throw new WrapError(message, { - code: WrapErrorCode.WRAPPER_INTERNAL_ERROR, - uri: options.uri.uri, - method, - args: JSON.stringify(WasmWrapper._decodeArgs(args), typesHandler, 2), - }); - }; - - const memory = AsyncWasmInstance.createMemory({ module: wasm }); - const instance = await AsyncWasmInstance.createInstance({ - module: wasm, - imports: createImports({ - state, - client, - memory, - abortWithInvokeAborted, - abortWithInternalError, - }), - requiredExports: WasmWrapper.requiredExports, - }); - - const exports = instance.exports as WrapExports; - - const result = await exports._wrap_invoke( - state.method.length, - state.args.byteLength, - state.env.byteLength - ); - - const invokeResult = this._processInvokeResult(state, result); - - if (invokeResult.ok) { - return { - ...invokeResult, - encoded: true, - }; - } else { - const error = new WrapError(invokeResult.error, { - code: WrapErrorCode.WRAPPER_INVOKE_FAIL, - uri: options.uri.uri, - method, - args: JSON.stringify(WasmWrapper._decodeArgs(args), typesHandler, 2), - }); - return ResultErr(error); - } - } catch (error) { - return ResultErr(error); - } - } - - private static _decodeArgs( - args: Uint8Array | Record - ): Record { - return args instanceof Uint8Array - ? (msgpackDecode(args) as Record) - : args; - } - - private _processInvokeResult( - state: State, - result: boolean - ): Result { - if (result) { - if (!state.invoke.result) { - return ResultErr("Invoke result is missing."); - } - - return ResultOk(state.invoke.result); - } else { - if (!state.invoke.error) { - return ResultErr("Invoke error is missing."); - } - - return ResultErr(state.invoke.error); - } - } - - private async _getWasmModule(): Promise> { - if (this._wasmModule === undefined) { - const result = await this._fileReader.readFile(WRAP_MODULE_PATH); - - if (!result.ok) { - return ResultErr( - `WasmWrapper: Wrapper does not contain a wasm module. ${result.error}` - ); - } - - this._wasmModule = result.value; - } - - return ResultOk(this._wasmModule); - } -} diff --git a/packages/js/wasm/src/__tests__/in-memory-file-reader.spec.ts b/packages/js/wasm/src/__tests__/in-memory-file-reader.spec.ts deleted file mode 100644 index bdb8c63b5f..0000000000 --- a/packages/js/wasm/src/__tests__/in-memory-file-reader.spec.ts +++ /dev/null @@ -1,129 +0,0 @@ -import { GetPathToTestWrappers } from "@polywrap/test-cases"; -import fs from "fs"; -import { InMemoryFileReader } from "../InMemoryFileReader"; -import { Result, ResultErr, ResultOk } from "@polywrap/result"; -import { WRAP_MANIFEST_PATH, WRAP_MODULE_PATH } from "../constants"; - -jest.setTimeout(200000); - -const wrapperPath = `${GetPathToTestWrappers()}/subinvoke/00-subinvoke/implementations/as`; - -describe("In-memory file reader", () => { - it("can create in-memory file reader from buffers", async () => { - const manifest = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MANIFEST_PATH}` - ); - - const wasmModule = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MODULE_PATH}` - ); - const fileReader = InMemoryFileReader.from(manifest, wasmModule); - - expect(await fileReader.readFile(WRAP_MANIFEST_PATH)).toEqual( - ResultOk(manifest) - ); - expect(await fileReader.readFile(WRAP_MODULE_PATH)).toEqual( - ResultOk(wasmModule) - ); - }); - - it("can create in-memory file reader from manifest and file reader", async () => { - const testEncoded = new TextEncoder().encode("test"); - - const manifest = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MANIFEST_PATH}` - ); - - const wasmModule = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MODULE_PATH}` - ); - - const fileReader = InMemoryFileReader.fromManifest(manifest, { - readFile: async (path: string): Promise> => { - if (path === WRAP_MODULE_PATH) { - return ResultOk(wasmModule); - } else if (path === "test.txt") { - return ResultOk(testEncoded); - } else { - return ResultErr(Error(`File ${path} not found`)); - } - }, - }); - - expect(await fileReader.readFile(WRAP_MANIFEST_PATH)).toEqual( - ResultOk(manifest) - ); - expect(await fileReader.readFile(WRAP_MODULE_PATH)).toEqual( - ResultOk(wasmModule) - ); - expect(await fileReader.readFile("test.txt")).toEqual( - ResultOk(testEncoded) - ); - }); - - it("can create in-memory file reader from wasm module and file reader", async () => { - const testEncoded = new TextEncoder().encode("test"); - - const manifest = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MANIFEST_PATH}` - ); - - const wasmModule = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MODULE_PATH}` - ); - - const fileReader = InMemoryFileReader.fromWasmModule(wasmModule, { - readFile: async (path: string): Promise> => { - if (path === WRAP_MANIFEST_PATH) { - return ResultOk(manifest); - } else if (path === "test.txt") { - return ResultOk(testEncoded); - } else { - return ResultErr(Error(`File ${path} not found`)); - } - }, - }); - - expect(await fileReader.readFile(WRAP_MANIFEST_PATH)).toEqual( - ResultOk(manifest) - ); - expect(await fileReader.readFile(WRAP_MODULE_PATH)).toEqual( - ResultOk(wasmModule) - ); - expect(await fileReader.readFile("test.txt")).toEqual( - ResultOk(testEncoded) - ); - }); - - it("can create in-memory file reader from manifest, wasm module and file reader", async () => { - const testEncoded = new TextEncoder().encode("test"); - - const manifest = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MANIFEST_PATH}` - ); - - const wasmModule = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MODULE_PATH}` - ); - - const fileReader = InMemoryFileReader.from(manifest, wasmModule, { - readFile: async (path: string): Promise> => { - if (path === "test.txt") { - return ResultOk(testEncoded); - } else { - return ResultErr(Error(`File ${path} not found`)); - } - }, - }); - - expect(await fileReader.readFile(WRAP_MANIFEST_PATH)).toEqual( - ResultOk(manifest) - ); - expect(await fileReader.readFile(WRAP_MODULE_PATH)).toEqual( - ResultOk(wasmModule) - ); - expect(await fileReader.readFile("test.txt")).toEqual( - ResultOk(testEncoded) - ); - }); -}); diff --git a/packages/js/wasm/src/__tests__/in-memory-packages.spec.ts b/packages/js/wasm/src/__tests__/in-memory-packages.spec.ts deleted file mode 100644 index f6bd89bff0..0000000000 --- a/packages/js/wasm/src/__tests__/in-memory-packages.spec.ts +++ /dev/null @@ -1,155 +0,0 @@ -import { GetPathToTestWrappers } from "@polywrap/test-cases"; -import fs from "fs"; -import { WasmPackage } from "../WasmPackage"; -import { InMemoryFileReader } from "../InMemoryFileReader"; -import { deserializeWrapManifest } from "@polywrap/wrap-manifest-types-js"; -import { ResultErr, ResultOk } from "@polywrap/result"; -import { WRAP_MANIFEST_PATH, WRAP_MODULE_PATH } from "../constants"; - -jest.setTimeout(200000); - -const wrapperPath = `${GetPathToTestWrappers()}/subinvoke/00-subinvoke/implementations/as`; - -describe("In-memory packages", () => { - it("can create in-memory packages from buffers", async () => { - const manifest = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MANIFEST_PATH}` - ); - const wrapManifest = await deserializeWrapManifest(manifest); - - const wasmModule = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MODULE_PATH}` - ); - const wasmPackage = WasmPackage.from(manifest, wasmModule); - - expect(await wasmPackage.getManifest()).toEqual(ResultOk(wrapManifest)); - expect(await wasmPackage.getWasmModule()).toEqual(ResultOk(wasmModule)); - - const wrapperResult = await wasmPackage.createWrapper(); - - if (!wrapperResult.ok) { - throw wrapperResult.error; - } - - const wrapper = wrapperResult.value; - - expect(wrapManifest).toEqual(wrapper.getManifest()); - expect(await wrapper.getFile({ path: WRAP_MANIFEST_PATH })).toEqual( - ResultOk(manifest) - ); - expect(await wrapper.getFile({ path: WRAP_MODULE_PATH })).toEqual( - ResultOk(wasmModule) - ); - }); - - it("can create in-memory packages from file reader", async () => { - const manifest = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MANIFEST_PATH}` - ); - const wrapManifest = await deserializeWrapManifest(manifest); - - const wasmModule = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MODULE_PATH}` - ); - - const fileReader = InMemoryFileReader.from(manifest, wasmModule); - const wasmPackage = WasmPackage.from(fileReader); - - expect(await wasmPackage.getManifest()).toEqual(ResultOk(wrapManifest)); - expect(await wasmPackage.getWasmModule()).toEqual(ResultOk(wasmModule)); - - const wrapperResult = await wasmPackage.createWrapper(); - - if (!wrapperResult.ok) { - throw wrapperResult.error; - } - - const wrapper = wrapperResult.value; - - expect(wrapManifest).toEqual(wrapper.getManifest()); - expect(await wrapper.getFile({ path: WRAP_MANIFEST_PATH })).toEqual( - ResultOk(manifest) - ); - expect(await wrapper.getFile({ path: WRAP_MODULE_PATH })).toEqual( - ResultOk(wasmModule) - ); - }); - - it("can create in-memory packages from manifest and file reader", async () => { - const manifest = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MANIFEST_PATH}` - ); - const wrapManifest = await deserializeWrapManifest(manifest); - - const wasmModule = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MODULE_PATH}` - ); - - const fileReader = InMemoryFileReader.from(manifest, wasmModule); - const wasmPackage = WasmPackage.from(manifest, fileReader); - - expect(await wasmPackage.getManifest()).toEqual(ResultOk(wrapManifest)); - expect(await wasmPackage.getWasmModule()).toEqual(ResultOk(wasmModule)); - - const wrapperResult = await wasmPackage.createWrapper(); - - if (!wrapperResult.ok) { - throw wrapperResult.error; - } - - const wrapper = wrapperResult.value; - - expect(wrapManifest).toEqual(wrapper.getManifest()); - expect(await wrapper.getFile({ path: WRAP_MANIFEST_PATH })).toEqual( - ResultOk(manifest) - ); - expect(await wrapper.getFile({ path: WRAP_MODULE_PATH })).toEqual( - ResultOk(wasmModule) - ); - }); - - it("can create in-memory packages from manifest, wasm module and file reader", async () => { - const testEncoded = new TextEncoder().encode("test"); - - const manifest = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MANIFEST_PATH}` - ); - const wrapManifest = await deserializeWrapManifest(manifest); - - const wasmModule = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MODULE_PATH}` - ); - - const wasmPackage = WasmPackage.from(manifest, wasmModule, { - readFile: async (path: string) => { - if (path === "test.txt") { - return ResultOk(testEncoded); - } else { - return ResultErr(Error(`File ${path} not found`)); - } - }, - }); - - expect(await wasmPackage.getManifest()).toEqual(ResultOk(wrapManifest)); - expect(await wasmPackage.getWasmModule()).toEqual(ResultOk(wasmModule)); - - const wrapperResult = await wasmPackage.createWrapper(); - - if (!wrapperResult.ok) { - throw wrapperResult.error; - } - - const wrapper = wrapperResult.value; - - expect(wrapManifest).toEqual(wrapper.getManifest()); - expect(await wrapper.getFile({ path: WRAP_MANIFEST_PATH })).toEqual( - ResultOk(manifest) - ); - expect(await wrapper.getFile({ path: WRAP_MODULE_PATH })).toEqual( - ResultOk(wasmModule) - ); - expect(await wrapper.getFile({ path: "test.txt" })).toEqual( - ResultOk(testEncoded) - ); - }); -}); diff --git a/packages/js/wasm/src/__tests__/in-memory-wrappers.spec.ts b/packages/js/wasm/src/__tests__/in-memory-wrappers.spec.ts deleted file mode 100644 index 529cc949e3..0000000000 --- a/packages/js/wasm/src/__tests__/in-memory-wrappers.spec.ts +++ /dev/null @@ -1,111 +0,0 @@ -import { GetPathToTestWrappers } from "@polywrap/test-cases"; -import fs from "fs"; -import { InMemoryFileReader } from "../InMemoryFileReader"; -import { deserializeWrapManifest } from "@polywrap/wrap-manifest-types-js"; -import { WasmWrapper } from "../WasmWrapper"; -import { Result, ResultErr, ResultOk } from "@polywrap/result"; -import { WRAP_MANIFEST_PATH, WRAP_MODULE_PATH } from "../constants"; - -jest.setTimeout(200000); - -const wrapperPath = `${GetPathToTestWrappers()}/subinvoke/00-subinvoke/implementations/as`; - -describe("In-memory wrappers", () => { - it("can create in-memory wrappers from buffers", async () => { - const manifest = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MANIFEST_PATH}` - ); - const wrapManifest = await deserializeWrapManifest(manifest); - - const wasmModule = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MODULE_PATH}` - ); - const wrapper = await WasmWrapper.from(manifest, wasmModule); - - expect(wrapper.getManifest()).toEqual(wrapManifest); - expect(await wrapper.getFile({ path: WRAP_MANIFEST_PATH })).toEqual( - ResultOk(manifest) - ); - expect(await wrapper.getFile({ path: WRAP_MODULE_PATH })).toEqual( - ResultOk(wasmModule) - ); - }); - - it("can create in-memory wrappers from file reader", async () => { - const manifest = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MANIFEST_PATH}` - ); - const wrapManifest = await deserializeWrapManifest(manifest); - - const wasmModule = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MODULE_PATH}` - ); - - const fileReader = InMemoryFileReader.from(manifest, wasmModule); - const wrapper = await WasmWrapper.from(fileReader); - - expect(wrapper.getManifest()).toEqual(wrapManifest); - expect(await wrapper.getFile({ path: WRAP_MANIFEST_PATH })).toEqual( - ResultOk(manifest) - ); - expect(await wrapper.getFile({ path: WRAP_MODULE_PATH })).toEqual( - ResultOk(wasmModule) - ); - }); - - it("can create in-memory wrappers from manifest and file reader", async () => { - const manifest = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MANIFEST_PATH}` - ); - const wrapManifest = await deserializeWrapManifest(manifest); - - const wasmModule = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MODULE_PATH}` - ); - - const fileReader = InMemoryFileReader.from(manifest, wasmModule); - const wrapper = await WasmWrapper.from(manifest, fileReader); - - expect(wrapper.getManifest()).toEqual(wrapManifest); - expect(await wrapper.getFile({ path: WRAP_MANIFEST_PATH })).toEqual( - ResultOk(manifest) - ); - expect(await wrapper.getFile({ path: WRAP_MODULE_PATH })).toEqual( - ResultOk(wasmModule) - ); - }); - - it("can create in-memory wrappers from manifest, wasm module and file reader", async () => { - const testEncoded = new TextEncoder().encode("test"); - - const manifest = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MANIFEST_PATH}` - ); - const wrapManifest = await deserializeWrapManifest(manifest); - - const wasmModule = await fs.promises.readFile( - `${wrapperPath}/${WRAP_MODULE_PATH}` - ); - - const wrapper = await WasmWrapper.from(manifest, wasmModule, { - readFile: async (path: string): Promise> => { - if (path === "test.txt") { - return ResultOk(testEncoded); - } else { - return ResultErr(Error(`File ${path} not found`)); - } - }, - }); - - expect(await wrapper.getManifest()).toEqual(wrapManifest); - expect(await wrapper.getFile({ path: WRAP_MANIFEST_PATH })).toEqual( - ResultOk(manifest) - ); - expect(await wrapper.getFile({ path: WRAP_MODULE_PATH })).toEqual( - ResultOk(wasmModule) - ); - expect(await wrapper.getFile({ path: "test.txt" })).toEqual( - ResultOk(testEncoded) - ); - }); -}); diff --git a/packages/js/wasm/src/buffer.ts b/packages/js/wasm/src/buffer.ts deleted file mode 100644 index 5c5734edf2..0000000000 --- a/packages/js/wasm/src/buffer.ts +++ /dev/null @@ -1,70 +0,0 @@ -/* eslint-disable @typescript-eslint/ban-ts-comment */ -export function writeString( - str: string, - dst: ArrayBuffer, - dstOffset: number -): Uint8Array { - const encoder = new TextEncoder(); - const strBuffer = encoder.encode(str); - const view = new Uint8Array(dst); - return memcpy(strBuffer, 0, view, dstOffset, strBuffer.byteLength); -} - -export function writeBytes( - bytes: ArrayBuffer, - dst: ArrayBuffer, - dstOffset: number -): Uint8Array { - const bytesView = new Uint8Array(bytes); - const dstView = new Uint8Array(dst); - return memcpy(bytesView, 0, dstView, dstOffset, bytesView.byteLength); -} - -export function readBytes( - from: ArrayBuffer, - offset: number, - length: number -): ArrayBuffer { - const buffer = new ArrayBuffer(length); - writeBytes(from.slice(offset, offset + length), buffer, 0); - return buffer; -} - -export function readString( - from: ArrayBuffer, - offset: number, - length: number -): string { - const buffer = readBytes(from, offset, length); - const decoder = new TextDecoder(); - return decoder.decode(buffer); -} - -function memcpy( - src: Uint8Array, - srcOffset: number, - dst: Uint8Array, - dstOffset: number, - length: number -): Uint8Array { - // @ts-ignore - src = (src.subarray || src.slice ? src : src.buffer) as Uint8Array; - // @ts-ignore - dst = (dst.subarray || dst.slice ? dst : dst.buffer) as Uint8Array; - - src = srcOffset - ? src.subarray - ? src.subarray(srcOffset, length && srcOffset + length) - : src.slice(srcOffset, length && srcOffset + length) - : src; - - if (dst.set) { - dst.set(src, dstOffset); - } else { - for (let i = 0; i < src.length; i++) { - dst[i + dstOffset] = src[i]; - } - } - - return dst; -} diff --git a/packages/js/wasm/src/constants.ts b/packages/js/wasm/src/constants.ts deleted file mode 100644 index 2143ae61f3..0000000000 --- a/packages/js/wasm/src/constants.ts +++ /dev/null @@ -1,2 +0,0 @@ -export const WRAP_MANIFEST_PATH = "wrap.info"; -export const WRAP_MODULE_PATH = "wrap.wasm"; diff --git a/packages/js/wasm/src/helpers/createWasmPackage.ts b/packages/js/wasm/src/helpers/createWasmPackage.ts deleted file mode 100644 index 67b909aef5..0000000000 --- a/packages/js/wasm/src/helpers/createWasmPackage.ts +++ /dev/null @@ -1,48 +0,0 @@ -import { IFileReader, WasmPackage, InMemoryFileReader } from ".."; - -// Helper function for creating wasm packages -// Not meant for exporting out of this library -export const createWasmPackage = ( - manifestBufferOrFileReader: Uint8Array | IFileReader, - wasmModuleOrFileReader?: Uint8Array | IFileReader, - fileReader?: IFileReader -): WasmPackage => { - let manifestBuffer: Uint8Array | undefined; - let wasmModule: Uint8Array | undefined; - let builtFileReader: IFileReader | undefined = fileReader; - - if (manifestBufferOrFileReader instanceof Uint8Array) { - manifestBuffer = manifestBufferOrFileReader as Uint8Array; - } else { - builtFileReader = manifestBufferOrFileReader as IFileReader; - } - - if (wasmModuleOrFileReader) { - if (wasmModuleOrFileReader instanceof Uint8Array) { - wasmModule = wasmModuleOrFileReader as Uint8Array; - } else if ((wasmModuleOrFileReader as Partial).readFile) { - builtFileReader = wasmModuleOrFileReader as IFileReader; - } - } - - if (manifestBuffer) { - if (wasmModule) { - return new WasmPackage( - InMemoryFileReader.from( - manifestBuffer, - wasmModule, - builtFileReader as IFileReader - ) - ); - } else { - return new WasmPackage( - InMemoryFileReader.fromManifest( - manifestBuffer, - builtFileReader as IFileReader - ) - ); - } - } else { - return new WasmPackage(builtFileReader as IFileReader); - } -}; diff --git a/packages/js/wasm/src/helpers/createWasmWrapper.ts b/packages/js/wasm/src/helpers/createWasmWrapper.ts deleted file mode 100644 index 15adc3df7d..0000000000 --- a/packages/js/wasm/src/helpers/createWasmWrapper.ts +++ /dev/null @@ -1,59 +0,0 @@ -import { IFileReader, WasmWrapper } from ".."; -import { createWasmPackage } from "./createWasmPackage"; - -import { GetManifestOptions } from "@polywrap/core-js"; - -// Helper function for creating wasm wrappers -// Not meant for exporting out of this library -export const createWasmWrapper = async ( - manifestBufferOrFileReader: Uint8Array | IFileReader, - wasmModuleOrFileReaderOrManifestOptions?: - | Uint8Array - | IFileReader - | GetManifestOptions, - fileReaderOrManifestOptions?: IFileReader | GetManifestOptions, - manifestOptions?: GetManifestOptions -): Promise => { - if ( - !wasmModuleOrFileReaderOrManifestOptions || - (wasmModuleOrFileReaderOrManifestOptions as GetManifestOptions) - .noValidate !== undefined - ) { - const result = await createWasmPackage( - manifestBufferOrFileReader - ).createWrapper( - wasmModuleOrFileReaderOrManifestOptions as GetManifestOptions - ); - - if (!result.ok) { - throw result.error; - } - return result.value as WasmWrapper; - } else if ( - !fileReaderOrManifestOptions || - (fileReaderOrManifestOptions as GetManifestOptions).noValidate !== undefined - ) { - const result = await createWasmPackage( - manifestBufferOrFileReader, - wasmModuleOrFileReaderOrManifestOptions as Uint8Array | IFileReader - ).createWrapper(fileReaderOrManifestOptions as GetManifestOptions); - - if (!result.ok) { - throw result.error; - } - - return result.value as WasmWrapper; - } else { - const result = await createWasmPackage( - manifestBufferOrFileReader, - wasmModuleOrFileReaderOrManifestOptions as Uint8Array, - fileReaderOrManifestOptions as IFileReader - ).createWrapper(manifestOptions); - - if (!result.ok) { - throw result.error; - } - - return result.value as WasmWrapper; - } -}; diff --git a/packages/js/wasm/src/imports.ts b/packages/js/wasm/src/imports.ts deleted file mode 100644 index 6eed941bdd..0000000000 --- a/packages/js/wasm/src/imports.ts +++ /dev/null @@ -1,252 +0,0 @@ -/* eslint-disable @typescript-eslint/naming-convention */ - -import { u32, WrapImports } from "./types"; -import { readBytes, readString, writeBytes, writeString } from "./buffer"; -import { State } from "./WasmWrapper"; - -import { msgpackEncode } from "@polywrap/msgpack-js"; -import { CoreClient, Uri, ErrorSource } from "@polywrap/core-js"; - -export const createImports = (config: { - client: CoreClient; - memory: WebAssembly.Memory; - state: State; - abortWithInvokeAborted: (message: string, source: ErrorSource) => never; - abortWithInternalError: (message: string) => never; -}): WrapImports => { - const { - memory, - state, - client, - abortWithInvokeAborted, - abortWithInternalError, - } = config; - - return { - wrap: { - __wrap_subinvoke: async ( - uriPtr: u32, - uriLen: u32, - methodPtr: u32, - methodLen: u32, - argsPtr: u32, - argsLen: u32 - ): Promise => { - // Reset our state - state.subinvoke.result = undefined; - state.subinvoke.error = undefined; - - const uri = readString(memory.buffer, uriPtr, uriLen); - const method = readString(memory.buffer, methodPtr, methodLen); - const args = readBytes(memory.buffer, argsPtr, argsLen); - - const result = await client.invoke({ - uri: Uri.from(uri), - method: method, - args: new Uint8Array(args), - encodeResult: true, - }); - - if (result.ok) { - state.subinvoke.result = result.value; - } else { - state.subinvoke.error = `${result.error?.name}: ${result.error?.message}`; - } - - return result.ok; - }, - // Give WASM the size of the result - __wrap_subinvoke_result_len: (): u32 => { - if (!state.subinvoke.result) { - abortWithInternalError( - "__wrap_subinvoke_result_len: subinvoke.result is not set" - ); - return 0; - } - return state.subinvoke.result.byteLength; - }, - // Copy the subinvoke result into WASM - __wrap_subinvoke_result: (ptr: u32): void => { - if (!state.subinvoke.result) { - abortWithInternalError( - "__wrap_subinvoke_result: subinvoke.result is not set" - ); - return; - } - writeBytes(state.subinvoke.result, memory.buffer, ptr); - }, - // Give WASM the size of the error - __wrap_subinvoke_error_len: (): u32 => { - if (!state.subinvoke.error) { - abortWithInternalError( - "__wrap_subinvoke_error_len: subinvoke.error is not set" - ); - return 0; - } - return state.subinvoke.error.length; - }, - // Copy the subinvoke error into WASM - __wrap_subinvoke_error: (ptr: u32): void => { - if (!state.subinvoke.error) { - abortWithInternalError( - "__wrap_subinvoke_error: subinvoke.error is not set" - ); - return; - } - writeString(state.subinvoke.error, memory.buffer, ptr); - }, - __wrap_subinvokeImplementation: async ( - interfaceUriPtr: u32, - interfaceUriLen: u32, - implUriPtr: u32, - implUriLen: u32, - methodPtr: u32, - methodLen: u32, - argsPtr: u32, - argsLen: u32 - ): Promise => { - state.subinvokeImplementation.result = undefined; - state.subinvokeImplementation.error = undefined; - - const implUri = readString(memory.buffer, implUriPtr, implUriLen); - const method = readString(memory.buffer, methodPtr, methodLen); - const args = readBytes(memory.buffer, argsPtr, argsLen); - - state.subinvokeImplementation.args = [implUri, method, args]; - - const result = await client.invoke({ - uri: Uri.from(implUri), - method: method, - args: new Uint8Array(args), - encodeResult: true, - }); - - if (result.ok) { - state.subinvokeImplementation.result = result.value; - } else { - state.subinvokeImplementation.error = `${result.error?.name}: ${result.error?.message}`; - } - - return result.ok; - }, - __wrap_subinvokeImplementation_result_len: (): u32 => { - if (!state.subinvokeImplementation.result) { - abortWithInternalError( - "__wrap_subinvokeImplementation_result_len: subinvokeImplementation.result is not set" - ); - return 0; - } - return state.subinvokeImplementation.result.byteLength; - }, - __wrap_subinvokeImplementation_result: (ptr: u32): void => { - if (!state.subinvokeImplementation.result) { - abortWithInternalError( - "__wrap_subinvokeImplementation_result: subinvokeImplementation.result is not set" - ); - return; - } - writeBytes(state.subinvokeImplementation.result, memory.buffer, ptr); - }, - __wrap_subinvokeImplementation_error_len: (): u32 => { - if (!state.subinvokeImplementation.error) { - abortWithInternalError( - "__wrap_subinvokeImplementation_error_len: subinvokeImplementation.error is not set" - ); - return 0; - } - return state.subinvokeImplementation.error.length; - }, - __wrap_subinvokeImplementation_error: (ptr: u32): void => { - if (!state.subinvokeImplementation.error) { - abortWithInternalError( - "__wrap_subinvokeImplementation_error: subinvokeImplementation.error is not set" - ); - return; - } - writeString(state.subinvokeImplementation.error, memory.buffer, ptr); - }, - // Copy the invocation's method & args into WASM - __wrap_invoke_args: (methodPtr: u32, argsPtr: u32): void => { - if (!state.method) { - abortWithInternalError("__wrap_invoke_args: method is not set"); - return; - } - if (!state.args) { - abortWithInternalError("__wrap_invoke_args: args is not set"); - return; - } - writeString(state.method, memory.buffer, methodPtr); - writeBytes(state.args, memory.buffer, argsPtr); - }, - // Store the invocation's result - __wrap_invoke_result: (ptr: u32, len: u32): void => { - state.invoke.result = new Uint8Array( - readBytes(memory.buffer, ptr, len) - ); - }, - // Store the invocation's error - __wrap_invoke_error: (ptr: u32, len: u32): void => { - state.invoke.error = readString(memory.buffer, ptr, len); - }, - __wrap_getImplementations: async ( - uriPtr: u32, - uriLen: u32 - ): Promise => { - const uri = readString(memory.buffer, uriPtr, uriLen); - const result = await client.getImplementations(Uri.from(uri), {}); - if (!result.ok) { - abortWithInternalError(result.error?.message as string); - return false; - } - const implementations = result.value.map((i) => i.uri); - state.getImplementationsResult = msgpackEncode(implementations); - return implementations.length > 0; - }, - __wrap_getImplementations_result_len: (): u32 => { - if (!state.getImplementationsResult) { - abortWithInternalError( - "__wrap_getImplementations_result_len: result is not set" - ); - return 0; - } - return state.getImplementationsResult.byteLength; - }, - __wrap_getImplementations_result: (ptr: u32): void => { - if (!state.getImplementationsResult) { - abortWithInternalError( - "__wrap_getImplementations_result: result is not set" - ); - return; - } - writeBytes(state.getImplementationsResult, memory.buffer, ptr); - }, - __wrap_load_env: (ptr: u32): void => { - writeBytes(state.env, memory.buffer, ptr); - }, - __wrap_abort: ( - msgPtr: u32, - msgLen: u32, - filePtr: u32, - fileLen: u32, - line: u32, - column: u32 - ): void => { - const msg = readString(memory.buffer, msgPtr, msgLen); - const file = readString(memory.buffer, filePtr, fileLen); - - abortWithInvokeAborted(`__wrap_abort: ${msg}`, { - file, - row: line, - col: column, - }); - }, - __wrap_debug_log: (ptr: u32, len: u32): void => { - const msg = readString(memory.buffer, ptr, len); - console.debug(`__wrap_debug_log: ${msg}`); - }, - }, - env: { - memory, - }, - }; -}; diff --git a/packages/js/wasm/src/index.ts b/packages/js/wasm/src/index.ts deleted file mode 100644 index 1309eab0b6..0000000000 --- a/packages/js/wasm/src/index.ts +++ /dev/null @@ -1,7 +0,0 @@ -export { WasmWrapper } from "./WasmWrapper"; -export { WasmPackage } from "./WasmPackage"; -export { IWasmPackage } from "./IWasmPackage"; -export { IFileReader } from "./IFileReader"; -export { InMemoryFileReader } from "./InMemoryFileReader"; -export { WrapImports } from "./types"; -export * from "./constants"; diff --git a/packages/js/wasm/src/types.ts b/packages/js/wasm/src/types.ts deleted file mode 100644 index b34f25c1e6..0000000000 --- a/packages/js/wasm/src/types.ts +++ /dev/null @@ -1,58 +0,0 @@ -/* eslint-disable @typescript-eslint/naming-convention */ -/* eslint-disable @typescript-eslint/ban-types */ - -export type u32 = number; - -export interface WrapExports extends WebAssembly.Exports { - _wrap_invoke: (nameLen: u32, argsLen: u32, envLen: u32) => boolean; -} - -export interface WrapImports extends WebAssembly.Imports { - wrap: { - __wrap_subinvoke: ( - uriPtr: u32, - uriLen: u32, - methodPtr: u32, - methodLen: u32, - argsPtr: u32, - argsLen: u32 - ) => Promise; - __wrap_subinvoke_result_len: () => u32; - __wrap_subinvoke_result: (ptr: u32) => void; - __wrap_subinvoke_error_len: () => u32; - __wrap_subinvoke_error: (ptr: u32) => void; - __wrap_subinvokeImplementation: ( - interfaceUriPtr: u32, - interfaceUriLen: u32, - implUriPtr: u32, - implUriLen: u32, - methodPtr: u32, - methodLen: u32, - argsPtr: u32, - argsLen: u32 - ) => Promise; - __wrap_subinvokeImplementation_result_len: () => u32; - __wrap_subinvokeImplementation_result: (ptr: u32) => void; - __wrap_subinvokeImplementation_error_len: () => u32; - __wrap_subinvokeImplementation_error: (ptr: u32) => void; - __wrap_invoke_args: (methodPtr: u32, argsPtr: u32) => void; - __wrap_invoke_result: (ptr: u32, len: u32) => void; - __wrap_invoke_error: (ptr: u32, len: u32) => void; - __wrap_getImplementations: (uriPtr: u32, uriLen: u32) => Promise; - __wrap_getImplementations_result_len: () => u32; - __wrap_getImplementations_result: (ptr: u32) => void; - __wrap_abort: ( - msgPtr: u32, - msgLen: u32, - filePtr: u32, - fileLen: u32, - line: u32, - column: u32 - ) => void; - __wrap_debug_log: (ptr: u32, len: u32) => void; - __wrap_load_env: (ptr: u32) => void; - }; - env: { - memory: WebAssembly.Memory; - }; -} diff --git a/packages/js/wasm/tsconfig.build.json b/packages/js/wasm/tsconfig.build.json deleted file mode 100644 index 77aadfdd2f..0000000000 --- a/packages/js/wasm/tsconfig.build.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "extends": "./tsconfig.json", - "include": [ - "./src/**/*.ts" - ], - "exclude": [ - "./src/**/__tests__" - ] -} diff --git a/packages/js/wasm/tsconfig.json b/packages/js/wasm/tsconfig.json deleted file mode 100644 index 5d37204c00..0000000000 --- a/packages/js/wasm/tsconfig.json +++ /dev/null @@ -1,10 +0,0 @@ -{ - "extends": "../../../tsconfig", - "compilerOptions": { - "outDir": "build" - }, - "include": [ - "./src/**/*.ts" - ], - "exclude": [] -} diff --git a/scripts/patch-peer-deps.ts b/scripts/patch-peer-deps.ts deleted file mode 100644 index 47153142de..0000000000 --- a/scripts/patch-peer-deps.ts +++ /dev/null @@ -1,26 +0,0 @@ -import rimraf from "rimraf"; -import path from "path"; - -const packagesToPatch = [ - "@polywrap/concurrent-plugin-js", - "@polywrap/ethereum-provider-js-v1", - "@polywrap/ethereum-provider-js", - "@polywrap/file-system-plugin-js", - "@polywrap/http-plugin-js", - "@polywrap/logger-plugin-js" -]; - -function main () { - for (const packageToPatch of packagesToPatch) { - rimraf.sync( - path.join( - __dirname, - "../node_modules", - packageToPatch, - "node_modules/@polywrap/core-js" - ) - ); - } -} - -main(); From fc72b4b8314b482f27eb75e0499f2fc664b5ff62 Mon Sep 17 00:00:00 2001 From: dOrgJelli Date: Wed, 19 Apr 2023 01:26:37 -0500 Subject: [PATCH 16/19] chore: remove test client workflow --- .github/workflows/ci-javascript.yaml | 51 ---------------------------- 1 file changed, 51 deletions(-) diff --git a/.github/workflows/ci-javascript.yaml b/.github/workflows/ci-javascript.yaml index a90d73eeba..6842c26b9b 100644 --- a/.github/workflows/ci-javascript.yaml +++ b/.github/workflows/ci-javascript.yaml @@ -155,57 +155,6 @@ jobs: - name: Test run: yarn test:core - Test-Client: - runs-on: ubuntu-latest - needs: CI-WRAP-Test-Harness - if: ${{ always() }} - timeout-minutes: 60 - steps: - - name: Checkout repository - uses: actions/checkout@v2 - - - name: Read .nvmrc - run: echo ::set-output name=NVMRC::$(cat .nvmrc) - id: nvm - - - name: Setup Node.js - uses: actions/setup-node@master - with: - node-version: '${{ steps.nvm.outputs.NVMRC }}' - - - name: Get yarn cache directory path - id: yarn-cache-dir-path - run: echo "::set-output name=dir::$(yarn cache dir)" - - - uses: actions/cache@v2 - with: - path: ${{ steps.yarn-cache-dir-path.outputs.dir }} - key: ${{ runner.os }}-yarn-${{ hashFiles('**/yarn.lock') }} - restore-keys: | - ${{ runner.os }}-yarn- - - - name: Install dependencies - run: yarn install --nonInteractive --frozen-lockfile --prefer-offline - - - name: Build - run: yarn build - - - name: Get updated wrappers - if: ${{ needs.CI-WRAP-Test-Harness.outputs.rebuild_required == 'true' }} - uses: actions/download-artifact@v3 - id: get-wrappers - with: - name: rebuilt-wrappers - path: ./wrappers - - - if: ${{ needs.CI-WRAP-Test-Harness.outputs.rebuild_required == 'true' }} - run: | - rm -rf packages/test-cases/cases/wrappers - mv wrappers packages/test-cases/cases - - - name: Test - run: yarn test:client - Test-Cli: runs-on: ubuntu-latest needs: CI-WRAP-Test-Harness From 8a03635ac8d894f277067cc9cf69348851fad8e4 Mon Sep 17 00:00:00 2001 From: dOrgJelli Date: Wed, 19 Apr 2023 02:27:26 -0500 Subject: [PATCH 17/19] chore: fix build --- package.json | 3 +- scripts/patch-peer-deps.ts | 28 ++++ yarn.lock | 281 ++++++++++++++++++++----------------- 3 files changed, 186 insertions(+), 126 deletions(-) create mode 100644 scripts/patch-peer-deps.ts diff --git a/package.json b/package.json index fd39ec5b09..41edc88e78 100644 --- a/package.json +++ b/package.json @@ -19,10 +19,11 @@ ] }, "scripts": { + "postinstall": "ts-node ./scripts/patch-peer-deps.ts", "reset": "yarn clean && yarn && yarn build", "clean": "npx rimraf ./**/node_modules ./**/yarn.lock ./**/build ./**/coverage ./**/.polywrap", "install:test-wrappers": "lerna run generate:wrappers --scope @polywrap/test-cases", - "build": "yarn build:core && yarn build:config && yarn build:cli && yarn install:test-wrappers", + "build": "yarn build:core && yarn build:cli && yarn install:test-wrappers", "build:core": "lerna run build --no-private --ignore polywrap --ignore @polywrap/cli-js", "build:cli": "lerna run build --scope polywrap && lerna run build --scope @polywrap/cli-js", "build:docs": "lerna run build:docs", diff --git a/scripts/patch-peer-deps.ts b/scripts/patch-peer-deps.ts new file mode 100644 index 0000000000..7e8538c8b1 --- /dev/null +++ b/scripts/patch-peer-deps.ts @@ -0,0 +1,28 @@ +import rimraf from "rimraf"; +import path from "path"; + +const packagesToPatch = [ + "@polywrap/concurrent-plugin-js", + "@polywrap/ethereum-provider-js-v1", + "@polywrap/ethereum-provider-js", + "@polywrap/file-system-plugin-js", + "@polywrap/http-plugin-js", + "@polywrap/logger-plugin-js", + "@polywrap/plugin-js", + "@polywrap/client-js" +]; + +function main () { + for (const packageToPatch of packagesToPatch) { + rimraf.sync( + path.join( + __dirname, + "../node_modules", + packageToPatch, + "node_modules/@polywrap" + ) + ); + } +} + +main(); \ No newline at end of file diff --git a/yarn.lock b/yarn.lock index 1591f2db65..dcbcec4654 100644 --- a/yarn.lock +++ b/yarn.lock @@ -2144,6 +2144,44 @@ resolved "https://registry.yarnpkg.com/@opentelemetry/semantic-conventions/-/semantic-conventions-1.6.0.tgz#ed410c9eb0070491cff9fe914246ce41f88d6f74" integrity sha512-aPfcBeLErM/PPiAuAbNFLN5sNbZLc3KZlar27uohllN8Zs6jJbHyJU1y7cMA6W/zuq+thkaG8mujiS+3iD/FWQ== +"@polywrap/asyncify-js@0.10.0": + version "0.10.0" + resolved "https://registry.yarnpkg.com/@polywrap/asyncify-js/-/asyncify-js-0.10.0.tgz#0570ce34501e91710274285b6b4740f1094f08a3" + integrity sha512-/ZhREKykF1hg5H/mm8vQHqv7MSedfCnwzbsNwYuLmH/IUtQi2t7NyD2XXavSLq5PFOHA/apPueatbSFTeIgBdA== + +"@polywrap/client-config-builder-js@0.10.0": + version "0.10.0" + resolved "https://registry.yarnpkg.com/@polywrap/client-config-builder-js/-/client-config-builder-js-0.10.0.tgz#e583f32dca97dfe0b9575db244fdad74a4f42d6f" + integrity sha512-9hZd5r/5rkLoHdeB76NDUNOYcUCzS+b8WjCI9kv5vNQiOR83dZnW3rTnQmcXOWWErRY70h6xvAQWWQ1WrW/SpQ== + dependencies: + "@polywrap/concurrent-plugin-js" "~0.10.0-pre" + "@polywrap/core-js" "0.10.0" + "@polywrap/ethereum-provider-js" "npm:@polywrap/ethereum-provider-js@~0.3.0" + "@polywrap/ethereum-provider-js-v1" "npm:@polywrap/ethereum-provider-js@~0.2.4" + "@polywrap/file-system-plugin-js" "~0.10.0-pre" + "@polywrap/http-plugin-js" "~0.10.0-pre" + "@polywrap/logger-plugin-js" "0.10.0-pre.10" + "@polywrap/uri-resolver-extensions-js" "0.10.0" + "@polywrap/uri-resolvers-js" "0.10.0" + "@polywrap/wasm-js" "0.10.0" + base64-to-uint8array "1.0.0" + +"@polywrap/client-js@0.10.0": + version "0.10.0" + resolved "https://registry.yarnpkg.com/@polywrap/client-js/-/client-js-0.10.0.tgz#607c24cd65c03f57ca8325f4a8ecc02a5485c993" + integrity sha512-wRr4HZ7a4oLrKuw8CchM5JYcE8er43GGKQnhtf/ylld5Q7FpNpfzhsi8eWknORugQYuvR3CSG7qZey4Ijgj6qQ== + dependencies: + "@polywrap/client-config-builder-js" "0.10.0" + "@polywrap/core-client-js" "0.10.0" + "@polywrap/core-js" "0.10.0" + "@polywrap/msgpack-js" "0.10.0" + "@polywrap/plugin-js" "0.10.0" + "@polywrap/result" "0.10.0" + "@polywrap/tracing-js" "0.10.0" + "@polywrap/uri-resolver-extensions-js" "0.10.0" + "@polywrap/uri-resolvers-js" "0.10.0" + "@polywrap/wrap-manifest-types-js" "0.10.0" + "@polywrap/concurrent-plugin-js@~0.10.0-pre": version "0.10.0-pre.10" resolved "https://registry.yarnpkg.com/@polywrap/concurrent-plugin-js/-/concurrent-plugin-js-0.10.0-pre.10.tgz#106e015173cabed5b043cbc2fac00a6ccf58f9a0" @@ -2153,6 +2191,26 @@ "@polywrap/msgpack-js" "0.10.0-pre.10" "@polywrap/plugin-js" "0.10.0-pre.10" +"@polywrap/core-client-js@0.10.0": + version "0.10.0" + resolved "https://registry.yarnpkg.com/@polywrap/core-client-js/-/core-client-js-0.10.0.tgz#bec91479d1294ca86b7fa77f5ed407dab4d2a0b4" + integrity sha512-Sv1fVHM/5ynobtT2N25jbXOKNju1y0Wk4TwFnTJXrAUcARrRMoAfmwLVfTwrqRZ2OjWMQ/AWTc7ziNBtH5dNAg== + dependencies: + "@polywrap/core-js" "0.10.0" + "@polywrap/msgpack-js" "0.10.0" + "@polywrap/result" "0.10.0" + "@polywrap/tracing-js" "0.10.0" + "@polywrap/wrap-manifest-types-js" "0.10.0" + +"@polywrap/core-js@0.10.0": + version "0.10.0" + resolved "https://registry.yarnpkg.com/@polywrap/core-js/-/core-js-0.10.0.tgz#5ddc31ff47019342659a2208eec05299b072b216" + integrity sha512-fx9LqRFnxAxLOhDK4M+ymrxMnXQbwuNPMLjCk5Ve5CPa9RFms0/Fzvj5ayMLidZSPSt/dLISkbDgW44vfv6wwA== + dependencies: + "@polywrap/result" "0.10.0" + "@polywrap/tracing-js" "0.10.0" + "@polywrap/wrap-manifest-types-js" "0.10.0" + "@polywrap/core-js@0.10.0-pre.10": version "0.10.0-pre.10" resolved "https://registry.yarnpkg.com/@polywrap/core-js/-/core-js-0.10.0-pre.10.tgz#3209dbcd097d3533574f1231c10ef633c2466d5c" @@ -2219,6 +2277,13 @@ "@polywrap/core-js" "0.10.0-pre.10" "@polywrap/plugin-js" "0.10.0-pre.10" +"@polywrap/msgpack-js@0.10.0": + version "0.10.0" + resolved "https://registry.yarnpkg.com/@polywrap/msgpack-js/-/msgpack-js-0.10.0.tgz#7303da87ed7bc21858f0ef392aec575c5da6df63" + integrity sha512-xt2Rkad1MFXuBlOKg9N/Tl3LTUFmE8iviwUiHXDU7ClQyYSsZ/NVAAfm0rXJktmBWB8c0/N7CgcFqJTI+XsQVQ== + dependencies: + "@msgpack/msgpack" "2.7.2" + "@polywrap/msgpack-js@0.10.0-pre.10": version "0.10.0-pre.10" resolved "https://registry.yarnpkg.com/@polywrap/msgpack-js/-/msgpack-js-0.10.0-pre.10.tgz#ac15d960dba2912f7ed657634f873e3c22c71843" @@ -2233,6 +2298,17 @@ dependencies: "@msgpack/msgpack" "2.7.2" +"@polywrap/plugin-js@0.10.0": + version "0.10.0" + resolved "https://registry.yarnpkg.com/@polywrap/plugin-js/-/plugin-js-0.10.0.tgz#e3bc81bf7832df9c84a4a319515228b159a05ba5" + integrity sha512-f0bjAKnveSu7u68NzWznYLWlzWo4MT8D6fudAF/wlV6S6R1euNJtIb8CTpAzfs6N173f81fzM/4OLS0pSYWdgQ== + dependencies: + "@polywrap/core-js" "0.10.0" + "@polywrap/msgpack-js" "0.10.0" + "@polywrap/result" "0.10.0" + "@polywrap/tracing-js" "0.10.0" + "@polywrap/wrap-manifest-types-js" "0.10.0" + "@polywrap/plugin-js@0.10.0-pre.10": version "0.10.0-pre.10" resolved "https://registry.yarnpkg.com/@polywrap/plugin-js/-/plugin-js-0.10.0-pre.10.tgz#090c1963f40ab862a09deda8c18e6d522fd2e3f2" @@ -2255,6 +2331,11 @@ "@polywrap/tracing-js" "0.10.0-pre.12" "@polywrap/wrap-manifest-types-js" "0.10.0-pre.12" +"@polywrap/result@0.10.0": + version "0.10.0" + resolved "https://registry.yarnpkg.com/@polywrap/result/-/result-0.10.0.tgz#712339223fba524dfabfb0bf868411f357d52e34" + integrity sha512-IxTBfGP89/OPNlUPMkjOrdYt/hwyvgI7TsYap6S35MHo4pXkR9mskzrHJ/AGE5DyGqP81CIIJNSYfooF97KY3A== + "@polywrap/result@0.10.0-pre.10": version "0.10.0-pre.10" resolved "https://registry.yarnpkg.com/@polywrap/result/-/result-0.10.0-pre.10.tgz#6e88ac447d92d8a10c7e7892a6371af29a072240" @@ -2265,6 +2346,18 @@ resolved "https://registry.yarnpkg.com/@polywrap/result/-/result-0.10.0-pre.12.tgz#530f8f5ced2bef189466f9fb8b41a520b12e9372" integrity sha512-KnGRJMBy1SCJt3mymO3ob0e1asqYOyY+NNKySQ5ocvG/iMlhtODs4dy2EeEtcIFZ+c7TyBPVD4SI863qHQGOUQ== +"@polywrap/tracing-js@0.10.0": + version "0.10.0" + resolved "https://registry.yarnpkg.com/@polywrap/tracing-js/-/tracing-js-0.10.0.tgz#31d7ca9cc73a1dbd877fc684000652aa2c22acdc" + integrity sha512-077oN9VfbCNsYMRjX9NA6D1vFV+Y3TH92LjZATKQ2W2fRx/IGRARamAjhNfR4qRKstrOCd9D4E2DmaqFax3QIg== + dependencies: + "@fetsorn/opentelemetry-console-exporter" "0.0.3" + "@opentelemetry/api" "1.2.0" + "@opentelemetry/exporter-trace-otlp-http" "0.32.0" + "@opentelemetry/resources" "1.6.0" + "@opentelemetry/sdk-trace-base" "1.6.0" + "@opentelemetry/sdk-trace-web" "1.6.0" + "@polywrap/tracing-js@0.10.0-pre.10": version "0.10.0-pre.10" resolved "https://registry.yarnpkg.com/@polywrap/tracing-js/-/tracing-js-0.10.0-pre.10.tgz#f50fb01883dcba4217a1711718aa53f3dd61cb1c" @@ -2289,10 +2382,46 @@ "@opentelemetry/sdk-trace-base" "1.6.0" "@opentelemetry/sdk-trace-web" "1.6.0" -"@polywrap/wrap-manifest-schemas@0.9.3": - version "0.9.3" - resolved "https://registry.yarnpkg.com/@polywrap/wrap-manifest-schemas/-/wrap-manifest-schemas-0.9.3.tgz#cdf950bb8951fba72afd8300aaf9a0a8159d7c37" - integrity sha512-+IW/NEnJUlZKIL+UCpiTThHbvgEek6qWjkTCX1glPh6Q6sryFZ/X37sb9PkRuxiHi7ZMWBZt9hnNPhvTAdgL3A== +"@polywrap/uri-resolver-extensions-js@0.10.0": + version "0.10.0" + resolved "https://registry.yarnpkg.com/@polywrap/uri-resolver-extensions-js/-/uri-resolver-extensions-js-0.10.0.tgz#ef0012e9b2231be44b0739f57b023a1c009c1b2b" + integrity sha512-mP8nLESuQFImhxeEV646m4qzJ1rc3d2LLgly9vPFUffXM7YMfJriL0nYNTzbyvZbhvH7PHfeEQ/m5DZFADMc7w== + dependencies: + "@polywrap/core-js" "0.10.0" + "@polywrap/result" "0.10.0" + "@polywrap/uri-resolvers-js" "0.10.0" + "@polywrap/wasm-js" "0.10.0" + "@polywrap/wrap-manifest-types-js" "0.10.0" + +"@polywrap/uri-resolvers-js@0.10.0": + version "0.10.0" + resolved "https://registry.yarnpkg.com/@polywrap/uri-resolvers-js/-/uri-resolvers-js-0.10.0.tgz#d80163666a5110a4a7bd36be7e0961364af761ce" + integrity sha512-lZP+sN4lnp8xRklYWkrAJFECFNXDsBawGqVk7jUrbcw1CX8YODHyDEB0dSV8vN30DMP4h70W7V4QeNwPiE1EzQ== + dependencies: + "@polywrap/core-js" "0.10.0" + "@polywrap/result" "0.10.0" + "@polywrap/wrap-manifest-types-js" "0.10.0" + +"@polywrap/wasm-js@0.10.0": + version "0.10.0" + resolved "https://registry.yarnpkg.com/@polywrap/wasm-js/-/wasm-js-0.10.0.tgz#6947b44669514cc0cb0653db8278f40631c45c7d" + integrity sha512-kI0Q9DQ/PlA0BTEj+Mye4fdt/aLh07l8YHjhbXQheuu46mcZuG9vfgnn78eug9c7wjGEECxlsK+B4hy/FPgYxQ== + dependencies: + "@polywrap/asyncify-js" "0.10.0" + "@polywrap/core-js" "0.10.0" + "@polywrap/msgpack-js" "0.10.0" + "@polywrap/result" "0.10.0" + "@polywrap/tracing-js" "0.10.0" + "@polywrap/wrap-manifest-types-js" "0.10.0" + +"@polywrap/wrap-manifest-types-js@0.10.0": + version "0.10.0" + resolved "https://registry.yarnpkg.com/@polywrap/wrap-manifest-types-js/-/wrap-manifest-types-js-0.10.0.tgz#f009a69d1591ee770dd13d67989d88f51e345d36" + integrity sha512-T3G/7NvNTuS1XyguRggTF4k7/h7yZCOcCbbUOTVoyVNfiNUY31hlrNZaFL4iriNqQ9sBDl9x6oRdOuFB7L9mlw== + dependencies: + "@apidevtools/json-schema-ref-parser" "9.0.9" + jsonschema "1.4.0" + semver "7.4.0" "@polywrap/wrap-manifest-types-js@0.10.0-pre.10": version "0.10.0-pre.10" @@ -2431,9 +2560,9 @@ "@types/json-schema" "*" "@types/estree@*": - version "1.0.0" - resolved "https://registry.yarnpkg.com/@types/estree/-/estree-1.0.0.tgz#5fb2e536c1ae9bf35366eed879e827fa59ca41c2" - integrity sha512-WulqXMDUTYAXCjZnk6JtIHPigp55cVtDgDrO2gHRwhyJto21+1zbVCtOYB2L1F9w4qCQ0rOGWBnBe0FNTiEJIQ== + version "1.0.1" + resolved "https://registry.yarnpkg.com/@types/estree/-/estree-1.0.1.tgz#aa22750962f3bf0e79d753d3cc067f010c95f194" + integrity sha512-LG4opVs2ANWZ1TJoKc937iMmNstM/d0ae1vNbnBvBhqCSezgVUOzcLCqbI5elV8Vy6WKwKjaqR+zO9VKirBBCA== "@types/fs-extra@9.0.12": version "9.0.12" @@ -2611,11 +2740,6 @@ resolved "https://registry.yarnpkg.com/@types/stack-utils/-/stack-utils-2.0.1.tgz#20f18294f797f2209b5f65c8e3b5c8e8261d127c" integrity sha512-Hl219/BT5fLAaz6NDkSuhzasy49dwQS/DSdu4MdggFB8zcXv7vflBI3xp7FEmkmdDkBUI2bPUNeMttp2knYdxw== -"@types/uuid@8.3.0": - version "8.3.0" - resolved "https://registry.yarnpkg.com/@types/uuid/-/uuid-8.3.0.tgz#215c231dff736d5ba92410e6d602050cce7e273f" - integrity sha512-eQ9qFW/fhfGJF8WKHGEHZEyVWfZxrT+6CLIJGBcZPfxUh/+BnEj+UCGYMlr9qZuX/2AltsvwrGqp0LhEW8D0zQ== - "@types/yargs-parser@*": version "21.0.0" resolved "https://registry.yarnpkg.com/@types/yargs-parser/-/yargs-parser-21.0.0.tgz#0c60e537fa790f5f9472ed2776c2b71ec117351b" @@ -3267,16 +3391,6 @@ before-after-hook@^2.2.0: resolved "https://registry.yarnpkg.com/before-after-hook/-/before-after-hook-2.2.3.tgz#c51e809c81a4e354084422b9b26bad88249c517c" integrity sha512-NzUnlZexiaH/46WDhANlyR2bXRopNg4F/zuSA3OpZnllCUgRaOF2znDioDWrmbNVsuZk6l9pMquQB38cfBZwkQ== -big.js@^5.2.2: - version "5.2.2" - resolved "https://registry.yarnpkg.com/big.js/-/big.js-5.2.2.tgz#65f0af382f578bcdc742bd9c281e9cb2d7768328" - integrity sha512-vyL2OymJxmarO8gxMr0mhChsO9QGwhynfuu4+MHTAW6czfq9humCB7rKpUjDd9YUiDPU4mzpyupFSvOClAwbmQ== - -bignumber.js@9.0.2: - version "9.0.2" - resolved "https://registry.yarnpkg.com/bignumber.js/-/bignumber.js-9.0.2.tgz#71c6c6bed38de64e24a65ebe16cfcf23ae693673" - integrity sha512-GAcQvbpsM0pUb0zw1EI0KhQEZ+lRwR5fYaAp3vPOYuP7aDvGy6cVN6XHLauvF8SOga2y0dcLcjt3iQDTSEliyw== - bignumber.js@^9.0.0: version "9.1.1" resolved "https://registry.yarnpkg.com/bignumber.js/-/bignumber.js-9.1.1.tgz#c4df7dc496bd849d4c9464344c1aa74228b4dac6" @@ -3810,11 +3924,6 @@ commander@^2.15.0, commander@^2.19.0: resolved "https://registry.yarnpkg.com/commander/-/commander-2.20.3.tgz#fd485e84c03eb4881c20722ba48035e8531aeb33" integrity sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ== -commander@^9.4.1: - version "9.5.0" - resolved "https://registry.yarnpkg.com/commander/-/commander-9.5.0.tgz#bc08d1eb5cedf7ccb797a96199d41c7bc3e60d30" - integrity sha512-KRs7WVDKg86PWiuAqhDrAQnTXZKraVcCc6vFdL14qrZ/DcWwuRo7VoiYXalXO7S5GKpqYiVEwCbgFDfxNHKJBQ== - compare-func@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/compare-func/-/compare-func-2.0.0.tgz#fb65e75edbddfd2e568554e8b5b05fff7a51fcb3" @@ -4153,7 +4262,7 @@ defaults@^1.0.3: dependencies: clone "^1.0.2" -define-properties@^1.1.3, define-properties@^1.1.4: +define-properties@^1.1.3, define-properties@^1.1.4, define-properties@^1.2.0: version "1.2.0" resolved "https://registry.yarnpkg.com/define-properties/-/define-properties-1.2.0.tgz#52988570670c9eacedd8064f4a990f2405849bd5" integrity sha512-xvqAVKGfT1+UAvPwKTVw/njhdQ8ZhXK4lI0bCIuCMrp2up9nPnaDftrLtmpTazqd1o+UY4zgzU+avtMbDP+ldA== @@ -4285,14 +4394,6 @@ dns-over-http-resolver@^1.0.0: native-fetch "^3.0.0" receptacle "^1.3.2" -doc-snippets@~1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/doc-snippets/-/doc-snippets-1.0.0.tgz#5921d52c6cfe6de0ab9b28f9594232cb6876c37e" - integrity sha512-4wVSd7jxhliPvqZ3sdhKhRla/EYy6DKlflWYd+E7JTGYXy1xBWyMnbSkWshGUiVK8TgZAF45iE4Y6eSo5F2lqg== - dependencies: - commander "^9.4.1" - glob "^8.0.3" - docker-compose@0.23.17: version "0.23.17" resolved "https://registry.yarnpkg.com/docker-compose/-/docker-compose-0.23.17.tgz#8816bef82562d9417dc8c790aa4871350f93a2ba" @@ -4357,9 +4458,9 @@ electron-fetch@^1.7.2: encoding "^0.1.13" electron-to-chromium@^1.4.284: - version "1.4.367" - resolved "https://registry.yarnpkg.com/electron-to-chromium/-/electron-to-chromium-1.4.367.tgz#d9ddc529ba2315fc852b722c359e4a40e86aa742" - integrity sha512-mNuDxb+HpLhPGUKrg0hSxbTjHWw8EziwkwlJNkFUj3W60ypigLDRVz04vU+VRsJPi8Gub+FDhYUpuTm9xiEwRQ== + version "1.4.368" + resolved "https://registry.yarnpkg.com/electron-to-chromium/-/electron-to-chromium-1.4.368.tgz#75901f97d3e23da2e66feb1e61fbb8e70ac96430" + integrity sha512-e2aeCAixCj9M7nJxdB/wDjO6mbYX+lJJxSJCXDzlr5YPGYVofuJwGN9nKg2o6wWInjX6XmxRinn3AeJMK81ltw== elliptic@6.5.4: version "6.5.4" @@ -4389,11 +4490,6 @@ emoji-regex@^9.0.0: resolved "https://registry.yarnpkg.com/emoji-regex/-/emoji-regex-9.2.2.tgz#840c8803b0d8047f4ff0cf963176b32d4ef3ed72" integrity sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg== -emojis-list@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/emojis-list/-/emojis-list-3.0.0.tgz#5570662046ad29e2e916e71aae260abdff4f6a78" - integrity sha512-/kyM18EfinwXZbno9FyUGeFh87KC8HRQBQGildHZbEuRyWFOmv1U10o9BBp8XVZDVNNuQKyIGIu5ZYAAXJ0V2Q== - encoding@^0.1.12, encoding@^0.1.13: version "0.1.13" resolved "https://registry.yarnpkg.com/encoding/-/encoding-0.1.13.tgz#56574afdd791f54a8e9b2785c0582a2d26210fa9" @@ -4408,15 +4504,6 @@ end-of-stream@^1.1.0: dependencies: once "^1.4.0" -enhanced-resolve@^4.0.0: - version "4.5.0" - resolved "https://registry.yarnpkg.com/enhanced-resolve/-/enhanced-resolve-4.5.0.tgz#2f3cfd84dbe3b487f18f2db2ef1e064a571ca5ec" - integrity sha512-Nv9m36S/vxpsI+Hc4/ZGRs0n9mXqSWGGq49zxb/cJfPAQMbUtttJAlNPS4AQzaBdw/pKskw5bMbekT/Y7W/Wlg== - dependencies: - graceful-fs "^4.1.2" - memory-fs "^0.5.0" - tapable "^1.0.0" - enquirer@^2.3.5: version "2.3.6" resolved "https://registry.yarnpkg.com/enquirer/-/enquirer-2.3.6.tgz#2a7fe5dd634a1e4125a975ec994ff5456dc3734d" @@ -4444,13 +4531,6 @@ err-code@^3.0.0: resolved "https://registry.yarnpkg.com/err-code/-/err-code-3.0.1.tgz#a444c7b992705f2b120ee320b09972eef331c920" integrity sha512-GiaH0KJUewYok+eeY05IIgjtAe4Yltygk9Wqp1V5yVWLdhf0hYZchRjNIT9bb0mSwRcIusT3cx7PJUf3zEIfUA== -errno@^0.1.3: - version "0.1.8" - resolved "https://registry.yarnpkg.com/errno/-/errno-0.1.8.tgz#8bb3e9c7d463be4976ff888f76b4809ebc2e811f" - integrity sha512-dJ6oBr5SQ1VSd9qkk7ByRgb/1SH4JZjCHSW/mr63/QcXO9zLVxvJ6Oy13nio03rxpSnVDDjFor75SjVeZWPW/A== - dependencies: - prr "~1.0.1" - error-ex@^1.2.0, error-ex@^1.3.1: version "1.3.2" resolved "https://registry.yarnpkg.com/error-ex/-/error-ex-1.3.2.tgz#b4ac40648107fdcdcfae242f428bea8a14d4f1bf" @@ -5219,7 +5299,7 @@ functional-red-black-tree@^1.0.1: resolved "https://registry.yarnpkg.com/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz#1b0ab3bd553b2a0d6399d29c0e3ea0b252078327" integrity sha512-dsKNQNdj6xA3T+QlADDA7mOSlX0qiMINjn0cgr+eGHGsbSHzTabcIogz2+p/iqP1Xs6EP/sS2SbqH+brGTbq0g== -functions-have-names@^1.2.2: +functions-have-names@^1.2.2, functions-have-names@^1.2.3: version "1.2.3" resolved "https://registry.yarnpkg.com/functions-have-names/-/functions-have-names-1.2.3.tgz#0404fe4ee2ba2f607f0e0ec3c80bae994133b834" integrity sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ== @@ -5401,17 +5481,6 @@ glob@^7.0.0, glob@^7.0.5, glob@^7.1.1, glob@^7.1.2, glob@^7.1.3, glob@^7.1.4, gl once "^1.3.0" path-is-absolute "^1.0.0" -glob@^8.0.3: - version "8.1.0" - resolved "https://registry.yarnpkg.com/glob/-/glob-8.1.0.tgz#d388f656593ef708ee3e34640fdfb99a9fd1c33e" - integrity sha512-r8hpEjiQEYlF2QU0df3dS+nxxSIreXQS1qRhMJM0Q5NDdR386C7jb7Hwwod8Fgiuex+k0GFjgft18yvxm5XoCQ== - dependencies: - fs.realpath "^1.0.0" - inflight "^1.0.4" - inherits "2" - minimatch "^5.0.1" - once "^1.3.0" - globals@^11.1.0: version "11.12.0" resolved "https://registry.yarnpkg.com/globals/-/globals-11.12.0.tgz#ab8795338868a0babd8525758018c2a7eb95c42e" @@ -7020,7 +7089,7 @@ json-text-sequence@~0.1.0: dependencies: delimit-stream "0.1.0" -json5@2.x, json5@^2.1.2, json5@^2.2.2: +json5@2.x, json5@^2.2.2: version "2.2.3" resolved "https://registry.yarnpkg.com/json5/-/json5-2.2.3.tgz#78cd6f1a19bdc12b73db5ad0c61efd66c1e29283" integrity sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg== @@ -7211,15 +7280,6 @@ load-json-file@^6.2.0: strip-bom "^4.0.0" type-fest "^0.6.0" -loader-utils@^2.0.0: - version "2.0.4" - resolved "https://registry.yarnpkg.com/loader-utils/-/loader-utils-2.0.4.tgz#8b5cb38b5c34a9a018ee1fc0e6a066d1dfcc528c" - integrity sha512-xXqpXoINfFhgua9xiqD8fPFHgkoq1mmmpE92WlDbm9rNRd/EbRb+Gqf908T2DMfuHjjJlksiK2RbHVOdD/MqSw== - dependencies: - big.js "^5.2.2" - emojis-list "^3.0.0" - json5 "^2.1.2" - locate-path@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-2.0.0.tgz#2b568b265eec944c6d9c0de9c3dbbbca0354cd8e" @@ -7433,14 +7493,6 @@ memoizee@^0.4.15: next-tick "^1.1.0" timers-ext "^0.1.7" -memory-fs@^0.5.0: - version "0.5.0" - resolved "https://registry.yarnpkg.com/memory-fs/-/memory-fs-0.5.0.tgz#324c01288b88652966d161db77838720845a8e3c" - integrity sha512-jA0rdU5KoQMC0e6ppoNRtpp6vjFq6+NY7r8hywnC7V+1Xj/MtHwGIbB1QaK/dunyjWteJzmkpd7ooeWg10T7GA== - dependencies: - errno "^0.1.3" - readable-stream "^2.0.1" - meow@^8.0.0: version "8.1.2" resolved "https://registry.yarnpkg.com/meow/-/meow-8.1.2.tgz#bcbe45bda0ee1729d350c03cffc8395a36c4e897" @@ -7494,7 +7546,7 @@ micromatch@^3.1.4: snapdragon "^0.8.1" to-regex "^3.0.2" -micromatch@^4.0.0, micromatch@^4.0.2, micromatch@^4.0.4: +micromatch@^4.0.2, micromatch@^4.0.4: version "4.0.5" resolved "https://registry.yarnpkg.com/micromatch/-/micromatch-4.0.5.tgz#bc8999a7cbbf77cdc89f132f6e467051b49090c6" integrity sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA== @@ -7548,13 +7600,6 @@ minimatch@^3.0.3, minimatch@^3.0.4, minimatch@^3.1.1: dependencies: brace-expansion "^1.1.7" -minimatch@^5.0.1: - version "5.1.6" - resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-5.1.6.tgz#1cfcb8cf5522ea69952cd2af95ae09477f122a96" - integrity sha512-lKwV/1brpG6mBUFHtb7NUmtABCb2WZZmm2wNiOA5hAb8VdCS4B3dtMWyvcoViccwAW/COERjXLt0zP1zXUN26g== - dependencies: - brace-expansion "^2.0.1" - minimist-options@4.1.0: version "4.1.0" resolved "https://registry.yarnpkg.com/minimist-options/-/minimist-options-4.1.0.tgz#c0655713c53a8a2ebd77ffa247d342c40f010619" @@ -8772,11 +8817,6 @@ proxy-from-env@^1.1.0: resolved "https://registry.yarnpkg.com/proxy-from-env/-/proxy-from-env-1.1.0.tgz#e102f16ca355424865755d2c9e8ea4f24d58c3e2" integrity sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg== -prr@~1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/prr/-/prr-1.0.1.tgz#d3fc114ba06995a45ec6893f484ceb1d78f5f476" - integrity sha512-yPw4Sng1gWghHQWj0B3ZggWUm4qVbPwPFcRG8KyxiU7J2OHFSoEHKS+EZ3fv5l1t9CyCiop6l/ZYeWbrgoQejw== - psl@^1.1.28, psl@^1.1.33: version "1.9.0" resolved "https://registry.yarnpkg.com/psl/-/psl-1.9.0.tgz#d0df2a137f00794565fcaf3b2c00cd09f8d5a5a7" @@ -8986,7 +9026,7 @@ readable-stream@3, readable-stream@^3.0.0, readable-stream@^3.0.2, readable-stre string_decoder "^1.1.1" util-deprecate "^1.0.1" -readable-stream@^2.0.1, readable-stream@^2.0.6, readable-stream@~2.3.6: +readable-stream@^2.0.6, readable-stream@~2.3.6: version "2.3.8" resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-2.3.8.tgz#91125e8042bba1b9887f49345f6277027ce8be9b" integrity sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA== @@ -9062,13 +9102,13 @@ regex-parser@2.2.11: integrity sha512-jbD/FT0+9MBU2XAZluI7w2OBs1RBi6p9M83nkoZayQXXU9e8Robt69FcZc7wU4eJD/YFTjn1JdCk3rbMJajz8Q== regexp.prototype.flags@^1.4.3: - version "1.4.3" - resolved "https://registry.yarnpkg.com/regexp.prototype.flags/-/regexp.prototype.flags-1.4.3.tgz#87cab30f80f66660181a3bb7bf5981a872b367ac" - integrity sha512-fjggEOO3slI6Wvgjwflkc4NFRCTZAu5CnNfBd5qOMYhWdn67nJBBu34/TkD++eeFmd8C9r9jfXJ27+nSiRkSUA== + version "1.5.0" + resolved "https://registry.yarnpkg.com/regexp.prototype.flags/-/regexp.prototype.flags-1.5.0.tgz#fe7ce25e7e4cca8db37b6634c8a2c7009199b9cb" + integrity sha512-0SutC3pNudRKgquxGoRGIz946MZVHqbNfPjBdxeOhBrdgDKlRoXmYLQN9xRbrR09ZXWeGAdPuif7egofn6v5LA== dependencies: call-bind "^1.0.2" - define-properties "^1.1.3" - functions-have-names "^1.2.2" + define-properties "^1.2.0" + functions-have-names "^1.2.3" regexpp@^3.0.0, regexpp@^3.1.0: version "3.2.0" @@ -9315,6 +9355,13 @@ semver@7.3.8: dependencies: lru-cache "^6.0.0" +semver@7.4.0: + version "7.4.0" + resolved "https://registry.yarnpkg.com/semver/-/semver-7.4.0.tgz#8481c92feffc531ab1e012a8ffc15bdd3a0f4318" + integrity sha512-RgOxM8Mw+7Zus0+zcLEUn8+JfoLpj/huFTItQy2hsM4khuC1HYRDp0cU482Ewn/Fcy6bCjufD8vAj7voC66KQw== + dependencies: + lru-cache "^6.0.0" + semver@7.5.0, semver@7.x, semver@^7.1.1, semver@^7.1.3, semver@^7.2.1, semver@^7.3.2, semver@^7.3.4, semver@^7.3.5: version "7.5.0" resolved "https://registry.yarnpkg.com/semver/-/semver-7.5.0.tgz#ed8c5dc8efb6c629c88b23d41dc9bf40c1d96cd0" @@ -9832,11 +9879,6 @@ table@^6.0.4, table@^6.7.1: string-width "^4.2.3" strip-ansi "^6.0.1" -tapable@^1.0.0: - version "1.1.3" - resolved "https://registry.yarnpkg.com/tapable/-/tapable-1.1.3.tgz#a1fccc06b58db61fd7a45da2da44f5f3a3e67ba2" - integrity sha512-4WK/bYZmj8xLr+HUCODHGF1ZFzsYffasLUgEiMBY4fgtltdO6B4WJtlSbPaDTLpYTcGVwM2qLnFTICEcNxs3kA== - tar@^4.4.12: version "4.4.19" resolved "https://registry.yarnpkg.com/tar/-/tar-4.4.19.tgz#2e4d7263df26f2b914dee10c825ab132123742f3" @@ -10065,17 +10107,6 @@ ts-jest@26.5.4: semver "7.x" yargs-parser "20.x" -ts-loader@8.0.17: - version "8.0.17" - resolved "https://registry.yarnpkg.com/ts-loader/-/ts-loader-8.0.17.tgz#98f2ccff9130074f4079fd89b946b4c637b1f2fc" - integrity sha512-OeVfSshx6ot/TCxRwpBHQ/4lRzfgyTkvi7ghDVrLXOHzTbSK413ROgu/xNqM72i3AFeAIJgQy78FwSMKmOW68w== - dependencies: - chalk "^4.1.0" - enhanced-resolve "^4.0.0" - loader-utils "^2.0.0" - micromatch "^4.0.0" - semver "^7.3.4" - ts-mixer@^5.4.1: version "5.4.1" resolved "https://registry.yarnpkg.com/ts-mixer/-/ts-mixer-5.4.1.tgz#b90db9ced48531aa17ce9184a2890d1e3c99b1e5" From ca8560469fd7bb115d0bdd5fd45c265a58c2f1ff Mon Sep 17 00:00:00 2001 From: dOrgJelli Date: Wed, 19 Apr 2023 02:32:22 -0500 Subject: [PATCH 18/19] chore: fix ci-rust --- .github/workflows/ci-rust.yaml | 51 ---------------------------------- 1 file changed, 51 deletions(-) diff --git a/.github/workflows/ci-rust.yaml b/.github/workflows/ci-rust.yaml index 596f1b8a2c..b55bf37605 100644 --- a/.github/workflows/ci-rust.yaml +++ b/.github/workflows/ci-rust.yaml @@ -59,57 +59,6 @@ jobs: CI-WRAP-Test-Harness: uses: ./.github/workflows/ci-wrap-test-harness.yaml - Test-Cases: - needs: CI-WRAP-Test-Harness - runs-on: ubuntu-latest - if: ${{ always() }} - steps: - - name: Checkout repository - uses: actions/checkout@v2 - - - name: Read .nvmrc - run: echo ::set-output name=NVMRC::$(cat .nvmrc) - id: nvm - - - name: Setup Node.js - uses: actions/setup-node@master - with: - node-version: '${{ steps.nvm.outputs.NVMRC }}' - - - name: Get yarn cache directory path - id: yarn-cache-dir-path - run: echo "::set-output name=dir::$(yarn cache dir)" - - - uses: actions/cache@v2 - with: - path: ${{ steps.yarn-cache-dir-path.outputs.dir }} - key: ${{ runner.os }}-yarn-${{ hashFiles('**/yarn.lock') }} - restore-keys: | - ${{ runner.os }}-yarn- - - - name: Install dependencies - run: yarn install --nonInteractive --frozen-lockfile --prefer-offline - - - name: Build - run: yarn build - - - name: Get updated wrappers - if: ${{ needs.CI-WRAP-Test-Harness.outputs.rebuild_required == 'true' }} - uses: actions/download-artifact@v3 - id: get-wrappers - with: - name: rebuilt-wrappers - path: ./wrappers - - - if: ${{ needs.CI-WRAP-Test-Harness.outputs.rebuild_required == 'true' }} - run: | - rm -rf packages/test-cases/cases/wrappers - mv wrappers packages/test-cases/cases - - - name: Test - run: yarn test:rust - working-directory: ./packages/js/client - Test-Cli: runs-on: ubuntu-latest needs: CI-WRAP-Test-Harness From ae6e122c959bbe43d2cd7fe6fe67ab86ff6c0b84 Mon Sep 17 00:00:00 2001 From: dOrgJelli Date: Wed, 19 Apr 2023 02:57:14 -0500 Subject: [PATCH 19/19] prep 0.10.1 --- CHANGELOG.md | 19 +++++++++++++++++++ VERSION | 2 +- 2 files changed, 20 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index b51451630f..63a5329ed0 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,22 @@ +# Polywrap Origin (0.10.1) +## Features +**`@polywrap/schema-bind`:** +* [PR-1694](https://github.com/polywrap/toolchain/pull/1694) **`plugin/rust` Env Bindings Refactor** + * Rust plugin bindings now expose `env` as a function argument. + +## Bugs +**`@polywrap/schema-bind`:** +* [PR-1700](https://github.com/polywrap/toolchain/pull/1700) **`plugin/rust` Serde renaming for snake-cased properties in rust plugins types** + * Rust plugins now properly convert wrap schema property names into snake-cased names, so they are compatable with Rust naming conventions. + +**`@polywrap/templates`:** +* [PR-1680](https://github.com/polywrap/toolchain/pull/1680) **Import newer logger in typescript template** + * Update the typescript app template to use the latest logging wrap at `ens/wraps.eth:logging@1.0.0`. + +**`@polywrap/polywrap-manifest-types-js`:** +* [PR-1692](https://github.com/polywrap/toolchain/pull/1692) **top-level `docker` property is now removed from build manifest during migration** + * Fixes a bug where the top-level `docker` property of build manifest version 0.1.0 was not being dropped during migration, causing migrated build manifests to fail validation. + # Polywrap Origin (0.10.0) ## Features ### Toolchain diff --git a/VERSION b/VERSION index 78bc1abd14..571215736a 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -0.10.0 +0.10.1