Releases: demergent-labs/azle
0.15.0
This release focuses on updating many of Azle's under-the-hood dependencies, most notably the underlying JS engine (Boa) and stable structures.
Breaking changes
StableBTreeMap
.insert
no longer returns a result, instead it returns an Opt
of the inserted value's type.
What's Changed
- Fixed name collisions by @dansteren in #995
- Update dfx to 0.13.1, Rust to 1.68.2, ic-cdk-macros to 0.6.10, ic-cdk-timers to 0.1.2, Boa to latest, ic-stable-structures to 0.5.2 by @lastmjs in #994
- Prefixed user defined functions by @dansteren in #996
- Reorganized JS Files by @dansteren in #969
- Documentation 0.15.0 by @lastmjs in #1003
Full Changelog: 0.14.0...0.15.0
0.14.0
The main focus of this release is further syntax changes that we hope improve the developer experience and solve various issues. If you run into problems while upgrading, please refer to these release notes and The Azle Book carefully.
Breaking Changes
Camel case
Generally speaking all Azle APIs have been converted from snake case to camel case. Methods or types from cross-canister calls, like from the management canister, have not changed.
The following are just a few examples.
management_canister
to managementCanister
:
Old
import { blob, match, $update } from 'azle';
import { management_canister } from 'azle/canisters/management';
$update;
export async function getRandomnessDirectly(): Promise<blob> {
const randomnessResult = await management_canister.raw_rand().call();
return match(randomnessResult, {
Ok: (randomness) => randomness,
Err: () => Uint8Array.from([])
});
}
New
import { blob, match, $update } from 'azle';
import { managementCanister } from 'azle/canisters/management';
$update;
export async function getRandomnessDirectly(): Promise<blob> {
const randomnessResult = await managementCanister.raw_rand().call();
return match(randomnessResult, {
Ok: (randomness) => randomness,
Err: () => Uint8Array.from([])
});
}
ic.canister_balance
to ic.canisterBalance
:
Old
import { ic, nat64, $query } from 'azle';
$query;
export function canisterBalance(): nat64 {
return ic.canister_balance();
}
New
import { ic, nat64, $query } from 'azle';
$query;
export function canisterBalance(): nat64 {
return ic.canisterBalance();
}
Alias
Type aliases must now explicitly use the Alias
type:
Old
import { nat64, $query } from 'azle';
type Tokens = nat64;
$query;
export numTokens(): Tokens {
return 100n;
}
New
import { Alias, nat64, $query } from 'azle';
type Tokens = Alias<nat64>;
$query;
export numTokens(): Tokens {
return 100n;
}
ExternalCanister, @method, and CanisterResult
The ExternalCanister
class has been changed to Service
, the @method
decorator has been changed to either @serviceQuery
for query methods or @serviceUpdate
for update methods, and CanisterResult
has been changed to CallResult
The service Candid type is now fully implemented:
Old
import { CanisterResult, ExternalCanister, method } from 'azle';
class SomeExternalCanister extends ExternalCanister {
@method
query1: () => CanisterResult<boolean>;
@method
update1: () => CanisterResult<string>;
}
New
import { CallResult, Service, serviceQuery, serviceUpdate } from 'azle';
class SomeService extends Service {
@serviceQuery
query1: () => CallResult<boolean>;
@serviceUpdate
update1: () => CallResult<string>;
}
[] -> Vec
For array types, the []
TypeScript array syntax can no longer be used. You must now use the Vec
type:
Old
import { $query } from 'azle';
$query;
export function listOfStringOne(param: string[]): string[] {
return param;
}
$query;
export function listOfStringTwo(params: string[][]): string[][] {
return params;
}
New
import { $query, Vec } from 'azle';
$query;
export function listOfStringOne(param: Vec<string>): Vec<string> {
return param;
}
$query;
export function listOfStringTwo(params: Vec<Vec<string>>): Vec<Vec<string>> {
return params;
}
void for system methods
The void
type must be explicitly used as the return type on all system methods:
Old
import { $init, $post_upgrade, $pre_upgrade } from 'azle';
$init;
export function init() {
console.log('runs on first canister install');
}
$pre_upgrade;
export function preUpgrade() {
console.log('runs before canister upgrade');
}
$post_upgrade;
export function postUpgrade() {
console.log('runs after canister upgrade');
}
New
import { $init, $postUpgrade, $preUpgrade } from 'azle';
$init;
export function init(): void {
console.log('runs on first canister install');
}
$preUpgrade;
export function preUpgrade(): void {
console.log('runs before canister upgrade');
}
$postUpgrade;
export function postUpgrade(): void {
console.log('runs after canister upgrade');
}
New Features
We have implemented some powerful new features with this release:
Generics
Before it was not possible to use generics with Variants, Records, or anywhere else. Generics are now supported in various locations, allowing you to do things like generics Result
s:
import { blob, Result } from 'azle';
import { managementCanister } from 'azle/canisters/management';
async function getRandomness(): Promise<Result<blob, string>> {
return await managementCanister.raw_rand().call();
}
Guard functions
You now have the ability to protect canister methods with guard functions. The guard function will be executed before the annotated function. If the guard function returns an error, the annotated function will not proceed.
Example
import { GuardResult, ic, $query } from 'azle';
function simpleWhitelist(): GuardResult {
if (ic.caller().toText() === 'aaaaa-aa') {
return { Ok: null };
} else {
return { Err: 'Access denied' };
}
}
$query({ guard: simpleWhitelist });
export function myCanisterMethod(): boolean {
return true;
}
See the guard functions example for more information.
text
is now an alias to Candid string
If you so desire, you can use the Azle text
type as an alias to Candid string
:
import { $query, test } from 'azle';
$query;
export textQueryMethod(): text {
return 'This works great';
}
number
is now an alias to Candid float64
If you so desire, you can use the TypeScript number
type as an alias to Candid float64
. We generally don't recommend doing this, it is designed to allow beginners to quickly get started without having to learn about the Candid number types:
import { $query } from 'azle';
$query;
export numberQueryMethod(): number {
return 1111;
}
match
We've introduced a powerful new match
function that attempts to emulate the behavior of Rust's match
function. Combined with the new generic Result
variants, we have a more capable algebraic data type-like typing situation:
import {
ic,
InsertError,
match,
nat64,
Principal,
Record,
Result,
StableBTreeMap,
$update,
Vec
} from 'azle';
type User = Record<{
id: Principal;
createdAt: nat64;
recordingIds: Vec<Principal>;
username: string;
}>;
let users = new StableBTreeMap<Principal, User>(0, 38, 100_000);
$update;
export function createUser(username: string): Result<User, InsertError> {
const id = generateId();
const user: User = {
id,
createdAt: ic.time(),
recordingIds: [],
username
};
const result = users.insert(user.id, user);
return match(result, {
Ok: () => ({ Ok: user }),
Err: (err) => ({ Err: err })
});
}
What's Changed
- The azle book reference by @lastmjs in #915
- fix up the book a bit by @lastmjs in #916
- Changed internal parsing algorithm and type alias syntax by @dansteren in #918
- Fix a few things in The Azle Book by @lastmjs in #922
- Remove cargo test by @lastmjs in #924
- Add nested tuple example by @dansteren in #946
- initial implementation of match by @lastmjs in #947
- add real tests, remove dummy by @bdemann in #955
- Added Guard Functions by @dansteren in #945
- 948 azle apis camel case with guard function refactor by @lastmjs in #952
- 949 convert all examples to camel case by @lastmjs in #953
- Clean up funcs by @lastmjs in #960
- Fixed flakiness in function guards test by @dansteren in #965
- first stab at services by @lastmjs in #962
- Added candid syntax improvements by @dansteren in #961
- Test case converter by @bdemann in #966
- update the azle book to fix some issues with match and service and cr… by @lastmjs in #973
- Reorganized code by @dansteren in #970
- unify guard functions, imports and manual reply by @bdemann in #971
- rename CanisterResult to CallResult by @lastmjs in #975
- Generics for Variants, Result type by @lastmjs in #977
- Alias generics by @lastmjs in #978
- added generics example with tests by @LastM...
0.13.2
This release improves error handling around external canister definitions.
What's Changed
- Changed External Canister Parsing Errors by @dansteren in #910
Full Changelog: 0.13.1...0.13.2
0.13.1
0.13.0
This release has introduced a number of syntax changes that we hope improve the developer experience and solve various issues.
Breaking Changes
Query and Update methods
We have introduced the following new annotations:
$heartbeat
$init
$inspect_message
$post_upgrade
$pre_upgrade
$query
$update
These annotations replace the wrapper return types previously used to mark canister methods:
Heartbeat
Init
InspectMessage
PostUpgrade
PreUpgrade
Query
Update
Here's an example of the old vs the new syntax for query methods. The other annotations are used similarly.
Old:
import { Query } from 'azle';
export function simple_query(): Query<string> {
return `This is a query method`;
}
New:
import { $query } from 'azle';
$query;
export function simple_query(): string {
return `This is a query method`;
}
Record
Record types must now be wrapped with the Record
type, similar to how variants currently work. Inline records also need to be wrapped in the Record
type:
Old:
type User = {
id: string;
username: string;
};
New:
import { Record } from 'azle';
type User = Record<{
id: string;
username: string;
}>;
Func
The function portion of Func
types now need to be wrapped in the Query
, Update
, or Oneway
types.
Old:
type BasicFunc = Func<(param1: string) => Query<string>>;
New:
type BasicFunc = Func<Query<(param1: string) => string>>;
External canister
External canisters are now defined as classes that extend from ExternalCanister
. Each method must be marked with either the @query
or @update
decorators.
Old:
import { Canister, CanisterResult, ic, nat64, Opt } from 'azle';
type Canister2 = Canister<{
transfer(from: string, to: string, amount: nat64): CanisterResult<nat64>;
balance(id: string): CanisterResult<nat64>;
account(accountArgs: AccountArgs): CanisterResult<Opt<Account>>;
accounts(): CanisterResult<Account[]>;
trap(): CanisterResult<string>;
receive_notification(message: string): CanisterResult<void>;
}>;
let canister2 = ic.canisters.Canister2<Canister2>(
Principal.fromText('ryjl3-tyaaa-aaaaa-aaaba-cai')
);
New:
import { CanisterResult, ExternalCanister, nat64, Opt, query, update } from 'azle';
class Canister2 extends ExternalCanister {
@update
transfer: (
from: string,
to: string,
amount: nat64
) => CanisterResult<nat64>;
@query
balance: (id: string) => CanisterResult<nat64>;
@query
account: (accountArgs: AccountArgs) => CanisterResult<Opt<Account>>;
@query
accounts: () => CanisterResult<Account[]>;
@query
trap: () => CanisterResult<string>;
@update
receive_notification: (message: string) => CanisterResult<void>;
}
const canister2 = new Canister2(
Principal.fromText('ryjl3-tyaaa-aaaaa-aaaba-cai')
);
What's Changed
- Void and null by @bdemann in #877
- Changed Func Parsing by @dansteren in #897
- Fixed errors for mismatched return values by @dansteren in #896
- Changed canister method parsing to support new custom decorator annotations by @dansteren in #891
- Changed external canister parsing by @dansteren in #898
- Changed
Record
syntax by @dansteren in #901 - Custom decorators by @lastmjs in #887
- The azle book by @lastmjs in #890
Full Changelog: 0.12.0...0.13.0
0.12.0
TLDR
Cross-canister calls within timers are now supported. Randomness is now automatically seeeded after init and post upgrade, giving better randomness to Math.random and any other APIs that rely on the under-the-hood Rust random number generation. Some issues were fixed with inline types.
What's Changed
- Fixed inline types by @dansteren in #878
- Timers cross canister by @lastmjs in #879
- Seed the custom randomness by @lastmjs in #881
Full Changelog: 0.11.0...0.12.0
0.11.0
TLDR
There is no more need to manually install Rust on your machine. Azle will now install an encapsulated Rust environment inside of ~/.config/azle
per version of Azle. Composite queries are now supported for use in the local replica, and the Manual
return type was introduced.
Breaking Changes
QueryManual
andUpdateManual
have been removed. If you want to create a manual query you must now use theManual
return type- Please delete your local
.dfx
,target
, andnode_modules
directories before installing and deploying with the new version of Azle - You should add
.azle
to your.gitignore
file
What's Changed
- The azle book by @lastmjs in #857
- initial structure in place by @lastmjs in #860
- Organized all generated code into generators folder by @dansteren in #862
- Remove rust install by @lastmjs in #863
- split out example into three canisters by @bdemann in #864
- Changed Manual return types by @dansteren in #867
- Composite query by @bdemann in #845
- Improving local Rust installation by @lastmjs in #868
- fix path by @lastmjs in #874
Full Changelog: 0.10.0...0.11.0
0.10.0
If you run into issues after an upgrade:
- Ensure all versions of dfx, Rust, and Node.js are exactly as described in the README
- Completely delete the
.dfx
,target
andnode_modules
directories and deploy again - Run
rustup update
TLDR
This release is all about introducing StableBTreeMap.
What's Changed
- Added
keys
,values
, anditems
methods to StableBTreeMap by @dansteren in #850 - Added StableBTreeMaps by @dansteren in #842
- Readme updates by @lastmjs in #853
- Added snippet annotations to StableBTreeMap error messages by @dansteren in #854
- update dfx to 0.12.1 by @lastmjs in #855
Full Changelog: 0.9.0...0.10.0
0.9.0
If you run into issues after an upgrade, the safest thing to do is ensure that all versions of dfx
, rust
, and node
are exactly as described in the README. Also try completely deleting the .dfx
, target
, and node_modules
directories and then reinstalling and deploying again.
TLDR
- async/await has replaced generators for cross-canister calls
- timers API now implemented
- Major Bug in Boa JS engine has been fixed
- Increased ECMAScript support and support for async/await and promises
- Principal.selfAuthenticating now works
- Reduced compilation times
- Candid metadata and CDK info metadata
- lists of lists now generally supported
Breaking Changes
ManagementCanister
fromazle/canisters/management
has been renamed tomanagement_canister
- All generators syntax (
yield
and*
) has been replaced withawait
andasync
with_cycles
andwith_cycles128
in the cross-canister calls API have been changed tocycles
andcycles128
- To execute a cross-canister call you must now explicitly invoke
.call
, similar to.notify
- You must update to at least
rustc 1.66
, userustup update
What's Changed
- Release 0.8.0 by @lastmjs in #796
- update the rejections and ic_api examples by @lastmjs in #802
- Ic api by @lastmjs in #803
- update ledger_canister tests by @lastmjs in #805
- Pass keywords to CDK Framework and
to_token_stream
by @dansteren in #806 - Change beta ribbon color by @dansteren in #808
- Update Boa to remove critical bug and add many new ECMAScript Features including async/await and Promises by @lastmjs in #817
- Documentation by @lastmjs in #811
- Principal self authenticating by @lastmjs in #818
- Update ic-cdk to 0.6.8 with the timers feature, update other ic dependencies, add Boa conditional compilation by @lastmjs in #821
- standardize canister method names by @bdemann in #770
- Prefixed everything with
_azle_
by @dansteren in #807 - Add candid metadata using ic-wasm by @dansteren in #822
- optimize compilation times by @lastmjs in #824
- add support for promises by @bdemann in #828
- support list of lists of lists by @bdemann in #825
- Adds the new timer API by @dansteren in #829
- Implement async/await for cross-canister calls by @lastmjs in #831
Full Changelog: 0.8.0...0.9.0
0.8.0
This release updates Azle to work with dfx 0.12.0, contains a large rewrite of the Azle compiler in Rust, the creation of a CDK Framework, and includes greatly improved compiler errors for the end user developer.
What's Changed
- 634 canister method bodies by @lastmjs in #635
- experiment with removing proc_macro, generate rust code directly and … by @lastmjs in #636
- basic canister method bodies work by @lastmjs in #639
- 640 ic object by @lastmjs in #641
- 642 heartbeat by @lastmjs in #645
- Added inspect message by @dansteren in #646
- init is implemented with params by @lastmjs in #651
- 648 pre upgrade by @lastmjs in #652
- 649 post upgrade by @lastmjs in #653
- Azle compiler types by @lastmjs in #638
- implement notify_raw by @lastmjs in #656
- Stable memory by @lastmjs in #658
- Get rid of uuid in favor of hash by @bdemann in #659
- Added
Func
type aliases in new compiler by @dansteren in #660 - 654 stable storage by @lastmjs in #661
- 662 generators by @lastmjs in #663
- complex records, variants, and funcs by @bdemann in #666
- complex types and canister dependencies by @bdemann in #668
- Added support for QueryManual and UpdateManual by @dansteren in #667
- Added
reply_raw
support to new compiler by @dansteren in #672 - Finished IC object functions by @dansteren in #673
- 664 cross canister calls by @lastmjs in #671
- Added support for inline types by @bdemann in #676
- Added support for tuple types by @bdemann in #677
- Moved all getters into ts_ast dir by @dansteren in #678
- remove unnecessary code by @lastmjs in #679
- 681 pull up variant and records by @bdemann in #683
- Start separation of ACT building and .to_token_stream by @dansteren in #684
- combine all type_alias code by @bdemann in #685
- 686 create data type act nodes by @bdemann in #688
- Organized canister methods by @dansteren in #687
- arrays, tuples, and funcs updated by @bdemann in #689
- Move system canister methods into CDK AST by @dansteren in #691
- 697 create ast node traits by @bdemann in #704
- 705 create literalortypealias enum by @bdemann in #706
- 674 azle compiler refactor by @bdemann in #709
- Re-implemented the compiler in Rust by @dansteren in #712
- Added generic vm value conversion traits by @dansteren in #713
- Improved boa errors by @bdemann in #717
- Changed compiler output by @dansteren in #714
- update motoko example tests by @bdemann in #721
- Surface azle_generate errors by @dansteren in #722
- Kybra test reuse by @lastmjs in #720
- Add SourceMap for improved error reporting by @bdemann in #726
- Improve compilation error messages by @dansteren in #727
- 77 type ref errors by @bdemann in #729
- update primitive types example by @lastmjs in #731
- 732 fn decl snippets by @dansteren in #733
- 77 azle type ref errors by @bdemann in #736
- 77 all azle type errors by @bdemann in #738
- 737 azle canister decl errors by @bdemann in #739
- 740 minor unwrap purge by @bdemann in #747
- 741 expunge todos panics and unwraps by @bdemann in #745
- update simple_user_accounts by @lastmjs in #754
- Simple erc20 by @lastmjs in #755
- update counter example by @lastmjs in #757
- update principal example by @lastmjs in #758
- Optional types example by @lastmjs in #759
- update tuple_types_example by @lastmjs in #761
- Complex types example by @lastmjs in #762
- Fix one tuple by @lastmjs in #763
- change test didc installation and use to be more universal across Rus… by @lastmjs in #765
- Surface spawnSync JS errors by @dansteren in #750
- Hooked up Source maps to Fn Decl errors by @dansteren in #751
- Finish removing unwraps, todos, and panics as noted on 741 by @dansteren in #756
- Cdk updates by @bdemann in #766
- removed redundant hash set conversion by @bdemann in #767
- fix notify_raw result type by @lastmjs in #768
- Refactored cross-canister calls by @dansteren in #769
- 77 Improve Errors by @dansteren in #771
- Update README.md by @lastmjs in #772
- remove cdk_act from source code, add cdk_framework from GitHub by @lastmjs in #774
- add Result back to CdkActTryIntoVmValue by @lastmjs in #775
- Various example fixes by @lastmjs in #776
- fix cycles tests by @lastmjs in #777
- update cdk_framework, move func type CDK-specific definitions to Azle by @lastmjs in #778
- Stable storage by @lastmjs in #788
- remove array check for blob manual reply by @bdemann in #789
- stable storage example is done by @lastmjs in #791
- Improved error messages for edge-cases in cross canister calls by @dansteren in #792
Full Changelog: 0.7.0...0.8.0