ihm_client/src/services/wasm.service.ts

429 lines
11 KiB
TypeScript

/**
* WASM Service - Manages communication with WASM Worker
* Similar to Database Service, but for WASM operations
*/
export class WasmService {
private static instance: WasmService;
private wasmWorker: Worker | null = null;
private messageIdCounter: number = 0;
private pendingMessages: Map<
string,
{ resolve: (value: any) => void; reject: (error: any) => void }
> = new Map();
// ============================================
// INITIALIZATION & SINGLETON
// ============================================
private constructor() {
this.initWasmWorker();
}
public static async getInstance(): Promise<WasmService> {
if (!WasmService.instance) {
WasmService.instance = new WasmService();
await WasmService.instance.waitForWorkerReady();
}
return WasmService.instance;
}
// ============================================
// WASM WORKER MANAGEMENT
// ============================================
private initWasmWorker(): void {
this.wasmWorker = new Worker(
new URL("../workers/wasm.worker.ts", import.meta.url),
{ type: "module" }
);
this.wasmWorker.onmessage = (event) => {
const { id, type, result, error } = event.data;
const pending = this.pendingMessages.get(id);
if (pending) {
this.pendingMessages.delete(id);
if (type === "SUCCESS") {
pending.resolve(result);
} else if (type === "ERROR") {
pending.reject(new Error(error));
}
}
};
this.wasmWorker.onerror = (error) => {
console.error("[WasmService] WASM Worker error:", error);
};
}
private async waitForWorkerReady(): Promise<void> {
return this.sendMessageToWorker("INIT", {});
}
private sendMessageToWorker<T = any>(type: string, payload: any): Promise<T> {
return new Promise((resolve, reject) => {
if (!this.wasmWorker) {
reject(new Error("WASM Worker not initialized"));
return;
}
const id = `wasm_${++this.messageIdCounter}`;
this.pendingMessages.set(id, { resolve, reject });
this.wasmWorker.postMessage({
id,
type,
...payload,
});
// Timeout after 30 seconds
setTimeout(() => {
if (this.pendingMessages.has(id)) {
this.pendingMessages.delete(id);
reject(new Error(`WASM Worker message timeout for type: ${type}`));
}
}, 30000);
});
}
// ============================================
// WASM METHOD CALLS
// ============================================
/**
* Generic method to call any WASM function
*/
public async callMethod(method: string, ...args: any[]): Promise<any> {
return this.sendMessageToWorker("WASM_METHOD", {
method,
args,
});
}
// ============================================
// WS MESSAGE PROCESSING METHODS
// ============================================
/**
* Parse cipher message from WebSocket
*/
public async parseCipher(
msg: string,
membersList: any,
processes: any
): Promise<any> {
return this.callMethod("parse_cipher", msg, membersList, processes);
}
/**
* Parse new transaction message from WebSocket
*/
public async parseNewTx(
msg: string,
blockHeight: number,
membersList: any
): Promise<any> {
return this.callMethod("parse_new_tx", msg, blockHeight, membersList);
}
// ============================================
// TRANSACTION METHODS
// ============================================
/**
* Create a transaction
*/
public async createTransaction(
addresses: string[],
feeRate: number
): Promise<any> {
return this.callMethod("create_transaction", addresses, feeRate);
}
/**
* Sign a partial transaction
*/
public async signTransaction(partialTx: any): Promise<any> {
return this.callMethod("sign_transaction", partialTx);
}
/**
* Get transaction ID
*/
public async getTxid(transaction: string): Promise<string> {
return this.callMethod("get_txid", transaction);
}
/**
* Get OP_RETURN from transaction
*/
public async getOpReturn(transaction: string): Promise<string> {
return this.callMethod("get_opreturn", transaction);
}
/**
* Get prevouts from transaction
*/
public async getPrevouts(transaction: string): Promise<string[]> {
return this.callMethod("get_prevouts", transaction);
}
// ============================================
// PROCESS MANIPULATION METHODS
// ============================================
/**
* Create a new process
*/
public async createProcess(
privateData: any,
publicData: any,
roles: any,
membersList: any
): Promise<any> {
return this.callMethod(
"create_process",
privateData,
publicData,
roles,
membersList
);
}
/**
* Update a process
*/
public async updateProcess(
process: any,
privateData: any,
publicData: any,
roles: any,
membersList: any
): Promise<any> {
return this.callMethod(
"update_process",
process,
privateData,
publicData,
roles,
membersList
);
}
/**
* Create update message
*/
public async createUpdateMessage(
process: any,
stateId: string,
membersList: any
): Promise<any> {
return this.callMethod("create_update_message", process, stateId, membersList);
}
/**
* Create PRD response
*/
public async createPrdResponse(
process: any,
stateId: string,
membersList: any
): Promise<any> {
return this.callMethod("create_response_prd", process, stateId, membersList);
}
/**
* Validate state
*/
public async validateState(
process: any,
stateId: string,
membersList: any
): Promise<any> {
return this.callMethod("validate_state", process, stateId, membersList);
}
/**
* Refuse state
*/
public async refuseState(process: any, stateId: string): Promise<any> {
return this.callMethod("refuse_state", process, stateId);
}
/**
* Request data from peers
*/
public async requestData(
processId: string,
stateIds: string[],
roles: any,
membersList: any
): Promise<any> {
return this.callMethod(
"request_data",
processId,
stateIds,
roles,
membersList
);
}
/**
* Process commit new state
*/
public async processCommitNewState(
process: any,
newStateId: string,
newTip: string
): Promise<void> {
return this.callMethod("process_commit_new_state", process, newStateId, newTip);
}
// ============================================
// ENCODING/DECODING METHODS
// ============================================
public async encodeJson(data: any): Promise<any> {
return this.callMethod("encode_json", data);
}
public async encodeBinary(data: any): Promise<any> {
return this.callMethod("encode_binary", data);
}
public async decodeValue(value: number[]): Promise<any> {
return this.callMethod("decode_value", value);
}
// ============================================
// WALLET METHODS
// ============================================
public async isPaired(): Promise<boolean> {
return this.callMethod("is_paired");
}
public async getAvailableAmount(): Promise<BigInt> {
return this.callMethod("get_available_amount");
}
public async getAddress(): Promise<string> {
return this.callMethod("get_address");
}
public async getPairingProcessId(): Promise<string> {
return this.callMethod("get_pairing_process_id");
}
public async createNewDevice(birthday: number, network: string): Promise<string> {
return this.callMethod("create_new_device", birthday, network);
}
public async dumpDevice(): Promise<any> {
return this.callMethod("dump_device");
}
public async dumpNeuteredDevice(): Promise<any> {
return this.callMethod("dump_neutered_device");
}
public async dumpWallet(): Promise<any> {
return this.callMethod("dump_wallet");
}
public async restoreDevice(device: any): Promise<void> {
return this.callMethod("restore_device", device);
}
public async pairDevice(processId: string, spAddresses: string[]): Promise<void> {
return this.callMethod("pair_device", processId, spAddresses);
}
public async unpairDevice(): Promise<void> {
return this.callMethod("unpair_device");
}
public async resetDevice(): Promise<void> {
return this.callMethod("reset_device");
}
// ============================================
// CRYPTO METHODS
// ============================================
public async hashValue(
fileBlob: { type: string; data: Uint8Array },
commitedIn: string,
label: string
): Promise<string> {
return this.callMethod("hash_value", fileBlob, commitedIn, label);
}
public async getMerkleProof(processState: any, attributeName: string): Promise<any> {
return this.callMethod("get_merkle_proof", processState, attributeName);
}
public async validateMerkleProof(proof: any, hash: string): Promise<boolean> {
return this.callMethod("validate_merkle_proof", proof, hash);
}
public async decryptData(key: Uint8Array, data: Uint8Array): Promise<Uint8Array> {
return this.callMethod("decrypt_data", key, data);
}
// ============================================
// PROCESS CREATION (with relay and fee)
// ============================================
public async createNewProcess(
privateData: any,
roles: any,
publicData: any,
relayAddress: string,
feeRate: number,
membersList: any
): Promise<any> {
return this.callMethod(
"create_new_process",
privateData,
roles,
publicData,
relayAddress,
feeRate,
membersList
);
}
// ============================================
// SECRETS MANAGEMENT
// ============================================
public async setSharedSecrets(secretsJson: string): Promise<void> {
return this.callMethod("set_shared_secrets", secretsJson);
}
// ============================================
// BLOCKCHAIN SCANNING
// ============================================
public async scanBlocks(tipHeight: number, blindbitUrl: string): Promise<void> {
return this.callMethod("scan_blocks", tipHeight, blindbitUrl);
}
// ============================================
// UTILITY METHODS
// ============================================
public async createFaucetMessage(): Promise<string> {
return this.callMethod("create_faucet_msg");
}
public async isChildRole(parent: any, child: any): Promise<boolean> {
return this.callMethod("is_child_role", JSON.stringify(parent), JSON.stringify(child));
}
}
export default WasmService;