SmartWeaveTags && SmartWeaveError

This commit is contained in:
asiaziola
2022-05-25 15:53:38 +02:00
parent 058eab7dce
commit 922899eb8c
16 changed files with 100 additions and 93 deletions

View File

@@ -3,7 +3,7 @@ import fs from 'fs';
import ArLocal from 'arlocal';
import Arweave from 'arweave';
import { JWKInterface } from 'arweave/node/lib/wallet';
import { Contract, getTag, LoggerFactory, Warp, WarpNodeFactory, WarpTags } from '@warp';
import { Contract, getTag, LoggerFactory, Warp, WarpNodeFactory, SmartWeaveTags } from '@warp';
import path from 'path';
import { addFunds, mineBlock } from '../_helpers';
@@ -72,9 +72,9 @@ describe('Testing the Warp client for AssemblyScript WASM contract', () => {
expect(contractTx).not.toBeNull();
const contractSrcTx = await arweave.transactions.get(getTag(contractTx, WarpTags.CONTRACT_SRC_TX_ID));
expect(getTag(contractSrcTx, WarpTags.CONTENT_TYPE)).toEqual('application/wasm');
expect(getTag(contractSrcTx, WarpTags.WASM_LANG)).toEqual('assemblyscript');
const contractSrcTx = await arweave.transactions.get(getTag(contractTx, SmartWeaveTags.CONTRACT_SRC_TX_ID));
expect(getTag(contractSrcTx, SmartWeaveTags.CONTENT_TYPE)).toEqual('application/wasm');
expect(getTag(contractSrcTx, SmartWeaveTags.WASM_LANG)).toEqual('assemblyscript');
});
it('should properly read initial state', async () => {

View File

@@ -3,7 +3,7 @@ import fs from 'fs';
import ArLocal from 'arlocal';
import Arweave from 'arweave';
import { JWKInterface } from 'arweave/node/lib/wallet';
import { getTag, LoggerFactory, PstContract, PstState, Warp, WarpNodeFactory, WarpTags } from '@warp';
import { getTag, LoggerFactory, PstContract, PstState, Warp, WarpNodeFactory, SmartWeaveTags } from '@warp';
import path from 'path';
import { addFunds, mineBlock } from '../_helpers';
@@ -109,9 +109,9 @@ describe('Testing the Go WASM Profit Sharing Token', () => {
expect(contractTx).not.toBeNull();
const contractSrcTx = await arweave.transactions.get(getTag(contractTx, WarpTags.CONTRACT_SRC_TX_ID));
expect(getTag(contractSrcTx, WarpTags.CONTENT_TYPE)).toEqual('application/wasm');
expect(getTag(contractSrcTx, WarpTags.WASM_LANG)).toEqual('go');
const contractSrcTx = await arweave.transactions.get(getTag(contractTx, SmartWeaveTags.CONTRACT_SRC_TX_ID));
expect(getTag(contractSrcTx, SmartWeaveTags.CONTENT_TYPE)).toEqual('application/wasm');
expect(getTag(contractSrcTx, SmartWeaveTags.WASM_LANG)).toEqual('go');
});
it('should read pst state and balance data', async () => {

View File

@@ -3,7 +3,16 @@ import fs from 'fs';
import ArLocal from 'arlocal';
import Arweave from 'arweave';
import { JWKInterface } from 'arweave/node/lib/wallet';
import { ArweaveWrapper, getTag, LoggerFactory, PstContract, PstState, Warp, WarpNodeFactory, WarpTags } from '@warp';
import {
ArweaveWrapper,
getTag,
LoggerFactory,
PstContract,
PstState,
Warp,
WarpNodeFactory,
SmartWeaveTags
} from '@warp';
import path from 'path';
import { addFunds, mineBlock } from '../_helpers';
import { WasmSrc } from '../../../core/modules/impl/wasm/WasmSrc';
@@ -116,11 +125,11 @@ describe('Testing the Rust WASM Profit Sharing Token', () => {
const contractTx = await arweave.transactions.get(contractTxId);
expect(contractTx).not.toBeNull();
const contractSrcTxId = getTag(contractTx, WarpTags.CONTRACT_SRC_TX_ID);
const contractSrcTxId = getTag(contractTx, SmartWeaveTags.CONTRACT_SRC_TX_ID);
const contractSrcTx = await arweave.transactions.get(contractSrcTxId);
expect(getTag(contractSrcTx, WarpTags.CONTENT_TYPE)).toEqual('application/wasm');
expect(getTag(contractSrcTx, WarpTags.WASM_LANG)).toEqual('rust');
expect(getTag(contractSrcTx, WarpTags.WASM_META)).toEqual(JSON.stringify({ dtor: 74 }));
expect(getTag(contractSrcTx, SmartWeaveTags.CONTENT_TYPE)).toEqual('application/wasm');
expect(getTag(contractSrcTx, SmartWeaveTags.WASM_LANG)).toEqual('rust');
expect(getTag(contractSrcTx, SmartWeaveTags.WASM_META)).toEqual(JSON.stringify({ dtor: 74 }));
const srcTxData = await arweaveWrapper.txData(contractSrcTxId);
const wasmSrc = new WasmSrc(srcTxData);

View File

@@ -27,7 +27,7 @@ import {
SigningFunction,
sleep,
Warp,
WarpTags,
SmartWeaveTags,
SourceType,
Tags,
SourceImpl,
@@ -314,7 +314,7 @@ export class HandlerBasedContract<State> implements Contract<State> {
innerWrites.forEach((contractTxId) => {
tags.push({
name: WarpTags.INTERACT_WRITE,
name: SmartWeaveTags.INTERACT_WRITE,
value: contractTxId
});
});
@@ -331,7 +331,7 @@ export class HandlerBasedContract<State> implements Contract<State> {
if (vrf) {
tags.push({
name: WarpTags.REQUEST_VRF,
name: SmartWeaveTags.REQUEST_VRF,
value: 'true'
});
}

View File

@@ -1,4 +1,3 @@
import { WarpTags } from '@warp';
import { BalanceResult, HandlerBasedContract, PstContract, PstState, TransferInput } from '@warp/contract';
interface BalanceInput {

View File

@@ -100,14 +100,14 @@ export class SourceImpl implements Source {
srcTx.addTag(WarpTags.APP_NAME, 'SmartWeaveContractSource');
// TODO: version should be taken from the current package.json version.
srcTx.addTag(WarpTags.APP_VERSION, '0.3.0');
srcTx.addTag(WarpTags.SDK, 'Warp');
srcTx.addTag(WarpTags.CONTENT_TYPE, contractType == 'js' ? 'application/javascript' : 'application/wasm');
srcTx.addTag(SmartWeaveTags.APP_VERSION, '0.3.0');
srcTx.addTag(SmartWeaveTags.SDK, 'Warp');
srcTx.addTag(SmartWeaveTags.CONTENT_TYPE, contractType == 'js' ? 'application/javascript' : 'application/wasm');
if (contractType == 'wasm') {
srcTx.addTag(WarpTags.WASM_LANG, wasmLang);
srcTx.addTag(WarpTags.WASM_LANG_VERSION, wasmVersion);
srcTx.addTag(WarpTags.WASM_META, JSON.stringify(metadata));
srcTx.addTag(SmartWeaveTags.WASM_LANG, wasmLang);
srcTx.addTag(SmartWeaveTags.WASM_LANG_VERSION, wasmVersion);
srcTx.addTag(SmartWeaveTags.WASM_META, JSON.stringify(metadata));
}
if (typeof signer == 'function') {

View File

@@ -1,7 +1,7 @@
/**
* Definition of all transaction tags used by the SmartWeave "protocol"
*/
export enum WarpTags {
export enum SmartWeaveTags {
APP_NAME = 'App-Name',
APP_VERSION = 'App-Version',
CONTRACT_TX_ID = 'Contract', // note: should be named Contract-Tx-Id

View File

@@ -19,7 +19,7 @@ export * from './modules/impl/StateCache';
export * from './modules/impl/wasm/WasmSrc';
export * from './ExecutionContextModifier';
export * from './WarpTags';
export * from './SmartWeaveTags';
export * from './ExecutionContext';
export * from './ContractDefinition';
export * from './ContractCallStack';

View File

@@ -8,7 +8,7 @@ import {
InteractionsLoader,
LoggerFactory,
sleep,
WarpTags
SmartWeaveTags
} from '@warp';
import Arweave from 'arweave';
@@ -85,11 +85,11 @@ export class ArweaveGatewayInteractionsLoader implements InteractionsLoader {
const mainTransactionsVariables: GqlReqVariables = {
tags: [
{
name: WarpTags.APP_NAME,
name: SmartWeaveTags.APP_NAME,
values: ['SmartWeaveAction']
},
{
name: WarpTags.CONTRACT_TX_ID,
name: SmartWeaveTags.CONTRACT_TX_ID,
values: [contractId]
}
],
@@ -108,7 +108,7 @@ export class ArweaveGatewayInteractionsLoader implements InteractionsLoader {
const innerWritesVariables: GqlReqVariables = {
tags: [
{
name: WarpTags.INTERACT_WRITE,
name: SmartWeaveTags.INTERACT_WRITE,
values: [contractId]
}
],

View File

@@ -7,8 +7,9 @@ import {
DefinitionLoader,
getTag,
LoggerFactory,
WarpTags,
WarpCache
SmartWeaveTags,
WarpCache,
WarpTags
} from '@warp';
import Arweave from 'arweave';
import Transaction from 'arweave/web/lib/transaction';
@@ -50,8 +51,8 @@ export class ContractDefinitionLoader implements DefinitionLoader {
this.logger.debug('Contract tx and owner', benchmark.elapsed());
benchmark.reset();
const contractSrcTxId = forcedSrcTxId ? forcedSrcTxId : getTag(contractTx, WarpTags.CONTRACT_SRC_TX_ID);
const minFee = getTag(contractTx, WarpTags.MIN_FEE);
const contractSrcTxId = forcedSrcTxId ? forcedSrcTxId : getTag(contractTx, SmartWeaveTags.CONTRACT_SRC_TX_ID);
const minFee = getTag(contractTx, SmartWeaveTags.MIN_FEE);
this.logger.debug('Tags decoding', benchmark.elapsed());
benchmark.reset();
const s = await this.evalInitialState(contractTx);
@@ -99,11 +100,11 @@ export class ContractDefinitionLoader implements DefinitionLoader {
let srcMetaData;
if (contractType == 'wasm') {
wasmSrc = new WasmSrc(src as Buffer);
srcWasmLang = getTag(contractSrcTx, WarpTags.WASM_LANG);
srcWasmLang = getTag(contractSrcTx, SmartWeaveTags.WASM_LANG);
if (!srcWasmLang) {
throw new Error(`Wasm lang not set for wasm contract src ${contractSrcTxId}`);
}
srcMetaData = JSON.parse(getTag(contractSrcTx, WarpTags.WASM_META));
srcMetaData = JSON.parse(getTag(contractSrcTx, SmartWeaveTags.WASM_META));
}
this.logger.debug('Contract src tx load', benchmark.elapsed());
@@ -120,10 +121,10 @@ export class ContractDefinitionLoader implements DefinitionLoader {
}
private async evalInitialState(contractTx: Transaction): Promise<string> {
if (getTag(contractTx, WarpTags.INIT_STATE)) {
return getTag(contractTx, WarpTags.INIT_STATE);
} else if (getTag(contractTx, WarpTags.INIT_STATE_TX)) {
const stateTX = getTag(contractTx, WarpTags.INIT_STATE_TX);
if (getTag(contractTx, SmartWeaveTags.INIT_STATE)) {
return getTag(contractTx, SmartWeaveTags.INIT_STATE);
} else if (getTag(contractTx, SmartWeaveTags.INIT_STATE_TX)) {
const stateTX = getTag(contractTx, SmartWeaveTags.INIT_STATE_TX);
return this.arweaveWrapper.txDataString(stateTX);
} else {
return this.arweaveWrapper.txDataString(contractTx.id);

View File

@@ -1,4 +1,4 @@
import { GQLEdgeInterface, GQLTagInterface, LoggerFactory, WarpTags } from '@warp';
import { GQLEdgeInterface, GQLTagInterface, LoggerFactory, SmartWeaveTags } from '@warp';
/**
* A class that is responsible for retrieving "input" tag from the interaction transaction.
@@ -17,7 +17,7 @@ export class TagsParser {
if (TagsParser.hasMultipleInteractions(interactionTransaction)) {
this.logger.debug('Interaction transaction is using multiple input tx tag format.');
const contractTagIndex = interactionTransaction.node.tags.findIndex(
(tag) => tag.name === WarpTags.CONTRACT_TX_ID && tag.value === contractTxId
(tag) => tag.name === SmartWeaveTags.CONTRACT_TX_ID && tag.value === contractTxId
);
// if "Contract" is the last tag
if (interactionTransaction.node.tags.length - 1 === contractTagIndex) {
@@ -27,7 +27,7 @@ export class TagsParser {
// in this case the "Input" tag MUST be right after the "Contract" tag
const inputTag = interactionTransaction.node.tags[contractTagIndex + 1];
// if the tag after "Contract" tag has wrong name
if (inputTag.name !== WarpTags.INPUT) {
if (inputTag.name !== SmartWeaveTags.INPUT) {
this.logger.warn(`No 'Input' tag found after 'Contract' tag. Instead ${inputTag.name} was found`);
return undefined;
}
@@ -37,28 +37,30 @@ export class TagsParser {
// the "old way" - i.e. tags ordering does not matter,
// if there is at most one "Contract" tag
// - so returning the first occurrence of "Input" tag.
return interactionTransaction.node.tags.find((tag) => tag.name === WarpTags.INPUT);
return interactionTransaction.node.tags.find((tag) => tag.name === SmartWeaveTags.INPUT);
}
}
isInteractWrite(interactionTransaction: GQLEdgeInterface, contractTxId: string): boolean {
return interactionTransaction.node.tags.some(
(tag) => tag.name === WarpTags.INTERACT_WRITE && tag.value === contractTxId
(tag) => tag.name === SmartWeaveTags.INTERACT_WRITE && tag.value === contractTxId
);
}
getInteractWritesContracts(interactionTransaction: GQLEdgeInterface): string[] {
return interactionTransaction.node.tags.filter((tag) => tag.name === WarpTags.INTERACT_WRITE).map((t) => t.value);
return interactionTransaction.node.tags
.filter((tag) => tag.name === SmartWeaveTags.INTERACT_WRITE)
.map((t) => t.value);
}
getContractTag(interactionTransaction: GQLEdgeInterface): string {
return interactionTransaction.node.tags.find((tag) => tag.name === WarpTags.CONTRACT_TX_ID)?.value;
return interactionTransaction.node.tags.find((tag) => tag.name === SmartWeaveTags.CONTRACT_TX_ID)?.value;
}
getContractsWithInputs(interactionTransaction: GQLEdgeInterface): Map<string, GQLTagInterface> {
const result = new Map<string, GQLTagInterface>();
const contractTags = interactionTransaction.node.tags.filter((tag) => tag.name === WarpTags.CONTRACT_TX_ID);
const contractTags = interactionTransaction.node.tags.filter((tag) => tag.name === SmartWeaveTags.CONTRACT_TX_ID);
contractTags.forEach((contractTag) => {
result.set(contractTag.value, this.getInputTag(interactionTransaction, contractTag.value));
@@ -68,6 +70,6 @@ export class TagsParser {
}
static hasMultipleInteractions(interactionTransaction): boolean {
return interactionTransaction.node.tags.filter((tag) => tag.name === WarpTags.CONTRACT_TX_ID).length > 1;
return interactionTransaction.node.tags.filter((tag) => tag.name === SmartWeaveTags.CONTRACT_TX_ID).length > 1;
}
}

View File

@@ -1,4 +1,4 @@
import { ContractDefinition, getTag, LoggerFactory, WarpTags, stripTrailingSlash, WarpCache } from '@warp';
import { ContractDefinition, getTag, LoggerFactory, SmartWeaveTags, stripTrailingSlash, WarpCache } from '@warp';
import Arweave from 'arweave';
import { ContractDefinitionLoader } from './ContractDefinitionLoader';
import 'redstone-isomorphic';
@@ -53,7 +53,7 @@ export class WarpGatewayContractDefinitionLoader extends ContractDefinitionLoade
} else {
sourceTx = await this.arweaveWrapper.tx(result.srcTxId);
}
const srcMetaData = JSON.parse(getTag(sourceTx, WarpTags.WASM_META));
const srcMetaData = JSON.parse(getTag(sourceTx, SmartWeaveTags.WASM_META));
result.metadata = srcMetaData;
}
result.contractType = result.src ? 'js' : 'wasm';

View File

@@ -1,5 +1,5 @@
import Arweave from 'arweave';
import { GQLNodeInterface, GQLTagInterface, SigningFunction, WarpTags } from '@warp';
import { GQLNodeInterface, GQLTagInterface, SigningFunction, SmartWeaveTags } from '@warp';
import Transaction from 'arweave/node/lib/transaction';
import { CreateTransactionInterface } from 'arweave/node/common';
import { BlockData } from 'arweave/node/blocks';
@@ -45,12 +45,12 @@ export async function createTx(
interactionTx.addTag(tag.name.toString(), tag.value.toString());
}
}
interactionTx.addTag(WarpTags.APP_NAME, 'SmartWeaveAction');
interactionTx.addTag(SmartWeaveTags.APP_NAME, 'SmartWeaveAction');
// use real SDK version here?
interactionTx.addTag(WarpTags.APP_VERSION, '0.3.0');
interactionTx.addTag(WarpTags.SDK, 'Warp');
interactionTx.addTag(WarpTags.CONTRACT_TX_ID, contractId);
interactionTx.addTag(WarpTags.INPUT, JSON.stringify(input));
interactionTx.addTag(SmartWeaveTags.APP_VERSION, '0.3.0');
interactionTx.addTag(SmartWeaveTags.SDK, 'Warp');
interactionTx.addTag(SmartWeaveTags.CONTRACT_TX_ID, contractId);
interactionTx.addTag(SmartWeaveTags.INPUT, JSON.stringify(input));
if (signer) {
await signer(interactionTx);

View File

@@ -1,13 +1,13 @@
export const enum WarpErrorType {
export const enum SmartWeaveErrorType {
CONTRACT_NOT_FOUND = 'CONTRACT_NOT_FOUND'
}
export class WarpError extends Error {
public readonly type: WarpErrorType;
export class SmartWeaveError extends Error {
public readonly type: SmartWeaveErrorType;
public readonly otherInfo: any;
constructor(
type: WarpErrorType,
type: SmartWeaveErrorType,
optional: {
message?: string;
requestedTxId?: string;
@@ -22,7 +22,7 @@ export class WarpError extends Error {
this.otherInfo = optional;
}
public getType(): WarpErrorType {
public getType(): SmartWeaveErrorType {
return this.type;
}
}

View File

@@ -6,8 +6,8 @@ import {
ExecutorFactory,
HandlerApi,
LoggerFactory,
WarpError,
WarpErrorType
SmartWeaveError,
SmartWeaveErrorType
} from '@warp';
/*
@@ -89,7 +89,7 @@ export class Evolve implements ExecutionContextModifier {
return executionContext;
} catch (e) {
throw new WarpError(WarpErrorType.CONTRACT_NOT_FOUND, {
throw new SmartWeaveError(SmartWeaveErrorType.CONTRACT_NOT_FOUND, {
message: `Contract having txId: ${contractTxId} not found`,
requestedTxId: contractTxId
});

View File

@@ -1,14 +1,11 @@
/* eslint-disable */
import Arweave from 'arweave';
import {
LoggerFactory,
WarpNodeFactory
} from '../src';
import { LoggerFactory, WarpNodeFactory } from '../src';
import { TsLogFactory } from '../src/logging/node/TsLogFactory';
import path from "path";
import knex from "knex";
import fs from "fs";
import {JWKInterface} from "arweave/node/lib/wallet";
import path from 'path';
import knex from 'knex';
import fs from 'fs';
import { JWKInterface } from 'arweave/node/lib/wallet';
const logger = LoggerFactory.INST.create('Contract');
@@ -28,7 +25,6 @@ async function main() {
logging: false // Enable network request logging
});
const cacheDir = path.join(__dirname, 'db');
const knexConfig = knex({
client: 'sqlite3',
@@ -46,13 +42,16 @@ async function main() {
const initialState = fs.readFileSync(path.join(__dirname, 'data/js/token-pst.json'), 'utf8');
// case 1 - full deploy, js contract
const contractTxId = await warp.createContract.deploy({
wallet,
initState: initialState,
src: jsContractSrc,
}, true);
const contractTxId = await warp.createContract.deploy(
{
wallet,
initState: initialState,
src: jsContractSrc
},
true
);
logger.info("tx id:", contractTxId);
logger.info('tx id:', contractTxId);
// connecting to a given contract
const token = warp
@@ -61,25 +60,26 @@ async function main() {
// calling "writeInteraction" without connecting to a wallet first will cause a runtime error.
.connect(wallet);
const result = await token.bundleInteraction<any>({
function: "vrf",
}, {vrf: true});
const result = await token.bundleInteraction<any>(
{
function: 'vrf'
},
{ vrf: true }
);
console.log(result);
const { state } = await token.readState();
const {state} = await token.readState();
logger.info("State", state.vrf);
logger.info('State', state.vrf);
/*const result = await token.writeInteraction({
function: "transfer",
target: "33F0QHcb22W7LwWR1iRC8Az1ntZG09XQ03YWuw2ABqA",
qty: 10
}, [{
name: WarpTags.INTERACT_WRITE,
name: SmartWeaveTags.INTERACT_WRITE,
value: "33F0QHcb22W7LwWR1iRC8Az1ntZG09XQ03YWuw2ABqA"
},{
name: WarpTags.INTERACT_WRITE,
name: SmartWeaveTags.INTERACT_WRITE,
value: "4MnaOd-GvsE5iVQD4OhdY8DOrH3vo0QEqOw31HeIzQ0"
}
]);*/
@@ -88,7 +88,6 @@ async function main() {
//console.log(await redstoneLoader.load("33F0QHcb22W7LwWR1iRC8Az1ntZG09XQ03YWuw2ABqA", 0, 1_000_000));
// UjZsNC0t5Ex7TjU8FIGLZcn_b3Af9OoNBuVmTAgp2_U
/*const result1 = await token.readState();
@@ -111,8 +110,6 @@ async function main() {
//await sleep(1);
}*/
/*logger.info("Result from the sequencer", result);
// the new transaction is instantly available - ie. during the state read operation
@@ -123,7 +120,7 @@ async function main() {
}
function readJSON(path: string): JWKInterface {
const content = fs.readFileSync(path, "utf-8");
const content = fs.readFileSync(path, 'utf-8');
try {
return JSON.parse(content);
} catch (e) {
@@ -131,5 +128,4 @@ function readJSON(path: string): JWKInterface {
}
}
main().catch((e) => console.error(e));