feat: 📦 upend jslib + wasm can be used from node
ci/woodpecker/push/woodpecker Pipeline failed Details

feat/lang-upgrades-keys
Tomáš Mládek 2023-10-07 13:00:34 +02:00
parent f79995b6f4
commit 91cfa6a2da
11 changed files with 1528 additions and 1449 deletions

View File

@ -66,8 +66,12 @@ webui:
wasmlib:
FROM --platform=linux/amd64 +base-rust
WORKDIR tools/upend_wasm
RUN wasm-pack build --target web
SAVE ARTIFACT pkg
RUN wasm-pack build --target web --out-dir pkg-web && \
wasm-pack build --target nodejs --out-dir pkg-node
RUN sed -e 's%"name": "upend_wasm"%"name": "@upnd/wasm-web"%' -i pkg-web/package.json && \
sed -e 's%"name": "upend_wasm"%"name": "@upnd/wasm-node"%' -i pkg-node/package.json
SAVE ARTIFACT pkg-web AS LOCAL tools/upend_wasm/pkg-web
SAVE ARTIFACT pkg-node AS LOCAL tools/upend_wasm/pkg-node
jslib:
FROM +base-node
@ -188,7 +192,8 @@ base-node:
FROM node:lts
RUN npm install -g pnpm
WORKDIR /upend
COPY +wasmlib/pkg tools/upend_wasm/pkg
COPY +wasmlib/pkg-web tools/upend_wasm/pkg-web
COPY +wasmlib/pkg-node tools/upend_wasm/pkg-node
COPY tools/upend_js/package.json tools/upend_js/pnpm-lock.yaml tools/upend_js/
RUN cd tools/upend_js && pnpm install --frozen-lockfile
COPY webui/package.json webui/pnpm-lock.yaml webui/

View File

@ -13,14 +13,7 @@ import type {
StoreInfo,
VaultInfo,
} from "./types";
import init_wasm from "upend_wasm";
import {
AddressComponents,
AddressTypeConstants,
addr_to_components,
components_to_addr,
InitInput,
} from "upend_wasm";
import type { UpEndWasmExtensions, AddressComponents } from "./wasm";
import debug from "debug";
const dbg = debug("upend:api");
@ -28,28 +21,20 @@ export { AddressComponents };
export class UpEndApi {
private instanceUrl = "";
private wasmInit: InitInput | undefined;
private wasmInitialized = false;
private addressTypeConstants: AddressTypeConstants | undefined = undefined;
private wasmExtensions: UpEndWasmExtensions | undefined = undefined;
private queryOnceLRU = new LRU<string, UpListing>({ max: 128 });
private inFlightRequests: { [key: string]: Promise<UpListing> | null } = {};
constructor(instanceUrl = "", wasmInit?: InitInput) {
constructor(instanceUrl = "", wasmExtensions?: UpEndWasmExtensions) {
this.setInstanceUrl(instanceUrl);
if (wasmInit) {
this.setWasmInit(wasmInit);
}
this.wasmExtensions = wasmExtensions;
}
public setInstanceUrl(apiUrl: string) {
this.instanceUrl = apiUrl.replace(/\/+$/g, "");
}
public setWasmInit(wasmInit: InitInput) {
this.wasmInit = wasmInit;
}
public get apiUrl() {
return this.instanceUrl + "/api";
}
@ -215,14 +200,9 @@ export class UpEndApi {
): Promise<string> {
let response: Response;
if (typeof input === "string") {
try {
if (!this.addressTypeConstants) {
await this.initWasm();
this.addressTypeConstants = new AddressTypeConstants();
}
return this.addressTypeConstants[input];
} catch (err) {
console.warn(err);
if (this.wasmExtensions) {
await this.wasmExtensions.init();
return this.wasmExtensions.AddressTypeConstants[input];
}
response = await fetch(`${this.apiUrl}/address?type=${input}`);
} else {
@ -248,26 +228,20 @@ export class UpEndApi {
public async addressToComponents(
address: string
): Promise<AddressComponents> {
await this.initWasm();
return addr_to_components(address);
if (!this.wasmExtensions) {
throw new Error("WASM extensions not supplied.");
}
await this.wasmExtensions.init();
return this.wasmExtensions.addr_to_components(address);
}
public async componentsToAddress(
components: AddressComponents
): Promise<string> {
await this.initWasm();
return components_to_addr(components);
}
private async initWasm(): Promise<void> {
if (!this.wasmInitialized) {
if (!this.wasmInit) {
throw new Error(
"WASM init not specified, cannot initialize WASM extensions."
);
}
await init_wasm(this.wasmInit);
this.wasmInitialized = true;
if (!this.wasmExtensions) {
throw new Error("WASM extensions not initialized.");
}
await this.wasmExtensions.init();
return this.wasmExtensions.components_to_addr(components);
}
}

View File

@ -1,18 +1,18 @@
{
"name": "@upnd/upend",
"version": "0.0.1",
"version": "0.0.2",
"description": "Client library to interact with the UpEnd system.",
"scripts": {
"build": "tsc --build --listFiles --verbose && cp -v node_modules/upend_wasm/*.wasm .",
"build": "tsc --build --verbose",
"test": "ava",
"lint": "eslint ."
},
"author": "Tomáš Mládek <t@mldk.cz>",
"license": "MIT",
"license": "AGPL-3.0",
"files": [
"*.ts",
"*.js",
"*.wasm"
"**/*.ts",
"**/*.js",
"**/*.wasm"
],
"devDependencies": {
"@types/debug": "^4.1.8",
@ -20,11 +20,16 @@
"@typescript-eslint/parser": "latest",
"ava": "^3.15.0",
"eslint": "^8.7.0",
"typescript": "^4.4.4",
"upend_wasm": "file:../upend_wasm/pkg"
"typescript": "^4.4.4"
},
"dependencies": {
"debug": "^4.3.4",
"lru-cache": "^7.0.0"
}
"lru-cache": "^7.0.0",
"@upnd/wasm-node": "file:../upend_wasm/pkg-node",
"@upnd/wasm-web": "file:../upend_wasm/pkg-web"
},
"bundledDependencies": [
"@upnd/wasm-node",
"@upnd/wasm-web"
]
}

View File

@ -5,15 +5,18 @@ settings:
excludeLinksFromLockfile: false
dependencies:
'@upnd/wasm-node':
specifier: file:../upend_wasm/pkg-node
version: file:../upend_wasm/pkg-node
'@upnd/wasm-web':
specifier: file:../upend_wasm/pkg-web
version: file:../upend_wasm/pkg-web
debug:
specifier: ^4.3.4
version: 4.3.4
lru-cache:
specifier: ^7.0.0
version: 7.18.3
upend_wasm:
specifier: file:../upend_wasm/pkg
version: file:../upend_wasm/pkg
devDependencies:
'@types/debug':
@ -2440,7 +2443,12 @@ packages:
yargs-parser: 20.2.9
dev: true
file:../upend_wasm/pkg:
resolution: {directory: ../upend_wasm/pkg, type: directory}
name: upend_wasm
file:../upend_wasm/pkg-node:
resolution: {directory: ../upend_wasm/pkg-node, type: directory}
name: '@upnd/wasm-node'
dev: false
file:../upend_wasm/pkg-web:
resolution: {directory: ../upend_wasm/pkg-web, type: directory}
name: '@upnd/wasm-web'
dev: false

View File

@ -0,0 +1,34 @@
import debug from "debug";
const dbg = debug("upend:wasm");
export abstract class UpEndWasmExtensions {
private initialized = false;
private initPromise: Promise<void> | undefined = undefined;
protected abstract _init(): Promise<void>;
public async init(): Promise<void> {
if (!this.initialized) {
if (!this.initPromise) {
this.initPromise = this._init();
}
await this.initPromise;
this.initialized = true;
dbg("WASM extensions initialized.");
}
}
public abstract addr_to_components(address: string): AddressComponents;
public abstract components_to_addr(components: AddressComponents): string;
public abstract AddressTypeConstants: AddressTypeConstants;
}
export interface AddressTypeConstants {
Attribute: string;
Hash: string;
Url: string;
Uuid: string;
}
export interface AddressComponents {
t: string;
c?: string;
}

View File

@ -0,0 +1,28 @@
import {
AddressComponents,
AddressTypeConstants,
UpEndWasmExtensions,
} from ".";
import {
addr_to_components,
components_to_addr,
AddressComponents as WasmAddresComponents,
AddressTypeConstants as WasmAddresTypeConstants,
} from "@upnd/wasm-node";
export class UpEndWasmExtensionsNode extends UpEndWasmExtensions {
protected async _init(): Promise<void> {}
addr_to_components(address: string): AddressComponents {
return addr_to_components(address);
}
components_to_addr(components: AddressComponents): string {
const wc = new WasmAddresComponents(components.t, components.c);
return components_to_addr(wc);
}
get AddressTypeConstants(): AddressTypeConstants {
return new WasmAddresTypeConstants();
}
}

View File

@ -0,0 +1,39 @@
import {
AddressComponents,
AddressTypeConstants,
UpEndWasmExtensions,
} from ".";
import {
addr_to_components,
components_to_addr,
AddressComponents as WasmAddresComponents,
AddressTypeConstants as WasmAddresTypeConstants,
InitInput,
} from "@upnd/wasm-web";
import init_wasm from "@upnd/wasm-web";
export class UpEndWasmExtensionsWeb extends UpEndWasmExtensions {
private initInput: InitInput;
constructor(init: InitInput) {
super();
this.initInput = init;
}
protected async _init(): Promise<void> {
await init_wasm(this.initInput);
}
addr_to_components(address: string): AddressComponents {
return addr_to_components(address);
}
components_to_addr(components: AddressComponents): string {
const wc = new WasmAddresComponents(components.t, components.c);
return components_to_addr(wc);
}
get AddressTypeConstants(): AddressTypeConstants {
return new WasmAddresTypeConstants();
}
}

View File

@ -0,0 +1,2 @@
pkg-node
pkg-web

2
tools/upend_wasm/.gitignore vendored Normal file
View File

@ -0,0 +1,2 @@
pkg-node
pkg-web

File diff suppressed because it is too large Load Diff

View File

@ -1,7 +1,6 @@
import { UpEndApi } from "@upnd/upend";
import { UpEndWasmExtensionsWeb } from "@upnd/upend/wasm/web";
import wasmURL from "@upnd/upend/node_modules/@upnd/wasm-web/upend_wasm_bg.wasm?url";
// import wasmURL from "@upnd/upend/upend_wasm_bg.wasm?url";
console.log({ UpEndWasmExtensionsWeb, UpEndApi });
const wasm = new UpEndWasmExtensionsWeb();
const wasm = new UpEndWasmExtensionsWeb(wasmURL);
export default new UpEndApi("/", wasm);