diff --git a/.github/workflows/cd.yaml b/.github/workflows/cd.yaml index 479d0646..d8536c3b 100644 --- a/.github/workflows/cd.yaml +++ b/.github/workflows/cd.yaml @@ -26,7 +26,7 @@ jobs: skip-commit: "true" tag-prefix: "" skip-on-empty: "false" - + - name: Create Release uses: softprops/action-gh-release@v1 if: ${{ steps.tag.outputs.skipped == 'false' }} diff --git a/copier.yaml b/copier.yaml index 2ccf0859..4a3a79ac 100644 --- a/copier.yaml +++ b/copier.yaml @@ -55,6 +55,29 @@ deployment_language: TypeScript: "typescript" default: "python" +use_python_pytest: + type: bool + when: "{{ deployment_language == 'python' }}" + help: Do you want to include unit tests (via pytest)? + # deployment_language is empty when using the default_language + default: |- + {% if deployment_language|length == 0 or deployment_language == 'python' -%} + yes + {%- else -%} + no + {%- endif %} + +use_typescript_jest: + type: bool + when: "{{ deployment_language == 'typescript' }}" + help: Do you want to include unit tests (via jest)? + default: |- + {% if deployment_language == 'typescript' -%} + yes + {%- else -%} + no + {%- endif %} + python_linter: type: str help: Do you want to use a Python linter? @@ -86,11 +109,6 @@ use_python_mypy: no {%- endif %} -use_python_pytest: - type: bool - help: Do you want to include unit tests (via pytest)? - default: yes - use_python_pip_audit: type: bool when: "{{ preset_name == 'production' }}" diff --git a/includes/contract_name_kebab.jinja b/includes/contract_name_kebab.jinja new file mode 100644 index 00000000..69505487 --- /dev/null +++ b/includes/contract_name_kebab.jinja @@ -0,0 +1 @@ +{{- contract_name.split('_')|join('-') -}} diff --git a/includes/contract_name_pascal.jinja b/includes/contract_name_pascal.jinja new file mode 100644 index 00000000..e0f3c4d3 --- /dev/null +++ b/includes/contract_name_pascal.jinja @@ -0,0 +1 @@ +{{- contract_name.split('_')|map('capitalize')|join -}} diff --git a/template_content/.algokit.toml.jinja b/template_content/.algokit.toml.jinja index 786275c6..29ab5a94 100644 --- a/template_content/.algokit.toml.jinja +++ b/template_content/.algokit.toml.jinja @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] {%- if deployment_language == 'python' %} diff --git a/template_content/.gitignore.jinja b/template_content/.gitignore.jinja index 832924c3..4a926bbb 100644 --- a/template_content/.gitignore.jinja +++ b/template_content/.gitignore.jinja @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/template_content/README.md.jinja b/template_content/README.md.jinja index 8113229b..1339f29c 100644 --- a/template_content/README.md.jinja +++ b/template_content/README.md.jinja @@ -107,6 +107,9 @@ For pull requests and pushes to `main` branch against this repository the follow {%- endif %} {%- if use_python_pytest %} - Python tests are executed using [pytest](https://docs.pytest.org/) +{%- endif %} +{%- if use_typescript_jest %} + - Typescript tests are executed using [Jest](https://jestjs.io/) {%- endif %} - Smart contract artifacts are built - Smart contract artifacts are checked for [output stability](https://github.com/algorandfoundation/algokit-cli/blob/main/docs/articles/output_stability.md) @@ -131,12 +134,12 @@ This project makes use of Python to build Algorand smart contracts. The followin - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils]({% if deployment_language == "typescript" %}https://github.com/algorandfoundation/algokit-utils-ts{% else %}https://github.com/algorandfoundation/algokit-utils-py{% endif %}) - A set of core Algorand utilities that make it easier to build solutions on Algorand. - [Poetry](https://python-poetry.org/): Python packaging and dependency management. -{%- if use_python_black -%} +{%- if use_python_black %} - [Black](https://github.com/psf/black): A Python code formatter. {%- endif %} -{%- if python_linter == "ruff" -%} +{%- if python_linter == "ruff" %} - [Ruff](https://github.com/charliermarsh/ruff): An extremely fast Python linter. -{% elif python_linter == "flake8" -%} +{%- elif python_linter == "flake8" %} - [Flake8](https://flake8.pycqa.org/en/latest/): A Python linter for style guide enforcement. {%- endif %} {%- if use_python_mypy %} @@ -149,14 +152,16 @@ This project makes use of Python to build Algorand smart contracts. The followin - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. {%- endif %} {%- if use_pre_commit %} - - [pre-commit](https://pre-commit.com/): A framework for managing and maintaining multi-language pre-commit hooks, to enable pre-commit you need to run `pre-commit install` in the root of the repository. This will install the pre-commit hooks and run them against modified files when committing. If any of the hooks fail, the commit will be aborted. To run the hooks on all files, use `pre-commit run --all-files`. +- [pre-commit](https://pre-commit.com/): A framework for managing and maintaining multi-language pre-commit hooks, to enable pre-commit you need to run `pre-commit install` in the root of the repository. This will install the pre-commit hooks and run them against modified files when committing. If any of the hooks fail, the commit will be aborted. To run the hooks on all files, use `pre-commit run --all-files`. {%- endif %} {%- if deployment_language == "typescript" %} -- [npm](https://www.npmjs.com/): Node.js package manager -- [TypeScript](https://www.typescriptlang.org/): Strongly typed programming language that builds on JavaScript -- [ts-node-dev](https://github.com/wclr/ts-node-dev): TypeScript development execution environment -{% endif -%} - +- [npm](https://www.npmjs.com/): Node.js package manager. +- [TypeScript](https://www.typescriptlang.org/): Strongly typed programming language that builds on JavaScript. +- [ts-node-dev](https://github.com/wclr/ts-node-dev): TypeScript development execution environment. +{%- endif %} +{%- if use_typescript_jest %} +- [Jest](https://jestjs.io/): Automated testing. +{%- endif %} {% if ide_vscode %} It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. -{% endif %} +{%- endif %} diff --git a/template_content/smart_contracts/config.py.jinja b/template_content/smart_contracts/config.py.jinja index 8cefdd67..3a1d85fe 100644 --- a/template_content/smart_contracts/config.py.jinja +++ b/template_content/smart_contracts/config.py.jinja @@ -59,6 +59,6 @@ contracts = [ ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/template_content/smart_contracts/helpers/build.py.jinja b/template_content/smart_contracts/helpers/build.py.jinja index 7dc047b5..206a183d 100644 --- a/template_content/smart_contracts/helpers/build.py.jinja +++ b/template_content/smart_contracts/helpers/build.py.jinja @@ -37,7 +37,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/template_content/smart_contracts/{{ contract_name }}/{% if deployment_language == 'python' %}deploy_config.py{% endif %}.jinja b/template_content/smart_contracts/{{ contract_name }}/{% if deployment_language == 'python' %}deploy_config.py{% endif %}.jinja index bb169ac2..239e90b0 100644 --- a/template_content/smart_contracts/{{ contract_name }}/{% if deployment_language == 'python' %}deploy_config.py{% endif %}.jinja +++ b/template_content/smart_contracts/{{ contract_name }}/{% if deployment_language == 'python' %}deploy_config.py{% endif %}.jinja @@ -15,10 +15,10 @@ def deploy( deployer: algokit_utils.Account, ) -> None: from smart_contracts.artifacts.{{ contract_name }}.client import ( - {{ contract_name.split('_')|map('capitalize')|join }}Client, + {% include pathjoin('includes', 'contract_name_pascal.jinja') %}Client, ) - app_client = {{ contract_name.split('_')|map('capitalize')|join }}Client( + app_client = {% include pathjoin('includes', 'contract_name_pascal.jinja') %}Client( algod_client, creator=deployer, indexer_client=indexer_client, diff --git a/template_content/smart_contracts/{{ contract_name }}/{% if deployment_language == 'typescript' %}deploy-config.ts{% endif %}.jinja b/template_content/smart_contracts/{{ contract_name }}/{% if deployment_language == 'typescript' %}deploy-config.ts{% endif %}.jinja index 325fb24a..319c3a80 100644 --- a/template_content/smart_contracts/{{ contract_name }}/{% if deployment_language == 'typescript' %}deploy-config.ts{% endif %}.jinja +++ b/template_content/smart_contracts/{{ contract_name }}/{% if deployment_language == 'typescript' %}deploy-config.ts{% endif %}.jinja @@ -1,9 +1,9 @@ import * as algokit from '@algorandfoundation/algokit-utils' -import { {{ contract_name.split('_')|map('capitalize')|join }}Client } from '../artifacts/{{ contract_name }}/client' +import { {% include pathjoin('includes', 'contract_name_pascal.jinja') %}Client } from '../artifacts/{{ contract_name }}/client' // Below is a showcase of various deployment options you can use in TypeScript Client export async function deploy() { - console.log('=== Deploying {{ contract_name.split('_')|map('capitalize')|join }} ===') + console.log('=== Deploying {% include pathjoin('includes', 'contract_name_pascal.jinja') %} ===') const algod = algokit.getAlgoClient() const indexer = algokit.getAlgoIndexerClient() @@ -16,7 +16,7 @@ export async function deploy() { }, algod, ) - const appClient = new {{ contract_name.split('_')|map('capitalize')|join }}Client( + const appClient = new {% include pathjoin('includes', 'contract_name_pascal.jinja') %}Client( { resolveBy: 'creatorAndName', findExistingUsing: indexer, diff --git a/template_content/{% if deployment_language == 'typescript' %}.prettierignore{% endif %} b/template_content/{% if deployment_language == 'typescript' or use_typescript_jest %}.prettierignore{% endif %} similarity index 100% rename from template_content/{% if deployment_language == 'typescript' %}.prettierignore{% endif %} rename to template_content/{% if deployment_language == 'typescript' or use_typescript_jest %}.prettierignore{% endif %} diff --git a/template_content/{% if deployment_language == 'typescript' %}.prettierrc.js{% endif %} b/template_content/{% if deployment_language == 'typescript' or use_typescript_jest %}.prettierrc.js{% endif %} similarity index 100% rename from template_content/{% if deployment_language == 'typescript' %}.prettierrc.js{% endif %} rename to template_content/{% if deployment_language == 'typescript' or use_typescript_jest %}.prettierrc.js{% endif %} diff --git a/template_content/{% if deployment_language == 'typescript' %}package.json{% endif %}.jinja b/template_content/{% if deployment_language == 'typescript' or use_typescript_jest %}package.json{% endif %}.jinja similarity index 72% rename from template_content/{% if deployment_language == 'typescript' %}package.json{% endif %}.jinja rename to template_content/{% if deployment_language == 'typescript' or use_typescript_jest %}package.json{% endif %}.jinja index 4a3ecaea..360bdaef 100644 --- a/template_content/{% if deployment_language == 'typescript' %}package.json{% endif %}.jinja +++ b/template_content/{% if deployment_language == 'typescript' or use_typescript_jest %}package.json{% endif %}.jinja @@ -6,6 +6,9 @@ "scripts": { "deploy": "ts-node-dev --transpile-only --watch .env -r dotenv/config smart_contracts/index.ts", "deploy:ci": "ts-node --transpile-only -r dotenv/config smart_contracts/index.ts", + {%- if use_typescript_jest %} + "test": "jest --coverage", + {%- endif %} "format": "prettier --write ." }, "engines": { @@ -16,8 +19,14 @@ "algosdk": "^2.5.0" }, "devDependencies": { + {%- if use_typescript_jest %} + "@types/jest": "^29.5.11", + {%- endif %} "dotenv": "^16.0.3", "prettier": "^2.8.4", + {%- if use_typescript_jest %} + "ts-jest": "^29.1.1", + {%- endif %} "ts-node-dev": "^2.0.0", "typescript": "^4.9.5" } diff --git a/template_content/{% if deployment_language == 'typescript' or use_typescript_jest %}tsconfig.json{% endif %} b/template_content/{% if deployment_language == 'typescript' or use_typescript_jest %}tsconfig.json{% endif %} new file mode 100644 index 00000000..7c762042 --- /dev/null +++ b/template_content/{% if deployment_language == 'typescript' or use_typescript_jest %}tsconfig.json{% endif %} @@ -0,0 +1,24 @@ +{ + "compilerOptions": { + "target": "ES2020", + "declaration": true, + "declarationMap": true, + "sourceMap": true, + "strict": true, + "noImplicitReturns": true, + "noFallthroughCasesInSwitch": true, + "esModuleInterop": true, + "experimentalDecorators": true, + "emitDecoratorMetadata": true, + "skipLibCheck": true, + "forceConsistentCasingInFileNames": true, + "allowJs": false, + "allowSyntheticDefaultImports": true, + "moduleResolution": "Node", + "resolveJsonModule": true, + "isolatedModules": true, + "noEmit": true + }, + "include": ["src/**/*.ts"], + "exclude": ["node_modules", "dist", "coverage"] +} diff --git a/template_content/{% if ide_vscode %}.tours{% endif %}/getting-started-with-your-algokit-project.tour.jinja b/template_content/{% if ide_vscode %}.tours{% endif %}/getting-started-with-your-algokit-project.tour.jinja index fecd0d06..b3342a3f 100644 --- a/template_content/{% if ide_vscode %}.tours{% endif %}/getting-started-with-your-algokit-project.tour.jinja +++ b/template_content/{% if ide_vscode %}.tours{% endif %}/getting-started-with-your-algokit-project.tour.jinja @@ -23,9 +23,9 @@ "line": 32 }, { - "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "file": "tests/{% if deployment_language == 'typescript' %}{% include pathjoin('includes', 'contract_name_kebab.jinja') %}.spec.ts{% else %}{{ contract_name }}_test.py{% endif %}", + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": {% if deployment_language == 'typescript' %}39{% else %}36{% endif %} }, { "file": ".env.localnet.template", diff --git a/template_content/{% if use_github_actions %}.github{% endif %}/workflows/checks.yaml.jinja b/template_content/{% if use_github_actions %}.github{% endif %}/workflows/checks.yaml.jinja index edd56e6e..5b431364 100644 --- a/template_content/{% if use_github_actions %}.github{% endif %}/workflows/checks.yaml.jinja +++ b/template_content/{% if use_github_actions %}.github{% endif %}/workflows/checks.yaml.jinja @@ -66,6 +66,9 @@ jobs: # stop the build if there are Python syntax errors or undefined names poetry run flake8 . {%- endif %} + + - name: Build smart contracts + run: poetry run python -m smart_contracts build {%- if use_python_mypy %} - name: Check types with mypy @@ -79,9 +82,12 @@ jobs: set -o pipefail poetry run pytest --junitxml=pytest-junit.xml {%- endif %} +{%- if use_typescript_jest %} - - name: Build smart contracts - run: poetry run python -m smart_contracts build + - name: Run tests + shell: bash + run: npm run test +{%- endif %} - name: Check output stability of the smart contracts shell: bash @@ -93,7 +99,7 @@ jobs: - name: Run deployer against LocalNet {%- if deployment_language == 'typescript' %} - run: npm run --prefix smart_contracts deploy:ci + run: npm run deploy:ci {%- elif deployment_language == 'python' %} run: poetry run python -m smart_contracts deploy {%- endif %} diff --git a/template_content/{% if use_python_pytest %}tests{% endif %}/conftest.py b/template_content/{% if use_python_pytest %}tests{% endif %}/conftest.py index 06a89eb0..b0622e78 100644 --- a/template_content/{% if use_python_pytest %}tests{% endif %}/conftest.py +++ b/template_content/{% if use_python_pytest %}tests{% endif %}/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/template_content/{% if use_python_pytest %}tests{% endif %}/{% if use_python_pytest %}{{ contract_name }}_test.py{% endif %}.jinja b/template_content/{% if use_python_pytest %}tests{% endif %}/{% if use_python_pytest %}{{ contract_name }}_test.py{% endif %}.jinja index 49a75ad6..71f8beec 100644 --- a/template_content/{% if use_python_pytest %}tests{% endif %}/{% if use_python_pytest %}{{ contract_name }}_test.py{% endif %}.jinja +++ b/template_content/{% if use_python_pytest %}tests{% endif %}/{% if use_python_pytest %}{{ contract_name }}_test.py{% endif %}.jinja @@ -1,36 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.{{ contract_name }} import contract as {{ contract_name }}_contract - - -@pytest.fixture(scope="session") -def {{ contract_name }}_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return {{ contract_name }}_contract.app.build(algod_client) +from smart_contracts.artifacts.{{ contract_name }}.client import {% include pathjoin('includes', 'contract_name_pascal.jinja') %}Client @pytest.fixture(scope="session") def {{ contract_name }}_client( - algod_client: AlgodClient, {{ contract_name }}_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> {% include pathjoin('includes', 'contract_name_pascal.jinja') %}Client: + config.configure( + debug=True, + # trace_all=True, + ) + + client = {% include pathjoin('includes', 'contract_name_pascal.jinja') %}Client( algod_client, - app_spec={{ contract_name }}_app_spec, - signer=get_localnet_default_account(algod_client), - {%- if preset_name == 'production' %} - template_values={"UPDATABLE": 1, "DELETABLE": 1}, - {%- endif %} + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello({{ contract_name }}_client: ApplicationClient) -> None: - result = {{ contract_name }}_client.call({{ contract_name }}_contract.hello, name="World") +def test_says_hello({{ contract_name }}_client: {% include pathjoin('includes', 'contract_name_pascal.jinja') %}Client) -> None: + result = {{ contract_name }}_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + {{ contract_name }}_client: {% include pathjoin('includes', 'contract_name_pascal.jinja') %}Client, algod_client: AlgodClient +) -> None: + result = ( + {{ contract_name }}_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/template_content/{% if use_typescript_jest %}jest.config.ts{% endif %} b/template_content/{% if use_typescript_jest %}jest.config.ts{% endif %} new file mode 100644 index 00000000..381e1e05 --- /dev/null +++ b/template_content/{% if use_typescript_jest %}jest.config.ts{% endif %} @@ -0,0 +1,16 @@ +/* + * For a detailed explanation regarding each configuration property and type check, visit: + * https://jestjs.io/docs/configuration + */ +import type { Config } from 'jest' + +const config: Config = { + preset: 'ts-jest', + verbose: true, + transform: { + '^.+\\.tsx?$': 'ts-jest', + }, + testPathIgnorePatterns: ['node_modules', '.venv', 'coverage'], + testTimeout: 10000, +} +export default config diff --git a/template_content/{% if use_typescript_jest %}tests{% endif %}/{% if use_typescript_jest %}{% include pathjoin('includes', 'contract_name_kebab.jinja') %}.spec.ts{% endif %}.jinja b/template_content/{% if use_typescript_jest %}tests{% endif %}/{% if use_typescript_jest %}{% include pathjoin('includes', 'contract_name_kebab.jinja') %}.spec.ts{% endif %}.jinja new file mode 100644 index 00000000..76a06304 --- /dev/null +++ b/template_content/{% if use_typescript_jest %}tests{% endif %}/{% if use_typescript_jest %}{% include pathjoin('includes', 'contract_name_kebab.jinja') %}.spec.ts{% endif %}.jinja @@ -0,0 +1,53 @@ +import { algorandFixture } from '@algorandfoundation/algokit-utils/testing' +import { {% include pathjoin('includes', 'contract_name_pascal.jinja') %}Client } from '../smart_contracts/artifacts/{{ contract_name }}/client' +import { Account, Algodv2, Indexer } from 'algosdk' +import * as algokit from '@algorandfoundation/algokit-utils' + +describe('{{ contract_name.split('_')|join(' ') }} contract', () => { + const localnet = algorandFixture() + beforeAll(() => { + algokit.Config.configure({ + debug: true, + // traceAll: true, + }) + }) + beforeEach(localnet.beforeEach) + + const deploy = async (account: Account, algod: Algodv2, indexer: Indexer) => { + const client = new {% include pathjoin('includes', 'contract_name_pascal.jinja') %}Client( + { + resolveBy: 'creatorAndName', + findExistingUsing: indexer, + sender: account, + creatorAddress: account.addr, + }, + algod, + ) + await client.deploy({ + allowDelete: true, + allowUpdate: true, + onSchemaBreak: 'replace', + onUpdate: 'update', + }) + return { client } + } + + test('says hello', async () => { + const { algod, indexer, testAccount } = localnet.context + const { client } = await deploy(testAccount, algod, indexer) + + const result = await client.hello({ name: 'World' }) + + expect(result.return).toBe('Hello, World') + }) + + test('simulate says hello with correct budget consumed', async () => { + const { algod, indexer, testAccount } = localnet.context + const { client } = await deploy(testAccount, algod, indexer) + const result = await client.compose().hello({ name: 'World' }).hello({ name: 'Jane' }).simulate() + + expect(result.methodResults[0].returnValue).toBe('Hello, World') + expect(result.methodResults[1].returnValue).toBe('Hello, Jane') + expect(result.simulateResponse.txnGroups[0].appBudgetConsumed).toBeLessThan(100) + }) +}) diff --git a/tests/test_templates.py b/tests/test_templates.py index 0771ec24..c1b7fdc9 100644 --- a/tests/test_templates.py +++ b/tests/test_templates.py @@ -182,6 +182,9 @@ def get_questions_from_copier_yaml( "use_python_pip_audit", "use_dispenser", "use_pre_commit", + # this also needs deployment_language set to typescript + # and is already tested via the typescript tests + "use_typescript_jest", } ignored_keys.update(DEFAULT_PARAMETERS) diff --git a/tests_generated/test_default_parameters/.algokit.toml b/tests_generated/test_default_parameters/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_default_parameters/.algokit.toml +++ b/tests_generated/test_default_parameters/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_default_parameters/.gitignore b/tests_generated/test_default_parameters/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_default_parameters/.gitignore +++ b/tests_generated/test_default_parameters/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_default_parameters/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_default_parameters/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_default_parameters/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_default_parameters/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_default_parameters/README.md b/tests_generated/test_default_parameters/README.md index 9c741b46..339465c9 100644 --- a/tests_generated/test_default_parameters/README.md +++ b/tests_generated/test_default_parameters/README.md @@ -52,8 +52,9 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_default_parameters/smart_contracts/config.py b/tests_generated/test_default_parameters/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_default_parameters/smart_contracts/config.py +++ b/tests_generated/test_default_parameters/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_default_parameters/smart_contracts/helpers/build.py b/tests_generated/test_default_parameters/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_default_parameters/smart_contracts/helpers/build.py +++ b/tests_generated/test_default_parameters/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_default_parameters/tests/conftest.py b/tests_generated/test_default_parameters/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_default_parameters/tests/conftest.py +++ b/tests_generated/test_default_parameters/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_default_parameters/tests/hello_world_test.py b/tests_generated/test_default_parameters/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_default_parameters/tests/hello_world_test.py +++ b/tests_generated/test_default_parameters/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_deployment_language-python/.algokit.toml b/tests_generated/test_deployment_language-python/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_deployment_language-python/.algokit.toml +++ b/tests_generated/test_deployment_language-python/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_deployment_language-python/.gitignore b/tests_generated/test_deployment_language-python/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_deployment_language-python/.gitignore +++ b/tests_generated/test_deployment_language-python/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_deployment_language-python/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_deployment_language-python/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_deployment_language-python/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_deployment_language-python/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_deployment_language-python/README.md b/tests_generated/test_deployment_language-python/README.md index 750ea8ad..b5e2f672 100644 --- a/tests_generated/test_deployment_language-python/README.md +++ b/tests_generated/test_deployment_language-python/README.md @@ -52,8 +52,9 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_deployment_language-python/pyproject.toml b/tests_generated/test_deployment_language-python/pyproject.toml index 2d6b5198..e74425f3 100644 --- a/tests_generated/test_deployment_language-python/pyproject.toml +++ b/tests_generated/test_deployment_language-python/pyproject.toml @@ -8,7 +8,7 @@ readme = "README.md" [tool.poetry.dependencies] python = "^3.10" beaker-pyteal = "^1.1.1" -algokit-utils = "^2.2.0b1" +algokit-utils = "^2.2.0" python-dotenv = "^1.0.0" [tool.poetry.group.dev.dependencies] diff --git a/tests_generated/test_deployment_language-python/smart_contracts/__main__.py b/tests_generated/test_deployment_language-python/smart_contracts/__main__.py index c30e558b..331f4564 100644 --- a/tests_generated/test_deployment_language-python/smart_contracts/__main__.py +++ b/tests_generated/test_deployment_language-python/smart_contracts/__main__.py @@ -6,6 +6,7 @@ from smart_contracts.config import contracts from smart_contracts.helpers.build import build +from smart_contracts.helpers.deploy import deploy # # Uncomment the following lines to enable auto generation of AVM Debugger compliant sourceMap and simulation trace file. # # Learn more about using AlgoKit AVM Debugger to debug your TEAL source codes and inspect various kinds of Algorand transactions in atomic groups -> https://github.com/algorandfoundation/algokit-avm-vscode-debugger diff --git a/tests_generated/test_deployment_language-python/smart_contracts/config.py b/tests_generated/test_deployment_language-python/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_deployment_language-python/smart_contracts/config.py +++ b/tests_generated/test_deployment_language-python/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_deployment_language-python/smart_contracts/helpers/build.py b/tests_generated/test_deployment_language-python/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_deployment_language-python/smart_contracts/helpers/build.py +++ b/tests_generated/test_deployment_language-python/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_deployment_language-python/tests/conftest.py b/tests_generated/test_deployment_language-python/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_deployment_language-python/tests/conftest.py +++ b/tests_generated/test_deployment_language-python/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_deployment_language-python/tests/hello_world_test.py b/tests_generated/test_deployment_language-python/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_deployment_language-python/tests/hello_world_test.py +++ b/tests_generated/test_deployment_language-python/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_deployment_language-typescript/.algokit.toml b/tests_generated/test_deployment_language-typescript/.algokit.toml index 08717563..ad84a3ce 100644 --- a/tests_generated/test_deployment_language-typescript/.algokit.toml +++ b/tests_generated/test_deployment_language-typescript/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "npm run deploy:ci" diff --git a/tests_generated/test_deployment_language-typescript/.copier-answers.yml b/tests_generated/test_deployment_language-typescript/.copier-answers.yml index 7e61565d..e8ab2e8a 100644 --- a/tests_generated/test_deployment_language-typescript/.copier-answers.yml +++ b/tests_generated/test_deployment_language-typescript/.copier-answers.yml @@ -15,5 +15,5 @@ indexer_token: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa preset_name: starter project_name: test_deployment_language-typescript use_python_black: true -use_python_pytest: true +use_typescript_jest: true diff --git a/tests_generated/test_deployment_language-typescript/.gitignore b/tests_generated/test_deployment_language-typescript/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_deployment_language-typescript/.gitignore +++ b/tests_generated/test_deployment_language-typescript/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_deployment_language-typescript/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_deployment_language-typescript/.tours/getting-started-with-your-algokit-project.tour index d7882591..09841231 100644 --- a/tests_generated/test_deployment_language-typescript/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_deployment_language-typescript/.tours/getting-started-with-your-algokit-project.tour @@ -23,9 +23,9 @@ "line": 32 }, { - "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "file": "tests/hello-world.spec.ts", + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 39 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_deployment_language-typescript/.vscode/settings.json b/tests_generated/test_deployment_language-typescript/.vscode/settings.json index 64ef1305..9f03b8da 100644 --- a/tests_generated/test_deployment_language-typescript/.vscode/settings.json +++ b/tests_generated/test_deployment_language-typescript/.vscode/settings.json @@ -27,7 +27,6 @@ "editor.defaultFormatter": "ms-python.black-formatter", }, "black-formatter.args": ["--config=pyproject.toml"], - "python.testing.pytestEnabled": true, // On Windows, if execution policy is set to Signed (default) then it won't be able to activate the venv // so instead let's set it to RemoteSigned for VS Code terminal diff --git a/tests_generated/test_deployment_language-typescript/README.md b/tests_generated/test_deployment_language-typescript/README.md index a7956c64..e6a68831 100644 --- a/tests_generated/test_deployment_language-typescript/README.md +++ b/tests_generated/test_deployment_language-typescript/README.md @@ -53,12 +53,12 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-ts) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. -- [pytest](https://docs.pytest.org/): Automated testing. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -- [npm](https://www.npmjs.com/): Node.js package manager -- [TypeScript](https://www.typescriptlang.org/): Strongly typed programming language that builds on JavaScript -- [ts-node-dev](https://github.com/wclr/ts-node-dev): TypeScript development execution environment +- [npm](https://www.npmjs.com/): Node.js package manager. +- [TypeScript](https://www.typescriptlang.org/): Strongly typed programming language that builds on JavaScript. +- [ts-node-dev](https://github.com/wclr/ts-node-dev): TypeScript development execution environment. +- [Jest](https://jestjs.io/): Automated testing. It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. - diff --git a/tests_generated/test_deployment_language-typescript/jest.config.ts b/tests_generated/test_deployment_language-typescript/jest.config.ts new file mode 100644 index 00000000..381e1e05 --- /dev/null +++ b/tests_generated/test_deployment_language-typescript/jest.config.ts @@ -0,0 +1,16 @@ +/* + * For a detailed explanation regarding each configuration property and type check, visit: + * https://jestjs.io/docs/configuration + */ +import type { Config } from 'jest' + +const config: Config = { + preset: 'ts-jest', + verbose: true, + transform: { + '^.+\\.tsx?$': 'ts-jest', + }, + testPathIgnorePatterns: ['node_modules', '.venv', 'coverage'], + testTimeout: 10000, +} +export default config diff --git a/tests_generated/test_deployment_language-typescript/package.json b/tests_generated/test_deployment_language-typescript/package.json index 4a3ecaea..4afc3fb0 100644 --- a/tests_generated/test_deployment_language-typescript/package.json +++ b/tests_generated/test_deployment_language-typescript/package.json @@ -6,6 +6,7 @@ "scripts": { "deploy": "ts-node-dev --transpile-only --watch .env -r dotenv/config smart_contracts/index.ts", "deploy:ci": "ts-node --transpile-only -r dotenv/config smart_contracts/index.ts", + "test": "jest --coverage", "format": "prettier --write ." }, "engines": { @@ -16,8 +17,10 @@ "algosdk": "^2.5.0" }, "devDependencies": { + "@types/jest": "^29.5.11", "dotenv": "^16.0.3", "prettier": "^2.8.4", + "ts-jest": "^29.1.1", "ts-node-dev": "^2.0.0", "typescript": "^4.9.5" } diff --git a/tests_generated/test_deployment_language-typescript/pyproject.toml b/tests_generated/test_deployment_language-typescript/pyproject.toml index 957829dc..5b443fd5 100644 --- a/tests_generated/test_deployment_language-typescript/pyproject.toml +++ b/tests_generated/test_deployment_language-typescript/pyproject.toml @@ -13,14 +13,9 @@ python-dotenv = "^1.0.0" [tool.poetry.group.dev.dependencies] black = {extras = ["d"], version = "*"} -pytest = "*" -pytest-cov = "*" pip-audit = "*" [build-system] requires = ["poetry-core"] build-backend = "poetry.core.masonry.api" - -[tool.pytest.ini_options] -pythonpath = ["smart_contracts", "tests"] diff --git a/tests_generated/test_deployment_language-typescript/smart_contracts/config.py b/tests_generated/test_deployment_language-typescript/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_deployment_language-typescript/smart_contracts/config.py +++ b/tests_generated/test_deployment_language-typescript/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_deployment_language-typescript/smart_contracts/helpers/build.py b/tests_generated/test_deployment_language-typescript/smart_contracts/helpers/build.py index 20d6d6d6..167ee907 100644 --- a/tests_generated/test_deployment_language-typescript/smart_contracts/helpers/build.py +++ b/tests_generated/test_deployment_language-typescript/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_deployment_language-typescript/tests/__init__.py b/tests_generated/test_deployment_language-typescript/tests/__init__.py deleted file mode 100644 index e69de29b..00000000 diff --git a/tests_generated/test_deployment_language-typescript/tests/conftest.py b/tests_generated/test_deployment_language-typescript/tests/conftest.py deleted file mode 100644 index 06a89eb0..00000000 --- a/tests_generated/test_deployment_language-typescript/tests/conftest.py +++ /dev/null @@ -1,25 +0,0 @@ -from pathlib import Path - -import pytest -from algokit_utils import ( - get_algod_client, - is_localnet, -) -from algosdk.v2client.algod import AlgodClient -from dotenv import load_dotenv - - -@pytest.fixture(autouse=True, scope="session") -def environment_fixture() -> None: - env_path = Path(__file__).parent.parent / ".env.localnet" - load_dotenv(env_path) - - -@pytest.fixture(scope="session") -def algod_client() -> AlgodClient: - client = get_algod_client() - - # you can remove this assertion to test on other networks, - # included here to prevent accidentally running against other networks - assert is_localnet(client) - return client diff --git a/tests_generated/test_deployment_language-typescript/tests/hello-world.spec.ts b/tests_generated/test_deployment_language-typescript/tests/hello-world.spec.ts new file mode 100644 index 00000000..81e62fa1 --- /dev/null +++ b/tests_generated/test_deployment_language-typescript/tests/hello-world.spec.ts @@ -0,0 +1,53 @@ +import { algorandFixture } from '@algorandfoundation/algokit-utils/testing' +import { HelloWorldClient } from '../smart_contracts/artifacts/hello_world/client' +import { Account, Algodv2, Indexer } from 'algosdk' +import * as algokit from '@algorandfoundation/algokit-utils' + +describe('hello world contract', () => { + const localnet = algorandFixture() + beforeAll(() => { + algokit.Config.configure({ + debug: true, + // traceAll: true, + }) + }) + beforeEach(localnet.beforeEach) + + const deploy = async (account: Account, algod: Algodv2, indexer: Indexer) => { + const client = new HelloWorldClient( + { + resolveBy: 'creatorAndName', + findExistingUsing: indexer, + sender: account, + creatorAddress: account.addr, + }, + algod, + ) + await client.deploy({ + allowDelete: true, + allowUpdate: true, + onSchemaBreak: 'replace', + onUpdate: 'update', + }) + return { client } + } + + test('says hello', async () => { + const { algod, indexer, testAccount } = localnet.context + const { client } = await deploy(testAccount, algod, indexer) + + const result = await client.hello({ name: 'World' }) + + expect(result.return).toBe('Hello, World') + }) + + test('simulate says hello with correct budget consumed', async () => { + const { algod, indexer, testAccount } = localnet.context + const { client } = await deploy(testAccount, algod, indexer) + const result = await client.compose().hello({ name: 'World' }).hello({ name: 'Jane' }).simulate() + + expect(result.methodResults[0].returnValue).toBe('Hello, World') + expect(result.methodResults[1].returnValue).toBe('Hello, Jane') + expect(result.simulateResponse.txnGroups[0].appBudgetConsumed).toBeLessThan(100) + }) +}) diff --git a/tests_generated/test_deployment_language-typescript/tests/hello_world_test.py b/tests_generated/test_deployment_language-typescript/tests/hello_world_test.py deleted file mode 100644 index 50fd3324..00000000 --- a/tests_generated/test_deployment_language-typescript/tests/hello_world_test.py +++ /dev/null @@ -1,33 +0,0 @@ -import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) -from algosdk.v2client.algod import AlgodClient - -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) - - -@pytest.fixture(scope="session") -def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( - algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), - ) - client.create() - return client - - -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") - - assert result.return_value == "Hello, World" diff --git a/tests_generated/test_deployment_language-typescript/tsconfig.json b/tests_generated/test_deployment_language-typescript/tsconfig.json new file mode 100644 index 00000000..7c762042 --- /dev/null +++ b/tests_generated/test_deployment_language-typescript/tsconfig.json @@ -0,0 +1,24 @@ +{ + "compilerOptions": { + "target": "ES2020", + "declaration": true, + "declarationMap": true, + "sourceMap": true, + "strict": true, + "noImplicitReturns": true, + "noFallthroughCasesInSwitch": true, + "esModuleInterop": true, + "experimentalDecorators": true, + "emitDecoratorMetadata": true, + "skipLibCheck": true, + "forceConsistentCasingInFileNames": true, + "allowJs": false, + "allowSyntheticDefaultImports": true, + "moduleResolution": "Node", + "resolveJsonModule": true, + "isolatedModules": true, + "noEmit": true + }, + "include": ["src/**/*.ts"], + "exclude": ["node_modules", "dist", "coverage"] +} diff --git a/tests_generated/test_ide_jetbrains-False/.algokit.toml b/tests_generated/test_ide_jetbrains-False/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_ide_jetbrains-False/.algokit.toml +++ b/tests_generated/test_ide_jetbrains-False/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_ide_jetbrains-False/.gitignore b/tests_generated/test_ide_jetbrains-False/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_ide_jetbrains-False/.gitignore +++ b/tests_generated/test_ide_jetbrains-False/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_ide_jetbrains-False/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_ide_jetbrains-False/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_ide_jetbrains-False/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_ide_jetbrains-False/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_ide_jetbrains-False/README.md b/tests_generated/test_ide_jetbrains-False/README.md index a6e6cbc9..dd816786 100644 --- a/tests_generated/test_ide_jetbrains-False/README.md +++ b/tests_generated/test_ide_jetbrains-False/README.md @@ -52,8 +52,9 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_ide_jetbrains-False/smart_contracts/config.py b/tests_generated/test_ide_jetbrains-False/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_ide_jetbrains-False/smart_contracts/config.py +++ b/tests_generated/test_ide_jetbrains-False/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_ide_jetbrains-False/smart_contracts/helpers/build.py b/tests_generated/test_ide_jetbrains-False/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_ide_jetbrains-False/smart_contracts/helpers/build.py +++ b/tests_generated/test_ide_jetbrains-False/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_ide_jetbrains-False/tests/conftest.py b/tests_generated/test_ide_jetbrains-False/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_ide_jetbrains-False/tests/conftest.py +++ b/tests_generated/test_ide_jetbrains-False/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_ide_jetbrains-False/tests/hello_world_test.py b/tests_generated/test_ide_jetbrains-False/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_ide_jetbrains-False/tests/hello_world_test.py +++ b/tests_generated/test_ide_jetbrains-False/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_ide_jetbrains-True/.algokit.toml b/tests_generated/test_ide_jetbrains-True/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_ide_jetbrains-True/.algokit.toml +++ b/tests_generated/test_ide_jetbrains-True/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_ide_jetbrains-True/.gitignore b/tests_generated/test_ide_jetbrains-True/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_ide_jetbrains-True/.gitignore +++ b/tests_generated/test_ide_jetbrains-True/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_ide_jetbrains-True/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_ide_jetbrains-True/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_ide_jetbrains-True/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_ide_jetbrains-True/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_ide_jetbrains-True/README.md b/tests_generated/test_ide_jetbrains-True/README.md index db1a8477..6f9dd938 100644 --- a/tests_generated/test_ide_jetbrains-True/README.md +++ b/tests_generated/test_ide_jetbrains-True/README.md @@ -52,8 +52,9 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_ide_jetbrains-True/pyproject.toml b/tests_generated/test_ide_jetbrains-True/pyproject.toml index f6e6bd10..91415256 100644 --- a/tests_generated/test_ide_jetbrains-True/pyproject.toml +++ b/tests_generated/test_ide_jetbrains-True/pyproject.toml @@ -8,7 +8,7 @@ readme = "README.md" [tool.poetry.dependencies] python = "^3.10" beaker-pyteal = "^1.1.1" -algokit-utils = "^2.2.0b1" +algokit-utils = "^2.2.0" python-dotenv = "^1.0.0" [tool.poetry.group.dev.dependencies] diff --git a/tests_generated/test_ide_jetbrains-True/smart_contracts/config.py b/tests_generated/test_ide_jetbrains-True/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_ide_jetbrains-True/smart_contracts/config.py +++ b/tests_generated/test_ide_jetbrains-True/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_ide_jetbrains-True/smart_contracts/helpers/build.py b/tests_generated/test_ide_jetbrains-True/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_ide_jetbrains-True/smart_contracts/helpers/build.py +++ b/tests_generated/test_ide_jetbrains-True/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_ide_jetbrains-True/tests/conftest.py b/tests_generated/test_ide_jetbrains-True/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_ide_jetbrains-True/tests/conftest.py +++ b/tests_generated/test_ide_jetbrains-True/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_ide_jetbrains-True/tests/hello_world_test.py b/tests_generated/test_ide_jetbrains-True/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_ide_jetbrains-True/tests/hello_world_test.py +++ b/tests_generated/test_ide_jetbrains-True/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_ide_vscode-False/.algokit.toml b/tests_generated/test_ide_vscode-False/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_ide_vscode-False/.algokit.toml +++ b/tests_generated/test_ide_vscode-False/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_ide_vscode-False/.gitignore b/tests_generated/test_ide_vscode-False/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_ide_vscode-False/.gitignore +++ b/tests_generated/test_ide_vscode-False/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_ide_vscode-False/README.md b/tests_generated/test_ide_vscode-False/README.md index 2b4ba433..035dadc0 100644 --- a/tests_generated/test_ide_vscode-False/README.md +++ b/tests_generated/test_ide_vscode-False/README.md @@ -52,6 +52,8 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. + diff --git a/tests_generated/test_ide_vscode-False/smart_contracts/config.py b/tests_generated/test_ide_vscode-False/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_ide_vscode-False/smart_contracts/config.py +++ b/tests_generated/test_ide_vscode-False/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_ide_vscode-False/smart_contracts/helpers/build.py b/tests_generated/test_ide_vscode-False/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_ide_vscode-False/smart_contracts/helpers/build.py +++ b/tests_generated/test_ide_vscode-False/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_ide_vscode-False/tests/conftest.py b/tests_generated/test_ide_vscode-False/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_ide_vscode-False/tests/conftest.py +++ b/tests_generated/test_ide_vscode-False/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_ide_vscode-False/tests/hello_world_test.py b/tests_generated/test_ide_vscode-False/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_ide_vscode-False/tests/hello_world_test.py +++ b/tests_generated/test_ide_vscode-False/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_ide_vscode-True/.algokit.toml b/tests_generated/test_ide_vscode-True/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_ide_vscode-True/.algokit.toml +++ b/tests_generated/test_ide_vscode-True/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_ide_vscode-True/.gitignore b/tests_generated/test_ide_vscode-True/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_ide_vscode-True/.gitignore +++ b/tests_generated/test_ide_vscode-True/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_ide_vscode-True/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_ide_vscode-True/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_ide_vscode-True/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_ide_vscode-True/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_ide_vscode-True/README.md b/tests_generated/test_ide_vscode-True/README.md index 6e126934..13d67ecd 100644 --- a/tests_generated/test_ide_vscode-True/README.md +++ b/tests_generated/test_ide_vscode-True/README.md @@ -52,8 +52,9 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_ide_vscode-True/smart_contracts/config.py b/tests_generated/test_ide_vscode-True/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_ide_vscode-True/smart_contracts/config.py +++ b/tests_generated/test_ide_vscode-True/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_ide_vscode-True/smart_contracts/helpers/build.py b/tests_generated/test_ide_vscode-True/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_ide_vscode-True/smart_contracts/helpers/build.py +++ b/tests_generated/test_ide_vscode-True/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_ide_vscode-True/tests/conftest.py b/tests_generated/test_ide_vscode-True/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_ide_vscode-True/tests/conftest.py +++ b/tests_generated/test_ide_vscode-True/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_ide_vscode-True/tests/hello_world_test.py b/tests_generated/test_ide_vscode-True/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_ide_vscode-True/tests/hello_world_test.py +++ b/tests_generated/test_ide_vscode-True/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_preset_name-production/.algokit.toml b/tests_generated/test_preset_name-production/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_preset_name-production/.algokit.toml +++ b/tests_generated/test_preset_name-production/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_preset_name-production/.github/workflows/checks.yaml b/tests_generated/test_preset_name-production/.github/workflows/checks.yaml index c03719d7..15449bf4 100644 --- a/tests_generated/test_preset_name-production/.github/workflows/checks.yaml +++ b/tests_generated/test_preset_name-production/.github/workflows/checks.yaml @@ -55,6 +55,9 @@ jobs: # stop the build if there are Python syntax errors or undefined names poetry run ruff . + - name: Build smart contracts + run: poetry run python -m smart_contracts build + - name: Check types with mypy run: poetry run mypy @@ -64,9 +67,6 @@ jobs: set -o pipefail poetry run pytest --junitxml=pytest-junit.xml - - name: Build smart contracts - run: poetry run python -m smart_contracts build - - name: Check output stability of the smart contracts shell: bash run: | diff --git a/tests_generated/test_preset_name-production/.gitignore b/tests_generated/test_preset_name-production/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_preset_name-production/.gitignore +++ b/tests_generated/test_preset_name-production/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_preset_name-production/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_preset_name-production/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_preset_name-production/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_preset_name-production/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_preset_name-production/README.md b/tests_generated/test_preset_name-production/README.md index 753f8b50..a01f8c9d 100644 --- a/tests_generated/test_preset_name-production/README.md +++ b/tests_generated/test_preset_name-production/README.md @@ -100,11 +100,12 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter.- [Ruff](https://github.com/charliermarsh/ruff): An extremely fast Python linter. - +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. +- [Ruff](https://github.com/charliermarsh/ruff): An extremely fast Python linter. - [mypy](https://mypy-lang.org/): Static type checker. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. - - [pre-commit](https://pre-commit.com/): A framework for managing and maintaining multi-language pre-commit hooks, to enable pre-commit you need to run `pre-commit install` in the root of the repository. This will install the pre-commit hooks and run them against modified files when committing. If any of the hooks fail, the commit will be aborted. To run the hooks on all files, use `pre-commit run --all-files`. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +- [pre-commit](https://pre-commit.com/): A framework for managing and maintaining multi-language pre-commit hooks, to enable pre-commit you need to run `pre-commit install` in the root of the repository. This will install the pre-commit hooks and run them against modified files when committing. If any of the hooks fail, the commit will be aborted. To run the hooks on all files, use `pre-commit run --all-files`. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_preset_name-production/smart_contracts/config.py b/tests_generated/test_preset_name-production/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_preset_name-production/smart_contracts/config.py +++ b/tests_generated/test_preset_name-production/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_preset_name-production/smart_contracts/helpers/build.py b/tests_generated/test_preset_name-production/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_preset_name-production/smart_contracts/helpers/build.py +++ b/tests_generated/test_preset_name-production/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_preset_name-production/tests/conftest.py b/tests_generated/test_preset_name-production/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_preset_name-production/tests/conftest.py +++ b/tests_generated/test_preset_name-production/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_preset_name-production/tests/hello_world_test.py b/tests_generated/test_preset_name-production/tests/hello_world_test.py index 55f83335..05066855 100644 --- a/tests_generated/test_preset_name-production/tests/hello_world_test.py +++ b/tests_generated/test_preset_name-production/tests/hello_world_test.py @@ -1,34 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), - template_values={"UPDATABLE": 1, "DELETABLE": 1}, + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_preset_name-starter/.algokit.toml b/tests_generated/test_preset_name-starter/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_preset_name-starter/.algokit.toml +++ b/tests_generated/test_preset_name-starter/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_preset_name-starter/.gitignore b/tests_generated/test_preset_name-starter/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_preset_name-starter/.gitignore +++ b/tests_generated/test_preset_name-starter/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_preset_name-starter/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_preset_name-starter/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_preset_name-starter/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_preset_name-starter/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_preset_name-starter/README.md b/tests_generated/test_preset_name-starter/README.md index ca5cc1a0..b669c04d 100644 --- a/tests_generated/test_preset_name-starter/README.md +++ b/tests_generated/test_preset_name-starter/README.md @@ -52,8 +52,9 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_preset_name-starter/smart_contracts/config.py b/tests_generated/test_preset_name-starter/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_preset_name-starter/smart_contracts/config.py +++ b/tests_generated/test_preset_name-starter/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_preset_name-starter/smart_contracts/helpers/build.py b/tests_generated/test_preset_name-starter/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_preset_name-starter/smart_contracts/helpers/build.py +++ b/tests_generated/test_preset_name-starter/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_preset_name-starter/tests/conftest.py b/tests_generated/test_preset_name-starter/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_preset_name-starter/tests/conftest.py +++ b/tests_generated/test_preset_name-starter/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_preset_name-starter/tests/hello_world_test.py b/tests_generated/test_preset_name-starter/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_preset_name-starter/tests/hello_world_test.py +++ b/tests_generated/test_preset_name-starter/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_python_linter-flake8/.algokit.toml b/tests_generated/test_python_linter-flake8/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_python_linter-flake8/.algokit.toml +++ b/tests_generated/test_python_linter-flake8/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_python_linter-flake8/.gitignore b/tests_generated/test_python_linter-flake8/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_python_linter-flake8/.gitignore +++ b/tests_generated/test_python_linter-flake8/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_python_linter-flake8/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_python_linter-flake8/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_python_linter-flake8/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_python_linter-flake8/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_python_linter-flake8/README.md b/tests_generated/test_python_linter-flake8/README.md index d3d1d3f6..acc99c2e 100644 --- a/tests_generated/test_python_linter-flake8/README.md +++ b/tests_generated/test_python_linter-flake8/README.md @@ -52,8 +52,10 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter.- [Flake8](https://flake8.pycqa.org/en/latest/): A Python linter for style guide enforcement. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. +- [Flake8](https://flake8.pycqa.org/en/latest/): A Python linter for style guide enforcement. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_python_linter-flake8/pyproject.toml b/tests_generated/test_python_linter-flake8/pyproject.toml index fcc06250..6e6c9809 100644 --- a/tests_generated/test_python_linter-flake8/pyproject.toml +++ b/tests_generated/test_python_linter-flake8/pyproject.toml @@ -8,7 +8,7 @@ readme = "README.md" [tool.poetry.dependencies] python = "^3.10" beaker-pyteal = "^1.1.1" -algokit-utils = "^2.2.0b1" +algokit-utils = "^2.2.0" python-dotenv = "^1.0.0" [tool.poetry.group.dev.dependencies] diff --git a/tests_generated/test_python_linter-flake8/smart_contracts/config.py b/tests_generated/test_python_linter-flake8/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_python_linter-flake8/smart_contracts/config.py +++ b/tests_generated/test_python_linter-flake8/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_python_linter-flake8/smart_contracts/helpers/build.py b/tests_generated/test_python_linter-flake8/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_python_linter-flake8/smart_contracts/helpers/build.py +++ b/tests_generated/test_python_linter-flake8/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_python_linter-flake8/tests/conftest.py b/tests_generated/test_python_linter-flake8/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_python_linter-flake8/tests/conftest.py +++ b/tests_generated/test_python_linter-flake8/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_python_linter-flake8/tests/hello_world_test.py b/tests_generated/test_python_linter-flake8/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_python_linter-flake8/tests/hello_world_test.py +++ b/tests_generated/test_python_linter-flake8/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_python_linter-none/.algokit.toml b/tests_generated/test_python_linter-none/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_python_linter-none/.algokit.toml +++ b/tests_generated/test_python_linter-none/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_python_linter-none/.gitignore b/tests_generated/test_python_linter-none/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_python_linter-none/.gitignore +++ b/tests_generated/test_python_linter-none/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_python_linter-none/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_python_linter-none/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_python_linter-none/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_python_linter-none/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_python_linter-none/README.md b/tests_generated/test_python_linter-none/README.md index 6917dbd4..a12f4dc2 100644 --- a/tests_generated/test_python_linter-none/README.md +++ b/tests_generated/test_python_linter-none/README.md @@ -52,8 +52,9 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_python_linter-none/smart_contracts/config.py b/tests_generated/test_python_linter-none/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_python_linter-none/smart_contracts/config.py +++ b/tests_generated/test_python_linter-none/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_python_linter-none/smart_contracts/helpers/build.py b/tests_generated/test_python_linter-none/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_python_linter-none/smart_contracts/helpers/build.py +++ b/tests_generated/test_python_linter-none/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_python_linter-none/tests/conftest.py b/tests_generated/test_python_linter-none/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_python_linter-none/tests/conftest.py +++ b/tests_generated/test_python_linter-none/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_python_linter-none/tests/hello_world_test.py b/tests_generated/test_python_linter-none/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_python_linter-none/tests/hello_world_test.py +++ b/tests_generated/test_python_linter-none/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_python_linter-ruff/.algokit.toml b/tests_generated/test_python_linter-ruff/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_python_linter-ruff/.algokit.toml +++ b/tests_generated/test_python_linter-ruff/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_python_linter-ruff/.gitignore b/tests_generated/test_python_linter-ruff/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_python_linter-ruff/.gitignore +++ b/tests_generated/test_python_linter-ruff/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_python_linter-ruff/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_python_linter-ruff/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_python_linter-ruff/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_python_linter-ruff/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_python_linter-ruff/README.md b/tests_generated/test_python_linter-ruff/README.md index bbd3f62c..59752e69 100644 --- a/tests_generated/test_python_linter-ruff/README.md +++ b/tests_generated/test_python_linter-ruff/README.md @@ -52,9 +52,10 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter.- [Ruff](https://github.com/charliermarsh/ruff): An extremely fast Python linter. - +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. +- [Ruff](https://github.com/charliermarsh/ruff): An extremely fast Python linter. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_python_linter-ruff/smart_contracts/config.py b/tests_generated/test_python_linter-ruff/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_python_linter-ruff/smart_contracts/config.py +++ b/tests_generated/test_python_linter-ruff/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_python_linter-ruff/smart_contracts/helpers/build.py b/tests_generated/test_python_linter-ruff/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_python_linter-ruff/smart_contracts/helpers/build.py +++ b/tests_generated/test_python_linter-ruff/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_python_linter-ruff/tests/conftest.py b/tests_generated/test_python_linter-ruff/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_python_linter-ruff/tests/conftest.py +++ b/tests_generated/test_python_linter-ruff/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_python_linter-ruff/tests/hello_world_test.py b/tests_generated/test_python_linter-ruff/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_python_linter-ruff/tests/hello_world_test.py +++ b/tests_generated/test_python_linter-ruff/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_python/.algokit.toml b/tests_generated/test_smart_contract_generator_default_production_preset_python/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_python/.algokit.toml +++ b/tests_generated/test_smart_contract_generator_default_production_preset_python/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_python/.github/workflows/checks.yaml b/tests_generated/test_smart_contract_generator_default_production_preset_python/.github/workflows/checks.yaml index c03719d7..15449bf4 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_python/.github/workflows/checks.yaml +++ b/tests_generated/test_smart_contract_generator_default_production_preset_python/.github/workflows/checks.yaml @@ -55,6 +55,9 @@ jobs: # stop the build if there are Python syntax errors or undefined names poetry run ruff . + - name: Build smart contracts + run: poetry run python -m smart_contracts build + - name: Check types with mypy run: poetry run mypy @@ -64,9 +67,6 @@ jobs: set -o pipefail poetry run pytest --junitxml=pytest-junit.xml - - name: Build smart contracts - run: poetry run python -m smart_contracts build - - name: Check output stability of the smart contracts shell: bash run: | diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_python/.gitignore b/tests_generated/test_smart_contract_generator_default_production_preset_python/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_python/.gitignore +++ b/tests_generated/test_smart_contract_generator_default_production_preset_python/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_python/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_smart_contract_generator_default_production_preset_python/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_python/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_smart_contract_generator_default_production_preset_python/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_python/README.md b/tests_generated/test_smart_contract_generator_default_production_preset_python/README.md index 6fb357f6..051dc9f3 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_python/README.md +++ b/tests_generated/test_smart_contract_generator_default_production_preset_python/README.md @@ -100,11 +100,12 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter.- [Ruff](https://github.com/charliermarsh/ruff): An extremely fast Python linter. - +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. +- [Ruff](https://github.com/charliermarsh/ruff): An extremely fast Python linter. - [mypy](https://mypy-lang.org/): Static type checker. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. - - [pre-commit](https://pre-commit.com/): A framework for managing and maintaining multi-language pre-commit hooks, to enable pre-commit you need to run `pre-commit install` in the root of the repository. This will install the pre-commit hooks and run them against modified files when committing. If any of the hooks fail, the commit will be aborted. To run the hooks on all files, use `pre-commit run --all-files`. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +- [pre-commit](https://pre-commit.com/): A framework for managing and maintaining multi-language pre-commit hooks, to enable pre-commit you need to run `pre-commit install` in the root of the repository. This will install the pre-commit hooks and run them against modified files when committing. If any of the hooks fail, the commit will be aborted. To run the hooks on all files, use `pre-commit run --all-files`. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_python/smart_contracts/config.py b/tests_generated/test_smart_contract_generator_default_production_preset_python/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_python/smart_contracts/config.py +++ b/tests_generated/test_smart_contract_generator_default_production_preset_python/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_python/smart_contracts/helpers/build.py b/tests_generated/test_smart_contract_generator_default_production_preset_python/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_python/smart_contracts/helpers/build.py +++ b/tests_generated/test_smart_contract_generator_default_production_preset_python/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_python/tests/conftest.py b/tests_generated/test_smart_contract_generator_default_production_preset_python/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_python/tests/conftest.py +++ b/tests_generated/test_smart_contract_generator_default_production_preset_python/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_python/tests/hello_world_test.py b/tests_generated/test_smart_contract_generator_default_production_preset_python/tests/hello_world_test.py index 55f83335..05066855 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_python/tests/hello_world_test.py +++ b/tests_generated/test_smart_contract_generator_default_production_preset_python/tests/hello_world_test.py @@ -1,34 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), - template_values={"UPDATABLE": 1, "DELETABLE": 1}, + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.algokit.toml b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.algokit.toml index 08717563..ad84a3ce 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.algokit.toml +++ b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "npm run deploy:ci" diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.copier-answers.yml b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.copier-answers.yml index 803705b1..7eaefa8b 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.copier-answers.yml +++ b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.copier-answers.yml @@ -21,5 +21,5 @@ use_pre_commit: true use_python_black: true use_python_mypy: true use_python_pip_audit: true -use_python_pytest: true +use_typescript_jest: true diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.github/workflows/checks.yaml b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.github/workflows/checks.yaml index 92be59ee..07d38c9d 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.github/workflows/checks.yaml +++ b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.github/workflows/checks.yaml @@ -55,17 +55,15 @@ jobs: # stop the build if there are Python syntax errors or undefined names poetry run ruff . + - name: Build smart contracts + run: poetry run python -m smart_contracts build + - name: Check types with mypy run: poetry run mypy - name: Run tests shell: bash - run: | - set -o pipefail - poetry run pytest --junitxml=pytest-junit.xml - - - name: Build smart contracts - run: poetry run python -m smart_contracts build + run: npm run test - name: Check output stability of the smart contracts shell: bash @@ -76,4 +74,4 @@ jobs: git diff --exit-code --minimal ./smart_contracts/artifacts || (echo "::error ::Smart contract artifacts have changed, ensure committed artifacts are up to date" && exit 1); - name: Run deployer against LocalNet - run: npm run --prefix smart_contracts deploy:ci + run: npm run deploy:ci diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.gitignore b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.gitignore +++ b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.tours/getting-started-with-your-algokit-project.tour index d7882591..09841231 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.tours/getting-started-with-your-algokit-project.tour @@ -23,9 +23,9 @@ "line": 32 }, { - "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "file": "tests/hello-world.spec.ts", + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 39 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.vscode/settings.json b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.vscode/settings.json index 50d7af1b..af8031fe 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.vscode/settings.json +++ b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/.vscode/settings.json @@ -27,7 +27,6 @@ "editor.defaultFormatter": "ms-python.black-formatter", }, "black-formatter.args": ["--config=pyproject.toml"], - "python.testing.pytestEnabled": true, "ruff.enable": true, "ruff.lint.run": "onSave", "ruff.lint.args": ["--config=pyproject.toml"], diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/README.md b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/README.md index 65f64c71..3bb7acde 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/README.md +++ b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/README.md @@ -80,7 +80,7 @@ For pull requests and pushes to `main` branch against this repository the follow - Code formatting is checked using [Black](https://github.com/psf/black) - Linting is checked using [Ruff](https://github.com/charliermarsh/ruff) - Types are checked using [mypy](https://mypy-lang.org/) - - Python tests are executed using [pytest](https://docs.pytest.org/) + - Typescript tests are executed using [Jest](https://jestjs.io/) - Smart contract artifacts are built - Smart contract artifacts are checked for [output stability](https://github.com/algorandfoundation/algokit-cli/blob/main/docs/articles/output_stability.md) - Smart contract is deployed to a AlgoKit LocalNet instance @@ -101,15 +101,15 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-ts) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter.- [Ruff](https://github.com/charliermarsh/ruff): An extremely fast Python linter. - +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. +- [Ruff](https://github.com/charliermarsh/ruff): An extremely fast Python linter. - [mypy](https://mypy-lang.org/): Static type checker. -- [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. - - [pre-commit](https://pre-commit.com/): A framework for managing and maintaining multi-language pre-commit hooks, to enable pre-commit you need to run `pre-commit install` in the root of the repository. This will install the pre-commit hooks and run them against modified files when committing. If any of the hooks fail, the commit will be aborted. To run the hooks on all files, use `pre-commit run --all-files`. -- [npm](https://www.npmjs.com/): Node.js package manager -- [TypeScript](https://www.typescriptlang.org/): Strongly typed programming language that builds on JavaScript -- [ts-node-dev](https://github.com/wclr/ts-node-dev): TypeScript development execution environment +- [pre-commit](https://pre-commit.com/): A framework for managing and maintaining multi-language pre-commit hooks, to enable pre-commit you need to run `pre-commit install` in the root of the repository. This will install the pre-commit hooks and run them against modified files when committing. If any of the hooks fail, the commit will be aborted. To run the hooks on all files, use `pre-commit run --all-files`. +- [npm](https://www.npmjs.com/): Node.js package manager. +- [TypeScript](https://www.typescriptlang.org/): Strongly typed programming language that builds on JavaScript. +- [ts-node-dev](https://github.com/wclr/ts-node-dev): TypeScript development execution environment. +- [Jest](https://jestjs.io/): Automated testing. It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. - diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/jest.config.ts b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/jest.config.ts new file mode 100644 index 00000000..381e1e05 --- /dev/null +++ b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/jest.config.ts @@ -0,0 +1,16 @@ +/* + * For a detailed explanation regarding each configuration property and type check, visit: + * https://jestjs.io/docs/configuration + */ +import type { Config } from 'jest' + +const config: Config = { + preset: 'ts-jest', + verbose: true, + transform: { + '^.+\\.tsx?$': 'ts-jest', + }, + testPathIgnorePatterns: ['node_modules', '.venv', 'coverage'], + testTimeout: 10000, +} +export default config diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/package.json b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/package.json index 4a3ecaea..4afc3fb0 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/package.json +++ b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/package.json @@ -6,6 +6,7 @@ "scripts": { "deploy": "ts-node-dev --transpile-only --watch .env -r dotenv/config smart_contracts/index.ts", "deploy:ci": "ts-node --transpile-only -r dotenv/config smart_contracts/index.ts", + "test": "jest --coverage", "format": "prettier --write ." }, "engines": { @@ -16,8 +17,10 @@ "algosdk": "^2.5.0" }, "devDependencies": { + "@types/jest": "^29.5.11", "dotenv": "^16.0.3", "prettier": "^2.8.4", + "ts-jest": "^29.1.1", "ts-node-dev": "^2.0.0", "typescript": "^4.9.5" } diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/pyproject.toml b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/pyproject.toml index f4360472..f5d27483 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/pyproject.toml +++ b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/pyproject.toml @@ -15,8 +15,6 @@ python-dotenv = "^1.0.0" black = {extras = ["d"], version = "*"} ruff = "^0.1.6" mypy = "*" -pytest = "*" -pytest-cov = "*" pip-audit = "*" pre-commit = "*" @@ -37,9 +35,6 @@ unfixable = ["B", "RUF"] allow-star-arg-any = true suppress-none-returning = true -[tool.pytest.ini_options] -pythonpath = ["smart_contracts", "tests"] - [tool.mypy] files = "smart_contracts/" python_version = "3.10" diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/smart_contracts/config.py b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/smart_contracts/config.py +++ b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/smart_contracts/helpers/build.py b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/smart_contracts/helpers/build.py index 20d6d6d6..167ee907 100644 --- a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/smart_contracts/helpers/build.py +++ b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/tests/__init__.py b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/tests/__init__.py deleted file mode 100644 index e69de29b..00000000 diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/tests/conftest.py b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/tests/conftest.py deleted file mode 100644 index 06a89eb0..00000000 --- a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/tests/conftest.py +++ /dev/null @@ -1,25 +0,0 @@ -from pathlib import Path - -import pytest -from algokit_utils import ( - get_algod_client, - is_localnet, -) -from algosdk.v2client.algod import AlgodClient -from dotenv import load_dotenv - - -@pytest.fixture(autouse=True, scope="session") -def environment_fixture() -> None: - env_path = Path(__file__).parent.parent / ".env.localnet" - load_dotenv(env_path) - - -@pytest.fixture(scope="session") -def algod_client() -> AlgodClient: - client = get_algod_client() - - # you can remove this assertion to test on other networks, - # included here to prevent accidentally running against other networks - assert is_localnet(client) - return client diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/tests/hello-world.spec.ts b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/tests/hello-world.spec.ts new file mode 100644 index 00000000..81e62fa1 --- /dev/null +++ b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/tests/hello-world.spec.ts @@ -0,0 +1,53 @@ +import { algorandFixture } from '@algorandfoundation/algokit-utils/testing' +import { HelloWorldClient } from '../smart_contracts/artifacts/hello_world/client' +import { Account, Algodv2, Indexer } from 'algosdk' +import * as algokit from '@algorandfoundation/algokit-utils' + +describe('hello world contract', () => { + const localnet = algorandFixture() + beforeAll(() => { + algokit.Config.configure({ + debug: true, + // traceAll: true, + }) + }) + beforeEach(localnet.beforeEach) + + const deploy = async (account: Account, algod: Algodv2, indexer: Indexer) => { + const client = new HelloWorldClient( + { + resolveBy: 'creatorAndName', + findExistingUsing: indexer, + sender: account, + creatorAddress: account.addr, + }, + algod, + ) + await client.deploy({ + allowDelete: true, + allowUpdate: true, + onSchemaBreak: 'replace', + onUpdate: 'update', + }) + return { client } + } + + test('says hello', async () => { + const { algod, indexer, testAccount } = localnet.context + const { client } = await deploy(testAccount, algod, indexer) + + const result = await client.hello({ name: 'World' }) + + expect(result.return).toBe('Hello, World') + }) + + test('simulate says hello with correct budget consumed', async () => { + const { algod, indexer, testAccount } = localnet.context + const { client } = await deploy(testAccount, algod, indexer) + const result = await client.compose().hello({ name: 'World' }).hello({ name: 'Jane' }).simulate() + + expect(result.methodResults[0].returnValue).toBe('Hello, World') + expect(result.methodResults[1].returnValue).toBe('Hello, Jane') + expect(result.simulateResponse.txnGroups[0].appBudgetConsumed).toBeLessThan(100) + }) +}) diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/tests/hello_world_test.py b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/tests/hello_world_test.py deleted file mode 100644 index 55f83335..00000000 --- a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/tests/hello_world_test.py +++ /dev/null @@ -1,34 +0,0 @@ -import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) -from algosdk.v2client.algod import AlgodClient - -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) - - -@pytest.fixture(scope="session") -def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( - algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), - template_values={"UPDATABLE": 1, "DELETABLE": 1}, - ) - client.create() - return client - - -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") - - assert result.return_value == "Hello, World" diff --git a/tests_generated/test_smart_contract_generator_default_production_preset_typescript/tsconfig.json b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/tsconfig.json new file mode 100644 index 00000000..7c762042 --- /dev/null +++ b/tests_generated/test_smart_contract_generator_default_production_preset_typescript/tsconfig.json @@ -0,0 +1,24 @@ +{ + "compilerOptions": { + "target": "ES2020", + "declaration": true, + "declarationMap": true, + "sourceMap": true, + "strict": true, + "noImplicitReturns": true, + "noFallthroughCasesInSwitch": true, + "esModuleInterop": true, + "experimentalDecorators": true, + "emitDecoratorMetadata": true, + "skipLibCheck": true, + "forceConsistentCasingInFileNames": true, + "allowJs": false, + "allowSyntheticDefaultImports": true, + "moduleResolution": "Node", + "resolveJsonModule": true, + "isolatedModules": true, + "noEmit": true + }, + "include": ["src/**/*.ts"], + "exclude": ["node_modules", "dist", "coverage"] +} diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_python/.algokit.toml b/tests_generated/test_smart_contract_generator_default_starter_preset_python/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_python/.algokit.toml +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_python/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_python/.gitignore b/tests_generated/test_smart_contract_generator_default_starter_preset_python/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_python/.gitignore +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_python/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_python/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_smart_contract_generator_default_starter_preset_python/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_python/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_python/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_python/README.md b/tests_generated/test_smart_contract_generator_default_starter_preset_python/README.md index 474a9a93..6699591b 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_python/README.md +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_python/README.md @@ -52,8 +52,9 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_python/smart_contracts/config.py b/tests_generated/test_smart_contract_generator_default_starter_preset_python/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_python/smart_contracts/config.py +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_python/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_python/smart_contracts/helpers/build.py b/tests_generated/test_smart_contract_generator_default_starter_preset_python/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_python/smart_contracts/helpers/build.py +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_python/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_python/tests/conftest.py b/tests_generated/test_smart_contract_generator_default_starter_preset_python/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_python/tests/conftest.py +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_python/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_python/tests/hello_world_test.py b/tests_generated/test_smart_contract_generator_default_starter_preset_python/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_python/tests/hello_world_test.py +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_python/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.algokit.toml b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.algokit.toml index 08717563..ad84a3ce 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.algokit.toml +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "npm run deploy:ci" diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.copier-answers.yml b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.copier-answers.yml index 11d110d1..ec22af28 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.copier-answers.yml +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.copier-answers.yml @@ -15,5 +15,5 @@ indexer_token: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa preset_name: starter project_name: test_smart_contract_generator_default_starter_preset_typescript use_python_black: true -use_python_pytest: true +use_typescript_jest: true diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.gitignore b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.gitignore +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.tours/getting-started-with-your-algokit-project.tour index d7882591..09841231 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.tours/getting-started-with-your-algokit-project.tour @@ -23,9 +23,9 @@ "line": 32 }, { - "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "file": "tests/hello-world.spec.ts", + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 39 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.vscode/settings.json b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.vscode/settings.json index 64ef1305..9f03b8da 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.vscode/settings.json +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/.vscode/settings.json @@ -27,7 +27,6 @@ "editor.defaultFormatter": "ms-python.black-formatter", }, "black-formatter.args": ["--config=pyproject.toml"], - "python.testing.pytestEnabled": true, // On Windows, if execution policy is set to Signed (default) then it won't be able to activate the venv // so instead let's set it to RemoteSigned for VS Code terminal diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/README.md b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/README.md index 1522ec35..773fe2dd 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/README.md +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/README.md @@ -53,12 +53,12 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-ts) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. -- [pytest](https://docs.pytest.org/): Automated testing. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -- [npm](https://www.npmjs.com/): Node.js package manager -- [TypeScript](https://www.typescriptlang.org/): Strongly typed programming language that builds on JavaScript -- [ts-node-dev](https://github.com/wclr/ts-node-dev): TypeScript development execution environment +- [npm](https://www.npmjs.com/): Node.js package manager. +- [TypeScript](https://www.typescriptlang.org/): Strongly typed programming language that builds on JavaScript. +- [ts-node-dev](https://github.com/wclr/ts-node-dev): TypeScript development execution environment. +- [Jest](https://jestjs.io/): Automated testing. It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. - diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/jest.config.ts b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/jest.config.ts new file mode 100644 index 00000000..381e1e05 --- /dev/null +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/jest.config.ts @@ -0,0 +1,16 @@ +/* + * For a detailed explanation regarding each configuration property and type check, visit: + * https://jestjs.io/docs/configuration + */ +import type { Config } from 'jest' + +const config: Config = { + preset: 'ts-jest', + verbose: true, + transform: { + '^.+\\.tsx?$': 'ts-jest', + }, + testPathIgnorePatterns: ['node_modules', '.venv', 'coverage'], + testTimeout: 10000, +} +export default config diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/package.json b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/package.json index 4a3ecaea..4afc3fb0 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/package.json +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/package.json @@ -6,6 +6,7 @@ "scripts": { "deploy": "ts-node-dev --transpile-only --watch .env -r dotenv/config smart_contracts/index.ts", "deploy:ci": "ts-node --transpile-only -r dotenv/config smart_contracts/index.ts", + "test": "jest --coverage", "format": "prettier --write ." }, "engines": { @@ -16,8 +17,10 @@ "algosdk": "^2.5.0" }, "devDependencies": { + "@types/jest": "^29.5.11", "dotenv": "^16.0.3", "prettier": "^2.8.4", + "ts-jest": "^29.1.1", "ts-node-dev": "^2.0.0", "typescript": "^4.9.5" } diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/pyproject.toml b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/pyproject.toml index 94b147c9..75ed874c 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/pyproject.toml +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/pyproject.toml @@ -13,14 +13,9 @@ python-dotenv = "^1.0.0" [tool.poetry.group.dev.dependencies] black = {extras = ["d"], version = "*"} -pytest = "*" -pytest-cov = "*" pip-audit = "*" [build-system] requires = ["poetry-core"] build-backend = "poetry.core.masonry.api" - -[tool.pytest.ini_options] -pythonpath = ["smart_contracts", "tests"] diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/smart_contracts/config.py b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/smart_contracts/config.py +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/smart_contracts/helpers/build.py b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/smart_contracts/helpers/build.py index 20d6d6d6..167ee907 100644 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/smart_contracts/helpers/build.py +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/tests/__init__.py b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/tests/__init__.py deleted file mode 100644 index e69de29b..00000000 diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/tests/conftest.py b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/tests/conftest.py deleted file mode 100644 index 06a89eb0..00000000 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/tests/conftest.py +++ /dev/null @@ -1,25 +0,0 @@ -from pathlib import Path - -import pytest -from algokit_utils import ( - get_algod_client, - is_localnet, -) -from algosdk.v2client.algod import AlgodClient -from dotenv import load_dotenv - - -@pytest.fixture(autouse=True, scope="session") -def environment_fixture() -> None: - env_path = Path(__file__).parent.parent / ".env.localnet" - load_dotenv(env_path) - - -@pytest.fixture(scope="session") -def algod_client() -> AlgodClient: - client = get_algod_client() - - # you can remove this assertion to test on other networks, - # included here to prevent accidentally running against other networks - assert is_localnet(client) - return client diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/tests/hello-world.spec.ts b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/tests/hello-world.spec.ts new file mode 100644 index 00000000..81e62fa1 --- /dev/null +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/tests/hello-world.spec.ts @@ -0,0 +1,53 @@ +import { algorandFixture } from '@algorandfoundation/algokit-utils/testing' +import { HelloWorldClient } from '../smart_contracts/artifacts/hello_world/client' +import { Account, Algodv2, Indexer } from 'algosdk' +import * as algokit from '@algorandfoundation/algokit-utils' + +describe('hello world contract', () => { + const localnet = algorandFixture() + beforeAll(() => { + algokit.Config.configure({ + debug: true, + // traceAll: true, + }) + }) + beforeEach(localnet.beforeEach) + + const deploy = async (account: Account, algod: Algodv2, indexer: Indexer) => { + const client = new HelloWorldClient( + { + resolveBy: 'creatorAndName', + findExistingUsing: indexer, + sender: account, + creatorAddress: account.addr, + }, + algod, + ) + await client.deploy({ + allowDelete: true, + allowUpdate: true, + onSchemaBreak: 'replace', + onUpdate: 'update', + }) + return { client } + } + + test('says hello', async () => { + const { algod, indexer, testAccount } = localnet.context + const { client } = await deploy(testAccount, algod, indexer) + + const result = await client.hello({ name: 'World' }) + + expect(result.return).toBe('Hello, World') + }) + + test('simulate says hello with correct budget consumed', async () => { + const { algod, indexer, testAccount } = localnet.context + const { client } = await deploy(testAccount, algod, indexer) + const result = await client.compose().hello({ name: 'World' }).hello({ name: 'Jane' }).simulate() + + expect(result.methodResults[0].returnValue).toBe('Hello, World') + expect(result.methodResults[1].returnValue).toBe('Hello, Jane') + expect(result.simulateResponse.txnGroups[0].appBudgetConsumed).toBeLessThan(100) + }) +}) diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/tests/hello_world_test.py b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/tests/hello_world_test.py deleted file mode 100644 index 50fd3324..00000000 --- a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/tests/hello_world_test.py +++ /dev/null @@ -1,33 +0,0 @@ -import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) -from algosdk.v2client.algod import AlgodClient - -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) - - -@pytest.fixture(scope="session") -def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( - algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), - ) - client.create() - return client - - -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") - - assert result.return_value == "Hello, World" diff --git a/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/tsconfig.json b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/tsconfig.json new file mode 100644 index 00000000..7c762042 --- /dev/null +++ b/tests_generated/test_smart_contract_generator_default_starter_preset_typescript/tsconfig.json @@ -0,0 +1,24 @@ +{ + "compilerOptions": { + "target": "ES2020", + "declaration": true, + "declarationMap": true, + "sourceMap": true, + "strict": true, + "noImplicitReturns": true, + "noFallthroughCasesInSwitch": true, + "esModuleInterop": true, + "experimentalDecorators": true, + "emitDecoratorMetadata": true, + "skipLibCheck": true, + "forceConsistentCasingInFileNames": true, + "allowJs": false, + "allowSyntheticDefaultImports": true, + "moduleResolution": "Node", + "resolveJsonModule": true, + "isolatedModules": true, + "noEmit": true + }, + "include": ["src/**/*.ts"], + "exclude": ["node_modules", "dist", "coverage"] +} diff --git a/tests_generated/test_use_github_actions-False/.algokit.toml b/tests_generated/test_use_github_actions-False/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_use_github_actions-False/.algokit.toml +++ b/tests_generated/test_use_github_actions-False/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_use_github_actions-False/.gitignore b/tests_generated/test_use_github_actions-False/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_use_github_actions-False/.gitignore +++ b/tests_generated/test_use_github_actions-False/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_use_github_actions-False/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_use_github_actions-False/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_use_github_actions-False/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_use_github_actions-False/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_use_github_actions-False/README.md b/tests_generated/test_use_github_actions-False/README.md index 24da688b..25c13fe3 100644 --- a/tests_generated/test_use_github_actions-False/README.md +++ b/tests_generated/test_use_github_actions-False/README.md @@ -52,8 +52,9 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_use_github_actions-False/smart_contracts/config.py b/tests_generated/test_use_github_actions-False/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_use_github_actions-False/smart_contracts/config.py +++ b/tests_generated/test_use_github_actions-False/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_use_github_actions-False/smart_contracts/helpers/build.py b/tests_generated/test_use_github_actions-False/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_use_github_actions-False/smart_contracts/helpers/build.py +++ b/tests_generated/test_use_github_actions-False/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_use_github_actions-False/tests/conftest.py b/tests_generated/test_use_github_actions-False/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_use_github_actions-False/tests/conftest.py +++ b/tests_generated/test_use_github_actions-False/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_use_github_actions-False/tests/hello_world_test.py b/tests_generated/test_use_github_actions-False/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_use_github_actions-False/tests/hello_world_test.py +++ b/tests_generated/test_use_github_actions-False/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_use_github_actions-True/.algokit.toml b/tests_generated/test_use_github_actions-True/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_use_github_actions-True/.algokit.toml +++ b/tests_generated/test_use_github_actions-True/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_use_github_actions-True/.github/workflows/checks.yaml b/tests_generated/test_use_github_actions-True/.github/workflows/checks.yaml index a5508d3c..56499b2b 100644 --- a/tests_generated/test_use_github_actions-True/.github/workflows/checks.yaml +++ b/tests_generated/test_use_github_actions-True/.github/workflows/checks.yaml @@ -50,15 +50,15 @@ jobs: # stop the build if there are files that don't meet formatting requirements poetry run black --check . + - name: Build smart contracts + run: poetry run python -m smart_contracts build + - name: Run tests shell: bash run: | set -o pipefail poetry run pytest --junitxml=pytest-junit.xml - - name: Build smart contracts - run: poetry run python -m smart_contracts build - - name: Check output stability of the smart contracts shell: bash run: | diff --git a/tests_generated/test_use_github_actions-True/.gitignore b/tests_generated/test_use_github_actions-True/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_use_github_actions-True/.gitignore +++ b/tests_generated/test_use_github_actions-True/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_use_github_actions-True/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_use_github_actions-True/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_use_github_actions-True/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_use_github_actions-True/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_use_github_actions-True/README.md b/tests_generated/test_use_github_actions-True/README.md index f4073c5d..a6253cfc 100644 --- a/tests_generated/test_use_github_actions-True/README.md +++ b/tests_generated/test_use_github_actions-True/README.md @@ -98,8 +98,9 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_use_github_actions-True/pyproject.toml b/tests_generated/test_use_github_actions-True/pyproject.toml index 6c0e983f..c1583815 100644 --- a/tests_generated/test_use_github_actions-True/pyproject.toml +++ b/tests_generated/test_use_github_actions-True/pyproject.toml @@ -8,7 +8,7 @@ readme = "README.md" [tool.poetry.dependencies] python = "^3.10" beaker-pyteal = "^1.1.1" -algokit-utils = "^2.2.0b1" +algokit-utils = "^2.2.0" python-dotenv = "^1.0.0" [tool.poetry.group.dev.dependencies] diff --git a/tests_generated/test_use_github_actions-True/smart_contracts/config.py b/tests_generated/test_use_github_actions-True/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_use_github_actions-True/smart_contracts/config.py +++ b/tests_generated/test_use_github_actions-True/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_use_github_actions-True/smart_contracts/helpers/build.py b/tests_generated/test_use_github_actions-True/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_use_github_actions-True/smart_contracts/helpers/build.py +++ b/tests_generated/test_use_github_actions-True/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_use_github_actions-True/tests/conftest.py b/tests_generated/test_use_github_actions-True/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_use_github_actions-True/tests/conftest.py +++ b/tests_generated/test_use_github_actions-True/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_use_github_actions-True/tests/hello_world_test.py b/tests_generated/test_use_github_actions-True/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_use_github_actions-True/tests/hello_world_test.py +++ b/tests_generated/test_use_github_actions-True/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_use_python_black-False/.algokit.toml b/tests_generated/test_use_python_black-False/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_use_python_black-False/.algokit.toml +++ b/tests_generated/test_use_python_black-False/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_use_python_black-False/.gitignore b/tests_generated/test_use_python_black-False/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_use_python_black-False/.gitignore +++ b/tests_generated/test_use_python_black-False/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_use_python_black-False/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_use_python_black-False/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_use_python_black-False/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_use_python_black-False/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_use_python_black-False/README.md b/tests_generated/test_use_python_black-False/README.md index 43124c9b..e4a754ee 100644 --- a/tests_generated/test_use_python_black-False/README.md +++ b/tests_generated/test_use_python_black-False/README.md @@ -55,5 +55,5 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Poetry](https://python-poetry.org/): Python packaging and dependency management. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_use_python_black-False/smart_contracts/config.py b/tests_generated/test_use_python_black-False/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_use_python_black-False/smart_contracts/config.py +++ b/tests_generated/test_use_python_black-False/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_use_python_black-False/smart_contracts/helpers/build.py b/tests_generated/test_use_python_black-False/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_use_python_black-False/smart_contracts/helpers/build.py +++ b/tests_generated/test_use_python_black-False/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_use_python_black-False/tests/conftest.py b/tests_generated/test_use_python_black-False/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_use_python_black-False/tests/conftest.py +++ b/tests_generated/test_use_python_black-False/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_use_python_black-False/tests/hello_world_test.py b/tests_generated/test_use_python_black-False/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_use_python_black-False/tests/hello_world_test.py +++ b/tests_generated/test_use_python_black-False/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_use_python_black-True/.algokit.toml b/tests_generated/test_use_python_black-True/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_use_python_black-True/.algokit.toml +++ b/tests_generated/test_use_python_black-True/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_use_python_black-True/.gitignore b/tests_generated/test_use_python_black-True/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_use_python_black-True/.gitignore +++ b/tests_generated/test_use_python_black-True/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_use_python_black-True/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_use_python_black-True/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_use_python_black-True/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_use_python_black-True/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_use_python_black-True/README.md b/tests_generated/test_use_python_black-True/README.md index 1940ea84..6124ab62 100644 --- a/tests_generated/test_use_python_black-True/README.md +++ b/tests_generated/test_use_python_black-True/README.md @@ -52,8 +52,9 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_use_python_black-True/pyproject.toml b/tests_generated/test_use_python_black-True/pyproject.toml index a3bb901a..e4030222 100644 --- a/tests_generated/test_use_python_black-True/pyproject.toml +++ b/tests_generated/test_use_python_black-True/pyproject.toml @@ -8,7 +8,7 @@ readme = "README.md" [tool.poetry.dependencies] python = "^3.10" beaker-pyteal = "^1.1.1" -algokit-utils = "^2.2.0b1" +algokit-utils = "^2.2.0" python-dotenv = "^1.0.0" [tool.poetry.group.dev.dependencies] diff --git a/tests_generated/test_use_python_black-True/smart_contracts/__main__.py b/tests_generated/test_use_python_black-True/smart_contracts/__main__.py index c30e558b..331f4564 100644 --- a/tests_generated/test_use_python_black-True/smart_contracts/__main__.py +++ b/tests_generated/test_use_python_black-True/smart_contracts/__main__.py @@ -6,6 +6,7 @@ from smart_contracts.config import contracts from smart_contracts.helpers.build import build +from smart_contracts.helpers.deploy import deploy # # Uncomment the following lines to enable auto generation of AVM Debugger compliant sourceMap and simulation trace file. # # Learn more about using AlgoKit AVM Debugger to debug your TEAL source codes and inspect various kinds of Algorand transactions in atomic groups -> https://github.com/algorandfoundation/algokit-avm-vscode-debugger diff --git a/tests_generated/test_use_python_black-True/smart_contracts/config.py b/tests_generated/test_use_python_black-True/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_use_python_black-True/smart_contracts/config.py +++ b/tests_generated/test_use_python_black-True/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_use_python_black-True/smart_contracts/helpers/build.py b/tests_generated/test_use_python_black-True/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_use_python_black-True/smart_contracts/helpers/build.py +++ b/tests_generated/test_use_python_black-True/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_use_python_black-True/tests/conftest.py b/tests_generated/test_use_python_black-True/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_use_python_black-True/tests/conftest.py +++ b/tests_generated/test_use_python_black-True/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_use_python_black-True/tests/hello_world_test.py b/tests_generated/test_use_python_black-True/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_use_python_black-True/tests/hello_world_test.py +++ b/tests_generated/test_use_python_black-True/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_use_python_mypy-False/.algokit.toml b/tests_generated/test_use_python_mypy-False/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_use_python_mypy-False/.algokit.toml +++ b/tests_generated/test_use_python_mypy-False/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_use_python_mypy-False/.gitignore b/tests_generated/test_use_python_mypy-False/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_use_python_mypy-False/.gitignore +++ b/tests_generated/test_use_python_mypy-False/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_use_python_mypy-False/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_use_python_mypy-False/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_use_python_mypy-False/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_use_python_mypy-False/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_use_python_mypy-False/README.md b/tests_generated/test_use_python_mypy-False/README.md index a08a2234..27f0b9d7 100644 --- a/tests_generated/test_use_python_mypy-False/README.md +++ b/tests_generated/test_use_python_mypy-False/README.md @@ -52,8 +52,9 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_use_python_mypy-False/smart_contracts/config.py b/tests_generated/test_use_python_mypy-False/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_use_python_mypy-False/smart_contracts/config.py +++ b/tests_generated/test_use_python_mypy-False/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_use_python_mypy-False/smart_contracts/helpers/build.py b/tests_generated/test_use_python_mypy-False/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_use_python_mypy-False/smart_contracts/helpers/build.py +++ b/tests_generated/test_use_python_mypy-False/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_use_python_mypy-False/tests/conftest.py b/tests_generated/test_use_python_mypy-False/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_use_python_mypy-False/tests/conftest.py +++ b/tests_generated/test_use_python_mypy-False/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_use_python_mypy-False/tests/hello_world_test.py b/tests_generated/test_use_python_mypy-False/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_use_python_mypy-False/tests/hello_world_test.py +++ b/tests_generated/test_use_python_mypy-False/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_use_python_mypy-True/.algokit.toml b/tests_generated/test_use_python_mypy-True/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_use_python_mypy-True/.algokit.toml +++ b/tests_generated/test_use_python_mypy-True/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_use_python_mypy-True/.gitignore b/tests_generated/test_use_python_mypy-True/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_use_python_mypy-True/.gitignore +++ b/tests_generated/test_use_python_mypy-True/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_use_python_mypy-True/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_use_python_mypy-True/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_use_python_mypy-True/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_use_python_mypy-True/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_use_python_mypy-True/README.md b/tests_generated/test_use_python_mypy-True/README.md index 905c64fc..36f5ef04 100644 --- a/tests_generated/test_use_python_mypy-True/README.md +++ b/tests_generated/test_use_python_mypy-True/README.md @@ -52,9 +52,10 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [mypy](https://mypy-lang.org/): Static type checker. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_use_python_mypy-True/pyproject.toml b/tests_generated/test_use_python_mypy-True/pyproject.toml index 8b876d83..32913534 100644 --- a/tests_generated/test_use_python_mypy-True/pyproject.toml +++ b/tests_generated/test_use_python_mypy-True/pyproject.toml @@ -8,7 +8,7 @@ readme = "README.md" [tool.poetry.dependencies] python = "^3.10" beaker-pyteal = "^1.1.1" -algokit-utils = "^2.2.0b1" +algokit-utils = "^2.2.0" python-dotenv = "^1.0.0" [tool.poetry.group.dev.dependencies] diff --git a/tests_generated/test_use_python_mypy-True/smart_contracts/config.py b/tests_generated/test_use_python_mypy-True/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_use_python_mypy-True/smart_contracts/config.py +++ b/tests_generated/test_use_python_mypy-True/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_use_python_mypy-True/smart_contracts/helpers/build.py b/tests_generated/test_use_python_mypy-True/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_use_python_mypy-True/smart_contracts/helpers/build.py +++ b/tests_generated/test_use_python_mypy-True/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_use_python_mypy-True/tests/conftest.py b/tests_generated/test_use_python_mypy-True/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_use_python_mypy-True/tests/conftest.py +++ b/tests_generated/test_use_python_mypy-True/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_use_python_mypy-True/tests/hello_world_test.py b/tests_generated/test_use_python_mypy-True/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_use_python_mypy-True/tests/hello_world_test.py +++ b/tests_generated/test_use_python_mypy-True/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100 diff --git a/tests_generated/test_use_python_pytest-False/.algokit.toml b/tests_generated/test_use_python_pytest-False/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_use_python_pytest-False/.algokit.toml +++ b/tests_generated/test_use_python_pytest-False/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_use_python_pytest-False/.gitignore b/tests_generated/test_use_python_pytest-False/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_use_python_pytest-False/.gitignore +++ b/tests_generated/test_use_python_pytest-False/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_use_python_pytest-False/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_use_python_pytest-False/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_use_python_pytest-False/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_use_python_pytest-False/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_use_python_pytest-False/README.md b/tests_generated/test_use_python_pytest-False/README.md index 19330d72..8e615797 100644 --- a/tests_generated/test_use_python_pytest-False/README.md +++ b/tests_generated/test_use_python_pytest-False/README.md @@ -52,7 +52,8 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_use_python_pytest-False/smart_contracts/config.py b/tests_generated/test_use_python_pytest-False/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_use_python_pytest-False/smart_contracts/config.py +++ b/tests_generated/test_use_python_pytest-False/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_use_python_pytest-False/smart_contracts/helpers/build.py b/tests_generated/test_use_python_pytest-False/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_use_python_pytest-False/smart_contracts/helpers/build.py +++ b/tests_generated/test_use_python_pytest-False/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_use_python_pytest-True/.algokit.toml b/tests_generated/test_use_python_pytest-True/.algokit.toml index 77dfd4bf..4a26acfd 100644 --- a/tests_generated/test_use_python_pytest-True/.algokit.toml +++ b/tests_generated/test_use_python_pytest-True/.algokit.toml @@ -1,5 +1,5 @@ [algokit] -min_version = "v1.7.3" +min_version = "v1.8.0" [deploy] command = "poetry run python -m smart_contracts deploy" diff --git a/tests_generated/test_use_python_pytest-True/.gitignore b/tests_generated/test_use_python_pytest-True/.gitignore index 832924c3..4a926bbb 100644 --- a/tests_generated/test_use_python_pytest-True/.gitignore +++ b/tests_generated/test_use_python_pytest-True/.gitignore @@ -50,6 +50,7 @@ coverage.xml .hypothesis/ .pytest_cache/ cover/ +coverage/ # Translations *.mo @@ -172,3 +173,6 @@ cython_debug/ # NPM node_modules + +# AlgoKit +debug_traces/ diff --git a/tests_generated/test_use_python_pytest-True/.tours/getting-started-with-your-algokit-project.tour b/tests_generated/test_use_python_pytest-True/.tours/getting-started-with-your-algokit-project.tour index 205994b6..41d7824a 100644 --- a/tests_generated/test_use_python_pytest-True/.tours/getting-started-with-your-algokit-project.tour +++ b/tests_generated/test_use_python_pytest-True/.tours/getting-started-with-your-algokit-project.tour @@ -24,8 +24,8 @@ }, { "file": "tests/hello_world_test.py", - "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit application client.", - "line": 21 + "description": "If you opted to include unit tests, the default tests provided demonstrate an example of mocking, setting up fixtures, and testing smart contract calls on an AlgoKit typed client.", + "line": 36 }, { "file": ".env.localnet.template", diff --git a/tests_generated/test_use_python_pytest-True/README.md b/tests_generated/test_use_python_pytest-True/README.md index b49c2119..aa2880f1 100644 --- a/tests_generated/test_use_python_pytest-True/README.md +++ b/tests_generated/test_use_python_pytest-True/README.md @@ -52,8 +52,9 @@ This project makes use of Python to build Algorand smart contracts. The followin - [Beaker](https://github.com/algorand-devrel/beaker) - Smart contract development framework for PyTeal; [docs](https://beaker.algo.xyz), [examples](https://github.com/algorand-devrel/beaker/tree/master/examples) - [PyTEAL](https://github.com/algorand/pyteal) - Python language binding for Algorand smart contracts; [docs](https://pyteal.readthedocs.io/en/stable/) - [AlgoKit Utils](https://github.com/algorandfoundation/algokit-utils-py) - A set of core Algorand utilities that make it easier to build solutions on Algorand. -- [Poetry](https://python-poetry.org/): Python packaging and dependency management.- [Black](https://github.com/psf/black): A Python code formatter. +- [Poetry](https://python-poetry.org/): Python packaging and dependency management. +- [Black](https://github.com/psf/black): A Python code formatter. - [pytest](https://docs.pytest.org/): Automated testing. - [pip-audit](https://pypi.org/project/pip-audit/): Tool for scanning Python environments for packages with known vulnerabilities. -It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. +It has also been configured to have a productive dev experience out of the box in [VS Code](https://code.visualstudio.com/), see the [.vscode](./.vscode) folder. diff --git a/tests_generated/test_use_python_pytest-True/pyproject.toml b/tests_generated/test_use_python_pytest-True/pyproject.toml index 309fe418..3b975ba1 100644 --- a/tests_generated/test_use_python_pytest-True/pyproject.toml +++ b/tests_generated/test_use_python_pytest-True/pyproject.toml @@ -8,7 +8,7 @@ readme = "README.md" [tool.poetry.dependencies] python = "^3.10" beaker-pyteal = "^1.1.1" -algokit-utils = "^2.2.0b1" +algokit-utils = "^2.2.0" python-dotenv = "^1.0.0" [tool.poetry.group.dev.dependencies] diff --git a/tests_generated/test_use_python_pytest-True/smart_contracts/config.py b/tests_generated/test_use_python_pytest-True/smart_contracts/config.py index 8cefdd67..3a1d85fe 100644 --- a/tests_generated/test_use_python_pytest-True/smart_contracts/config.py +++ b/tests_generated/test_use_python_pytest-True/smart_contracts/config.py @@ -59,6 +59,6 @@ def has_contract_file(directory: Path) -> bool: ## Comment the above and uncomment the below and define contracts manually if you want to build and specify them ## manually otherwise the above code will always include all contracts under contract.py file for any subdirectory -## in the smart_contracts directory. Optionally it will also grab the deploy function from deploy_config.py if it exists. +## in the smart_contracts directory. Optionally it will grab the deploy function from deploy_config.py if it exists. # contracts = [] diff --git a/tests_generated/test_use_python_pytest-True/smart_contracts/helpers/build.py b/tests_generated/test_use_python_pytest-True/smart_contracts/helpers/build.py index 201e5d66..753727bf 100644 --- a/tests_generated/test_use_python_pytest-True/smart_contracts/helpers/build.py +++ b/tests_generated/test_use_python_pytest-True/smart_contracts/helpers/build.py @@ -34,7 +34,7 @@ def build(output_dir: Path, app: beaker.Application) -> Path: if result.returncode: if "No such command" in result.stdout: raise Exception( - "Could not generate typed client, requires AlgoKit 1.1 or " + "Could not generate typed client, requires AlgoKit 1.8.0 or " "later. Please update AlgoKit" ) else: diff --git a/tests_generated/test_use_python_pytest-True/tests/conftest.py b/tests_generated/test_use_python_pytest-True/tests/conftest.py index 06a89eb0..b0622e78 100644 --- a/tests_generated/test_use_python_pytest-True/tests/conftest.py +++ b/tests_generated/test_use_python_pytest-True/tests/conftest.py @@ -3,9 +3,11 @@ import pytest from algokit_utils import ( get_algod_client, + get_indexer_client, is_localnet, ) from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient from dotenv import load_dotenv @@ -23,3 +25,8 @@ def algod_client() -> AlgodClient: # included here to prevent accidentally running against other networks assert is_localnet(client) return client + + +@pytest.fixture(scope="session") +def indexer_client() -> IndexerClient: + return get_indexer_client() diff --git a/tests_generated/test_use_python_pytest-True/tests/hello_world_test.py b/tests_generated/test_use_python_pytest-True/tests/hello_world_test.py index 50fd3324..05066855 100644 --- a/tests_generated/test_use_python_pytest-True/tests/hello_world_test.py +++ b/tests_generated/test_use_python_pytest-True/tests/hello_world_test.py @@ -1,33 +1,50 @@ +import algokit_utils import pytest -from algokit_utils import ( - ApplicationClient, - ApplicationSpecification, - get_localnet_default_account, -) +from algokit_utils import get_localnet_default_account +from algokit_utils.config import config from algosdk.v2client.algod import AlgodClient +from algosdk.v2client.indexer import IndexerClient -from smart_contracts.hello_world import contract as hello_world_contract - - -@pytest.fixture(scope="session") -def hello_world_app_spec(algod_client: AlgodClient) -> ApplicationSpecification: - return hello_world_contract.app.build(algod_client) +from smart_contracts.artifacts.hello_world.client import HelloWorldClient @pytest.fixture(scope="session") def hello_world_client( - algod_client: AlgodClient, hello_world_app_spec: ApplicationSpecification -) -> ApplicationClient: - client = ApplicationClient( + algod_client: AlgodClient, indexer_client: IndexerClient +) -> HelloWorldClient: + config.configure( + debug=True, + # trace_all=True, + ) + + client = HelloWorldClient( algod_client, - app_spec=hello_world_app_spec, - signer=get_localnet_default_account(algod_client), + creator=get_localnet_default_account(algod_client), + indexer_client=indexer_client, + ) + + client.deploy( + on_schema_break=algokit_utils.OnSchemaBreak.ReplaceApp, + on_update=algokit_utils.OnUpdate.UpdateApp, + allow_delete=True, + allow_update=True, ) - client.create() return client -def test_says_hello(hello_world_client: ApplicationClient) -> None: - result = hello_world_client.call(hello_world_contract.hello, name="World") +def test_says_hello(hello_world_client: HelloWorldClient) -> None: + result = hello_world_client.hello(name="World") assert result.return_value == "Hello, World" + + +def test_simulate_says_hello_with_correct_budget_consumed( + hello_world_client: HelloWorldClient, algod_client: AlgodClient +) -> None: + result = ( + hello_world_client.compose().hello(name="World").hello(name="Jane").simulate() + ) + + assert result.abi_results[0].return_value == "Hello, World" + assert result.abi_results[1].return_value == "Hello, Jane" + assert result.simulate_response["txn-groups"][0]["app-budget-consumed"] < 100