UNPKG

wowok

Version:

Create, collaborate, and transact on your own terms with the AI-driven web3 collaboration protocol.

366 lines (334 loc) 16.8 kB
import { FnCallType, PermissionObject, RepositoryObject, PassportObject, MachineObject, ProgressObject, ProgressAddress, Protocol, TxbObject, OrderObject} from './protocol'; import { Machine } from './machine'; import { Bcs, array_unique,IsValidName, IsValidAddress, IsValidArray, IsValidInt, IsValidDesription, IsValidTokenType } from './utils' import { ERROR, Errors } from './exception'; import { type TransactionResult, Transaction as TransactionBlock, } from '@mysten/sui/transactions'; export interface OrderWrap { object: OrderObject; pay_token_type: string; } export interface Deliverable { msg: string; orders: OrderWrap[]; } export type ProgressNext = { next_node_name: string; forward: string; } export type ParentProgress = { parent_id: string; parent_session_id: number; operation: ProgressNext; } export type CurrentSessionId = TransactionResult; export interface Holder { forward: string; who?:string; deliverable: Deliverable; accomplished:boolean; time: string; } export interface Session { id?: number; // sid next_node: string; holders: Holder[]; weights: number; threshold: number; node?:string; bComplete?: boolean; } export interface History { id: number; // sid node: string; next_node: string; time: string; sessions: Session[]; } export class Progress { protected permission ; protected machine; protected object : TxbObject; protected txb; get_object() { return this.object } private constructor(txb:TransactionBlock, machine:MachineObject, permission:PermissionObject) { this.permission = permission; this.txb = txb; this.machine = machine; this.object = ''; } static From(txb:TransactionBlock, machine:MachineObject, permission:PermissionObject, object:TxbObject) : Progress{ let p = new Progress(txb, machine, permission) p.object = Protocol.TXB_OBJECT(txb, object); return p } static New(txb:TransactionBlock, machine:MachineObject, permission:PermissionObject, task?:string | null, passport?:PassportObject) : Progress { if (!Protocol.IsValidObjects([machine, permission])) { ERROR(Errors.IsValidObjects, 'machine & permission') } let p = new Progress(txb, machine, permission); let t = txb.pure.option('address', task ? task : undefined); if (passport) { p.object = txb.moveCall({ target:Protocol.Instance().progressFn('new_with_passport') as FnCallType, arguments: [passport, t, Protocol.TXB_OBJECT(txb, machine), Protocol.TXB_OBJECT(txb, permission)], }) } else { p.object = txb.moveCall({ target:Protocol.Instance().progressFn('new') as FnCallType, arguments: [t, Protocol.TXB_OBJECT(txb, machine), Protocol.TXB_OBJECT(txb, permission)], }) } return p } launch() : ProgressAddress { return this.txb.moveCall({ target:Protocol.Instance().progressFn('create') as FnCallType, arguments: [Protocol.TXB_OBJECT(this.txb, this.object)], }) } set_namedOperator(name:string, addresses:string[], passport?:PassportObject) { if (!IsValidName(name)) { ERROR(Errors.IsValidName, 'name') } if (name === Machine.OPERATOR_ORDER_PAYER) { ERROR(Errors.InvalidParam, 'name cannot be '+Machine.OPERATOR_ORDER_PAYER); } if (addresses.length > Progress.MAX_NAMED_OPERATOR_COUNT || !IsValidArray(addresses, IsValidAddress)) { ERROR(Errors.InvalidParam, 'addresses') } if (passport) { this.txb.moveCall({ target:Protocol.Instance().progressFn('namedOperator_set_with_passport') as FnCallType, arguments: [passport, Protocol.TXB_OBJECT(this.txb, this.object), this.txb.pure.string(name), this.txb.pure.vector('address', array_unique(addresses)), Protocol.TXB_OBJECT(this.txb, this.machine), Protocol.TXB_OBJECT(this.txb, this.permission)], }) } else { this.txb.moveCall({ target:Protocol.Instance().progressFn('namedOperator_set') as FnCallType, arguments: [Protocol.TXB_OBJECT(this.txb, this.object), this.txb.pure.string(name), this.txb.pure.vector('address', array_unique(addresses)), Protocol.TXB_OBJECT(this.txb, this.machine), Protocol.TXB_OBJECT(this.txb, this.permission)], }) } } bind_task(task_address:string, passport?:PassportObject) { if (!IsValidAddress(task_address)) { ERROR(Errors.IsValidAddress) } if (passport) { this.txb.moveCall({ target:Protocol.Instance().progressFn('task_set_with_passport') as FnCallType, arguments: [passport, Protocol.TXB_OBJECT(this.txb, this.object), this.txb.pure.address(task_address), Protocol.TXB_OBJECT(this.txb, this.machine), Protocol.TXB_OBJECT(this.txb, this.permission)], }) } else { this.txb.moveCall({ target:Protocol.Instance().progressFn('task_set') as FnCallType, arguments: [Protocol.TXB_OBJECT(this.txb, this.object), this.txb.pure.address(task_address), Protocol.TXB_OBJECT(this.txb, this.machine), Protocol.TXB_OBJECT(this.txb, this.permission)], }) } } set_context_repository(repository?:RepositoryObject, passport?:PassportObject) { if (repository && !Protocol.IsValidObjects([repository])) { ERROR(Errors.IsValidObjects, 'repository') } if (passport) { if (repository) { this.txb.moveCall({ target:Protocol.Instance().progressFn('context_repository_set_with_passport') as FnCallType, arguments: [passport, Protocol.TXB_OBJECT(this.txb, this.object), Protocol.TXB_OBJECT(this.txb, repository), Protocol.TXB_OBJECT(this.txb, this.machine), Protocol.TXB_OBJECT(this.txb, this.permission)], }) } else { this.txb.moveCall({ target:Protocol.Instance().progressFn('context_repository_none_with_passport') as FnCallType, arguments: [passport, Protocol.TXB_OBJECT(this.txb, this.object), Protocol.TXB_OBJECT(this.txb, this.machine), Protocol.TXB_OBJECT(this.txb, this.permission)], }) } } else { if (repository) { this.txb.moveCall({ target:Protocol.Instance().progressFn('context_repository_set') as FnCallType, arguments: [Protocol.TXB_OBJECT(this.txb, this.object), Protocol.TXB_OBJECT(this.txb, repository), Protocol.TXB_OBJECT(this.txb, this.machine), Protocol.TXB_OBJECT(this.txb, this.permission)], }) } else { this.txb.moveCall({ target:Protocol.Instance().progressFn('context_repository_none') as FnCallType, arguments: [Protocol.TXB_OBJECT(this.txb, this.object), Protocol.TXB_OBJECT(this.txb, this.machine), Protocol.TXB_OBJECT(this.txb, this.permission)], }) } } } unhold(next:ProgressNext, passport?:PassportObject) { if (!Progress.IsValidProgressNext(next)) { ERROR(Errors.InvalidParam, 'unhold') } const clock = this.txb.sharedObjectRef(Protocol.CLOCK_OBJECT); if (passport) { this.txb.moveCall({ target:Protocol.Instance().progressFn('unhold_with_passport') as FnCallType, arguments: [passport, Protocol.TXB_OBJECT(this.txb, this.object), Protocol.TXB_OBJECT(this.txb, this.machine), this.txb.pure.string(next.next_node_name), this.txb.pure.string(next.forward), Protocol.TXB_OBJECT(this.txb, this.permission), this.txb.object(clock)], }) } else { this.txb.moveCall({ target:Protocol.Instance().progressFn('unhold') as FnCallType, arguments: [Protocol.TXB_OBJECT(this.txb, this.object), Protocol.TXB_OBJECT(this.txb, this.machine), this.txb.pure.string(next.next_node_name), this.txb.pure.string(next.forward), Protocol.TXB_OBJECT(this.txb, this.permission), this.txb.object(clock)], }) } } parent_none(passport?:PassportObject) { if (passport) { this.txb.moveCall({ target:Protocol.Instance().progressFn('parent_none_with_passport') as FnCallType, arguments: [passport, Protocol.TXB_OBJECT(this.txb, this.object), Protocol.TXB_OBJECT(this.txb, this.machine), Protocol.TXB_OBJECT(this.txb, this.permission)], }) } else { this.txb.moveCall({ target:Protocol.Instance().progressFn('parent_none') as FnCallType, arguments: [Protocol.TXB_OBJECT(this.txb, this.object), Protocol.TXB_OBJECT(this.txb, this.machine), Protocol.TXB_OBJECT(this.txb, this.permission)], }) } } parent(parent:ParentProgress, passport?:PassportObject) { if (!IsValidAddress(parent.parent_id) || !IsValidInt(parent.parent_session_id)) { ERROR(Errors.InvalidParam, 'parent') } if (!parent.operation.next_node_name || !parent.operation.forward) { ERROR(Errors.InvalidParam, 'parent') } if (passport) { this.txb.moveCall({ target:Protocol.Instance().progressFn('parent_set_with_passport') as FnCallType, arguments: [passport, Protocol.TXB_OBJECT(this.txb, this.object), Protocol.TXB_OBJECT(this.txb, this.machine), this.txb.object(parent.parent_id), this.txb.pure.u64(parent.parent_session_id), this.txb.pure.string(parent.operation.next_node_name), this.txb.pure.string(parent.operation.forward), Protocol.TXB_OBJECT(this.txb, this.permission)], }) } else { this.txb.moveCall({ target:Protocol.Instance().progressFn('parent_set') as FnCallType, arguments: [Protocol.TXB_OBJECT(this.txb, this.object), Protocol.TXB_OBJECT(this.txb, this.machine), this.txb.object(parent.parent_id), this.txb.pure.u64(parent.parent_session_id), this.txb.pure.string(parent.operation.next_node_name), this.txb.pure.string(parent.operation.forward), Protocol.TXB_OBJECT(this.txb, this.permission)], }) } } private deliverable(deliverable:Deliverable) : TransactionResult { if (!IsValidDesription(deliverable.msg)) { ERROR(Errors.IsValidDesription, 'deliverable.msg') } if (deliverable.orders.length > 0 && !Protocol.IsValidObjects(deliverable.orders.map(v=>v.object))) { ERROR(Errors.IsValidObjects, 'deliverable.orders') } const d = this.txb.moveCall({ target:Protocol.Instance().progressFn('deliverable_new') as FnCallType, arguments: [this.txb.pure.string(deliverable.msg)], }) deliverable.orders.forEach(v => { if (!IsValidTokenType(v.pay_token_type)) { ERROR(Errors.IsValidTokenType, 'deliverable.orders:' + v.object) } this.txb.moveCall({ target:Protocol.Instance().orderFn('as_deliverable') as FnCallType, arguments: [this.txb.object(v.object), d], typeArguments:[v.pay_token_type] }) }) return d } next(next:ProgressNext, deliverable:Deliverable, passport?:PassportObject) : CurrentSessionId { if (!Progress.IsValidProgressNext(next)) { ERROR(Errors.InvalidParam, 'next') } const d = this.deliverable(deliverable); const clock = this.txb.sharedObjectRef(Protocol.CLOCK_OBJECT); if (passport) { return this.txb.moveCall({ target:Protocol.Instance().progressFn('next_with_passport') as FnCallType, arguments: [passport, Protocol.TXB_OBJECT(this.txb, this.object), Protocol.TXB_OBJECT(this.txb, this.machine), this.txb.pure.string(next.next_node_name), this.txb.pure.string(next.forward), d, Protocol.TXB_OBJECT(this.txb, this.permission), this.txb.object(clock)], }) } else { return this.txb.moveCall({ target:Protocol.Instance().progressFn('next') as FnCallType, arguments: [Protocol.TXB_OBJECT(this.txb, this.object), Protocol.TXB_OBJECT(this.txb, this.machine), this.txb.pure.string(next.next_node_name), this.txb.pure.string(next.forward), d, Protocol.TXB_OBJECT(this.txb, this.permission), this.txb.object(clock)], }) } } hold(next:ProgressNext, hold:boolean) : CurrentSessionId { if (!Progress.IsValidProgressNext(next)) { ERROR(Errors.InvalidParam, 'hold') } const clock = this.txb.sharedObjectRef(Protocol.CLOCK_OBJECT); return this.txb.moveCall({ target:Protocol.Instance().progressFn('hold') as FnCallType, arguments: [Protocol.TXB_OBJECT(this.txb, this.object), Protocol.TXB_OBJECT(this.txb, this.machine), this.txb.pure.string(next.next_node_name), this.txb.pure.string(next.forward), this.txb.pure.bool(hold), Protocol.TXB_OBJECT(this.txb, this.permission), this.txb.object(clock)], }) } static QueryForwardGuard = async (progress:ProgressObject, machine:MachineObject, sender:string, next_node:string, forward:string): Promise<string | undefined> => { if (!progress || !machine || !next_node || !forward) { // prior_node maybe '' ERROR(Errors.InvalidParam, 'QueryForwardGuard'); return ; } const txb = new TransactionBlock(); txb.moveCall({ target:Protocol.Instance().progressFn('query_guard') as FnCallType, arguments:[Protocol.TXB_OBJECT(txb, progress), Protocol.TXB_OBJECT(txb, machine), txb.pure.string(next_node), txb.pure.string(forward)], }); const res = await Protocol.Client().devInspectTransactionBlock({sender:sender, transactionBlock:txb}); if (res.results?.length === 1 && res.results[0].returnValues?.length === 1) { const guard = Bcs.getInstance().de('Option<address>', Uint8Array.from(res.results[0].returnValues[0][0])); return guard?.some?('0x'+guard?.some):undefined; } } static DeSessions = (session: any) : Session[] => { let sessions : Session[] = []; session?.fields?.contents?.forEach((v:any) => { var s:Session = {next_node: v.fields.key, holders:[], weights:v.fields.value.fields.weights, threshold:v.fields.value.fields.threshold}; v.fields.value.fields.forwards.fields.contents.forEach((i:any) => { s.holders.push({forward:i.fields.key, accomplished:i.fields.value.fields.accomplished, time:i.fields.value.fields.time, who:i.fields.value.fields.who, deliverable:{msg:i.fields.value.fields.msg, orders:i.fields.value.fields.orders ?? []}, }) }) sessions.push(s); }) return sessions; } static DeHistories = (fields: any) : History[] => { return fields?.map((v:any) => { return Progress.DeHistory(v?.data?.content?.fields) }) } static DeHistory = (data: any) : History => { return {id:parseInt(data?.name), node:data?.value?.fields?.node, next_node:data?.value?.fields?.next_node, sessions:Progress.DeSessions(data?.value.fields?.session), time: data?.value?.fields?.time } } static MAX_NAMED_OPERATOR_COUNT = 20; static MAX_DELEVERABLE_ORDER_COUNT = 20; static IsValidProgressNext = (next:ProgressNext) => { return IsValidName(next.forward) && IsValidName(next.next_node_name); } }