Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions examples/voting/contract.spec.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { Bytes, Uint64 } from '@algorandfoundation/algorand-typescript'
import { bytesToUint8Array, TestExecutionContext } from '@algorandfoundation/algorand-typescript-testing'
import { encodingUtil, TestExecutionContext } from '@algorandfoundation/algorand-typescript-testing'
import { DynamicArray, UintN8 } from '@algorandfoundation/algorand-typescript/arc4'
import nacl from 'tweetnacl'
import { afterEach, describe, expect, it } from 'vitest'
Expand Down Expand Up @@ -50,7 +50,7 @@ describe('VotingRoundApp', () => {
contract.bootstrap(ctx.any.txn.payment({ receiver: app.address, amount: boostrapMinBalanceReq }))

const account = ctx.any.account()
const signature = nacl.sign.detached(bytesToUint8Array(account.bytes), keyPair.secretKey)
const signature = nacl.sign.detached(encodingUtil.toExternalValue(account.bytes), keyPair.secretKey)
ctx.txn.createScope([ctx.any.txn.applicationCall({ sender: account })]).execute(() => {
const preconditions = contract.getPreconditions(Bytes(signature))

Expand All @@ -67,7 +67,7 @@ describe('VotingRoundApp', () => {
contract.bootstrap(ctx.any.txn.payment({ receiver: app.address, amount: boostrapMinBalanceReq }))

const account = ctx.any.account()
const signature = nacl.sign.detached(bytesToUint8Array(account.bytes), keyPair.secretKey)
const signature = nacl.sign.detached(encodingUtil.toExternalValue(account.bytes), keyPair.secretKey)
const answerIds = new DynamicArray<UintN8>(
...Array(13)
.fill(0)
Expand Down
7 changes: 6 additions & 1 deletion src/index.ts
Original file line number Diff line number Diff line change
@@ -1,2 +1,7 @@
import { internal } from '@algorandfoundation/algorand-typescript'

export { TestExecutionContext } from './test-execution-context'
export { asUint8Array as bytesToUint8Array } from './util'
export const encodingUtil = {
...internal.encodingUtil,
toExternalValue: internal.primitives.toExternalValue,
}
1 change: 1 addition & 0 deletions src/subcontexts/ledger-context.ts
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ export class LedgerContext {
blocks = new Uint64Map<BlockData>()
globalData = new GlobalData()

/* @internal */
addAppIdContractMap(appId: internal.primitives.StubUint64Compat, contract: BaseContract): void {
this.appIdContractMap.set(appId, contract)
}
Expand Down
25 changes: 8 additions & 17 deletions src/subcontexts/transaction-context.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { bytes, Contract, internal, TransactionType, uint64 } from '@algorandfoundation/algorand-typescript'
import { AbiMetadata, getContractMethodAbiMetadata } from '../abi-metadata'
import { TRANSACTION_GROUP_MAX_SIZE } from '../constants'
import { checkRoutingConditions } from '../context-helpers/context-util'
import { lazyContext } from '../context-helpers/internal-context'
import { DecodedLogs, decodeLogs, LogDecoding } from '../decode-logs'
import { testInvariant } from '../errors'
Expand Down Expand Up @@ -49,23 +50,6 @@ interface ExecutionScope {
execute: <TReturn>(body: () => TReturn) => TReturn
}

export const checkRoutingConditions = (appId: uint64, metadata: AbiMetadata) => {
const appData = lazyContext.getApplicationData(appId)
const isCreating = appData.isCreating
if (isCreating && metadata.onCreate === 'disallow') {
throw new internal.errors.CodeError('method can not be called while creating')
}
if (!isCreating && metadata.onCreate === 'require') {
throw new internal.errors.CodeError('method can only be called while creating')
}
const txn = lazyContext.activeGroup.activeTransaction
if (txn instanceof ApplicationTransaction && metadata.allowActions && !metadata.allowActions.includes(txn.onCompletion)) {
throw new internal.errors.CodeError(
`method can only be called with one of the following on_completion values: ${metadata.allowActions.join(', ')}`,
)
}
}

export class DeferredAppCall<TParams extends unknown[], TReturn> {
constructor(
private readonly appId: uint64,
Expand Down Expand Up @@ -106,6 +90,7 @@ export class TransactionContext {
}
}

/* internal */
ensureScope(group: Transaction[], activeTransactionIndex?: number): ExecutionScope {
if (!this.#activeGroup || !this.#activeGroup.transactions.length) {
return this.createScope(group, activeTransactionIndex)
Expand Down Expand Up @@ -200,6 +185,7 @@ export class TransactionGroup {
return this.activeTransaction.appId.id
}

/* internal */
get constructingItxn() {
if (!this.constructingItxnGroup.length) {
internal.errors.internalError('itxn field without itxn begin')
Expand All @@ -221,9 +207,12 @@ export class TransactionGroup {
Object.assign(activeTransaction, filteredFields)
}

/* internal */
addInnerTransactionGroup(...itxns: InnerTxn[]) {
this.itxnGroups.push(new ItxnGroup(itxns))
}

/* internal */
beginInnerTransactionGroup() {
if (this.constructingItxnGroup.length) {
internal.errors.internalError('itxn begin without itxn submit')
Expand All @@ -235,13 +224,15 @@ export class TransactionGroup {
this.constructingItxnGroup.push({} as InnerTxnFields)
}

/* internal */
appendInnerTransactionGroup() {
if (!this.constructingItxnGroup.length) {
internal.errors.internalError('itxn next without itxn begin')
}
this.constructingItxnGroup.push({ type: TransactionType.Payment } as InnerTxnFields)
}

/* internal */
submitInnerTransactionGroup() {
if (!this.constructingItxnGroup.length) {
internal.errors.internalError('itxn submit without itxn begin')
Expand Down
10 changes: 10 additions & 0 deletions src/test-execution-context.ts
Original file line number Diff line number Diff line change
Expand Up @@ -44,26 +44,32 @@ export class TestExecutionContext implements internal.ExecutionContext {
this.#activeLogicSigArgs = []
}

/* @internal */
account(address?: bytes): Account {
return new AccountCls(address)
}

/* @internal */
application(id?: uint64): Application {
return new ApplicationCls(id)
}

/* @internal */
asset(id?: uint64): Asset {
return new AssetCls(id)
}

/* @internal */
log(value: bytes): void {
this.txn.appendLog(value)
}

/* @internal */
exportLogs<const T extends [...LogDecoding[]]>(appId: uint64, ...decoding: T): DecodedLogs<T> {
return this.txn.exportLogs(appId, ...decoding)
}

/* @internal */
get op() {
return ops
}
Expand All @@ -87,12 +93,14 @@ export class TestExecutionContext implements internal.ExecutionContext {
return this.#defaultSender
}

/* @internal */
get abiMetadata() {
return {
captureMethodConfig,
}
}

/* @internal */
get gtxn() {
return {
Transaction: (index: uint64) => this.txn.activeGroup.getTransaction(index),
Expand All @@ -105,6 +113,7 @@ export class TestExecutionContext implements internal.ExecutionContext {
}
}

/* @internal */
get itxn() {
return {
submitGroup: itxnSubmitGroup,
Expand All @@ -117,6 +126,7 @@ export class TestExecutionContext implements internal.ExecutionContext {
}
}

/* @internal */
get state() {
return {
GlobalState,
Expand Down
5 changes: 3 additions & 2 deletions tsconfig.build.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,9 @@
"compilerOptions": {
"outDir": "./dist/",
"noEmit": false,
"declaration": true
"declaration": true,
"stripInternal": true
},
"include": ["src/**/*.ts"],
"exclude": ["src/**/*.spec.ts", "src/**/*.test.ts", "src/**/tests/**", "examples/**/*.ts",]
"exclude": ["src/**/*.spec.ts", "src/**/*.test.ts", "src/**/tests/**", "examples/**/*.ts"]
}
Loading