Skip to content

Commit 25d4551

Browse files
authored
format comment, expect_failure, macro... (#185)
1 parent f05d2a8 commit 25d4551

31 files changed

+275
-198
lines changed

book/move-basics/testing.md

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -14,19 +14,22 @@ the bytecode and are never published.
1414
```move
1515
module book::testing;
1616
17+
#[test_only]
18+
use std::unit_test::assert_eq;
19+
1720
// The test attribute is placed before the `fun` keyword (can be both above or
1821
// right before the `fun` keyword, as in `#[test] fun my_test() { ... }`)
1922
// The name of the test in this case would be `book::testing::simple_test`.
2023
#[test]
2124
fun simple_test() {
2225
let sum = 2 + 2;
23-
assert!(sum == 4);
26+
assert_eq!(sum, 4);
2427
}
2528
2629
// The name of this test would be `book::testing::more_advanced_test`.
2730
#[test] fun more_advanced_test() {
2831
let sum = 2 + 2 + 2;
29-
assert!(sum == 4);
32+
assert_eq!(sum, 4);
3033
}
3134
```
3235

@@ -94,6 +97,9 @@ where the `#[test_only]` attribute comes in handy.
9497
```move
9598
module book::testing;
9699
100+
#[test_only]
101+
use std::unit_test::assert_eq;
102+
97103
// Public function which uses the `secret` function.
98104
public fun multiply_by_secret(x: u64): u64 {
99105
x * secret()
@@ -114,7 +120,7 @@ public fun secret_for_testing(): u64 {
114120
// In the test environment we have access to the `secret_for_testing` function.
115121
fun test_multiply_by_secret() {
116122
let expected = secret_for_testing() * 2;
117-
assert!(multiply_by_secret(2) == expected);
123+
assert_eq!(multiply_by_secret(2), expected);
118124
}
119125
```
120126

book/programmability/witness-pattern.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -96,7 +96,7 @@ public struct Balance<phantom T> has store {
9696
9797
/// Increase supply by `value` and create a new `Balance<T>` with this value.
9898
public fun increase_supply<T>(self: &mut Supply<T>, value: u64): Balance<T> {
99-
assert!(value < (18446744073709551615u64 - self.value), EOverflow);
99+
assert!(value < (std::u64::max_value!() - self.value), EOverflow);
100100
self.value = self.value + value;
101101
Balance { value }
102102
}

book/your-first-move/hello-world.md

Lines changed: 2 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -148,18 +148,7 @@ excludes comments and some identifiers (for example, for constants).
148148
To demonstrate these features, let's replace the contents of the _sources/hello_world.move_ file
149149
with the following:
150150

151-
```move
152-
/// The module `hello_world` under named address `hello_world`.
153-
/// The named address is set in the `Move.toml`.
154-
module hello_world::hello_world;
155-
156-
// Imports the `String` type from the Standard Library
157-
use std::string::String;
158-
159-
/// Returns the "Hello, World!" as a `String`.
160-
public fun hello_world(): String {
161-
b"Hello, World!".to_string()
162-
}
151+
```move file=packages/hello_world/sources/hello_world.move anchor=source
163152
```
164153

165154
During compilation, the code is built, but not run. A compiled package only includes functions that
@@ -201,16 +190,7 @@ the compiler. We explain tests in depth in the [Testing](./../move-basics/testin
201190

202191
Replace the contents of the `tests/hello_world_tests.move` with the following content:
203192

204-
```move
205-
#[test_only]
206-
module hello_world::hello_world_tests;
207-
208-
use hello_world::hello_world;
209-
210-
#[test]
211-
fun test_hello_world() {
212-
assert!(hello_world::hello_world() == b"Hello, World!".to_string(), 0);
213-
}
193+
```move file=packages/hello_world/tests/hello_world_tests.move anchor=test
214194
```
215195

216196
Here we import the `hello_world` module, and call its `hello_world` function to test that the output

packages/hello_world/sources/hello_world.move

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
// ANCHOR: source
12
/// The module `hello_world` under named address `hello_world`.
23
/// The named address is set in the `Move.toml`.
34
module hello_world::hello_world;
@@ -9,3 +10,4 @@ use std::string::String;
910
public fun hello_world(): String {
1011
b"Hello, World!".to_string()
1112
}
13+
// ANCHOR_END: source
Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,13 @@
1+
// ANCHOR: test
12
#[test_only]
23
module hello_world::hello_world_tests;
34

5+
use std::unit_test::assert_eq;
6+
47
use hello_world::hello_world;
58

69
#[test]
710
fun test_hello_world() {
8-
assert!(hello_world::hello_world() == b"Hello, World!".to_string(), 0);
11+
assert_eq!(hello_world::hello_world(), b"Hello, World!".to_string());
912
}
13+
// ANCHOR_END: test
Lines changed: 42 additions & 47 deletions
Original file line numberDiff line numberDiff line change
@@ -1,51 +1,46 @@
11
// Copyright (c) Mysten Labs, Inc.
22
// SPDX-License-Identifier: Apache-2.0
33

4-
module book::buffer {
5-
/// Error returned when the buffer is overflowed.
6-
const EBufferOverflow: u64 = 0;
7-
8-
/// The Buffer struct represents a growable buffer.
9-
public struct Buffer {
10-
data: vector<u8>,
11-
expected_len: Option<u64>
12-
}
13-
14-
/// Creates a new empty buffer.
15-
public fun new(): Buffer {
16-
Buffer { data: vector[], expected_len: option::none() }
17-
}
18-
19-
/// Creates a new empty buffer with the specified capacity (in bytes).
20-
/// If the buffer is overflowed, tx aborts with `EBufferOverflow`.
21-
public fun alloc(len: u64): Buffer {
22-
Buffer { data: vector[], expected_len: option::some(len) }
23-
}
24-
25-
/// Pushes the given data to the end of the buffer.
26-
public fun push(self: &mut Buffer, data: vector<u8>) {
27-
if (option::is_some(&self.expected_len)) {
28-
let max_len = *option::borrow(&self.expected_len);
29-
let future_len = self.len() + vector::length(&data);
30-
assert!(future_len <= max_len, EBufferOverflow);
31-
};
32-
33-
vector::append(&mut self.data, data)
34-
}
35-
36-
/// Unwraps the buffer and returns the underlying vector.
37-
public fun unwrap(self: Buffer): vector<u8> {
38-
let Buffer { data, expected_len: _ } = self;
39-
data
40-
}
41-
42-
/// Returns the length of the buffer.
43-
public fun len(self: &Buffer): u64 {
44-
vector::length(&self.data)
45-
}
46-
47-
/// Returns `true` if the buffer is empty.
48-
public fun is_empty(self: &Buffer): bool {
49-
vector::is_empty(&self.data)
50-
}
4+
module book::buffer;
5+
6+
/// Error returned when the buffer is overflowed.
7+
const EBufferOverflow: u64 = 0;
8+
9+
/// The Buffer struct represents a growable buffer.
10+
public struct Buffer {
11+
data: vector<u8>,
12+
expected_len: Option<u64>
13+
}
14+
15+
/// Creates a new empty buffer.
16+
public fun new(): Buffer {
17+
Buffer { data: vector[], expected_len: option::none() }
18+
}
19+
20+
/// Creates a new empty buffer with the specified capacity (in bytes).
21+
/// If the buffer is overflowed, tx aborts with `EBufferOverflow`.
22+
public fun alloc(len: u64): Buffer {
23+
Buffer { data: vector[], expected_len: option::some(len) }
24+
}
25+
26+
/// Pushes the given data to the end of the buffer.
27+
public fun push(self: &mut Buffer, data: vector<u8>) {
28+
self.expected_len.do_ref!(|max_len| assert!(self.len() + data.length() <= *max_len, EBufferOverflow));
29+
self.data.append(data)
30+
}
31+
32+
/// Unwraps the buffer and returns the underlying vector.
33+
public fun unwrap(self: Buffer): vector<u8> {
34+
let Buffer { data, expected_len: _ } = self;
35+
data
36+
}
37+
38+
/// Returns the length of the buffer.
39+
public fun len(self: &Buffer): u64 {
40+
self.data.length()
41+
}
42+
43+
/// Returns `true` if the buffer is empty.
44+
public fun is_empty(self: &Buffer): bool {
45+
self.data.is_empty()
5146
}
Lines changed: 34 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -1,44 +1,44 @@
11
// Copyright (c) Mysten Labs, Inc.
22
// SPDX-License-Identifier: Apache-2.0
33

4-
module book::ticket {
5-
/// A Ticket for an event or a service. Non-transferable by default and
6-
/// the usage varies based on the application.
7-
public struct Ticket<T: store + drop> has key {
8-
id: UID,
9-
used: bool,
10-
metadata: T
11-
}
4+
module book::ticket;
125

13-
/// Create a new Ticket with the metadata and the context.
14-
/// No need for a Witness here!
15-
public fun new<T: store + drop>(metadata: T, ctx: &mut TxContext): Ticket<T> {
16-
Ticket {
17-
id: object::new(ctx),
18-
used: false,
19-
metadata
20-
}
21-
}
6+
/// A Ticket for an event or a service. Non-transferable by default and
7+
/// the usage varies based on the application.
8+
public struct Ticket<T: store + drop> has key {
9+
id: UID,
10+
used: bool,
11+
metadata: T
12+
}
2213

23-
/// Consume the Ticket. Requires a Witness of the metadata type.
24-
/// May or may not be implemented by the application.
25-
public fun consume<T: store + drop>(_meta: T, ticket: &mut Ticket<T>) {
26-
ticket.used = true;
14+
/// Create a new Ticket with the metadata and the context.
15+
/// No need for a Witness here!
16+
public fun new<T: store + drop>(metadata: T, ctx: &mut TxContext): Ticket<T> {
17+
Ticket {
18+
id: object::new(ctx),
19+
used: false,
20+
metadata
2721
}
22+
}
2823

29-
/// Transfer the Ticket to another user. Requires a Witness of the metadata type.
30-
/// May or may not be implemented by the application.
31-
public fun transfer<T: store + drop>(_meta: T, ticket: Ticket<T>, to: address) {
32-
transfer::transfer(ticket, to)
33-
}
24+
/// Consume the Ticket. Requires a Witness of the metadata type.
25+
/// May or may not be implemented by the application.
26+
public fun consume<T: store + drop>(_meta: T, ticket: &mut Ticket<T>) {
27+
ticket.used = true;
28+
}
3429

35-
/// Get the metadata of the Ticket.
36-
public fun metadata<T: store + drop>(ticket: &Ticket<T>): &T {
37-
&ticket.metadata
38-
}
30+
/// Transfer the Ticket to another user. Requires a Witness of the metadata type.
31+
/// May or may not be implemented by the application.
32+
public fun transfer<T: store + drop>(_meta: T, ticket: Ticket<T>, to: address) {
33+
transfer::transfer(ticket, to)
34+
}
3935

40-
/// Check if the Ticket has been used.
41-
public fun is_used<T: store + drop>(ticket: &Ticket<T>): bool {
42-
ticket.used
43-
}
36+
/// Get the metadata of the Ticket.
37+
public fun metadata<T: store + drop>(ticket: &Ticket<T>): &T {
38+
&ticket.metadata
39+
}
40+
41+
/// Check if the Ticket has been used.
42+
public fun is_used<T: store + drop>(ticket: &Ticket<T>): bool {
43+
ticket.used
4444
}

packages/samples/sources/move-basics/constants-shop-price.move

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,9 @@ module book::shop_price;
66

77
use sui::{coin::Coin, sui::SUI};
88

9+
/// Trying to purchase an item at an incorrect price.
10+
const EWrongPrice: u64 = 0;
11+
912
/// The price of an item in the shop.
1013
const ITEM_PRICE: u64 = 100;
1114
/// The owner of the shop, an address.
@@ -16,7 +19,7 @@ public struct Item {}
1619

1720
/// Purchase an item from the shop.
1821
public fun purchase(coin: Coin<SUI>): Item {
19-
assert!(coin.value() == ITEM_PRICE);
22+
assert!(coin.value() == ITEM_PRICE, EWrongPrice);
2023

2124
transfer::public_transfer(coin, SHOP_OWNER);
2225

packages/samples/sources/move-basics/control-flow.move

Lines changed: 15 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,14 @@
11
// Copyright (c) Mysten Labs, Inc.
22
// SPDX-License-Identifier: Apache-2.0
33

4+
#[allow(unused_function)]
45
// ANCHOR: module
56
module book::control_flow;
67
// ANCHOR_END: module
78

9+
#[test_only]
10+
use std::unit_test::assert_eq;
11+
812
// ANCHOR: if_condition
913
#[test]
1014
fun test_if() {
@@ -26,7 +30,7 @@ fun test_if_else() {
2630
0
2731
};
2832

29-
assert!(y == 1);
33+
assert_eq!(y, 1);
3034
}
3135
// ANCHOR_END: if_else
3236
// ANCHOR: while_loop
@@ -50,9 +54,9 @@ fun while_loop(mut x: u8): u8 {
5054

5155
#[test]
5256
fun test_while() {
53-
assert!(while_loop(0) == 10); // 10 times
54-
assert!(while_loop(5) == 5); // 5 times
55-
assert!(while_loop(10) == 0); // loop never executed
57+
assert_eq!(while_loop(0), 10); // 10 times
58+
assert_eq!(while_loop(5), 5); // 5 times
59+
assert_eq!(while_loop(10), 0); // loop never executed
5660
}
5761
// ANCHOR_END: while_loop
5862
// ANCHOR: infinite_while
@@ -66,7 +70,7 @@ fun test_infinite_while() {
6670
};
6771

6872
// This line will never be executed.
69-
assert!(x == 5);
73+
assert_eq!(x, 5);
7074
}
7175
// ANCHOR_END: infinite_while
7276
#[allow(dead_code)]
@@ -81,7 +85,7 @@ fun test_infinite_loop() {
8185
};
8286

8387
// This line will never be executed.
84-
assert!(x == 5);
88+
assert_eq!(x, 5);
8589
}
8690
// ANCHOR_END: infinite_loop
8791
// ANCHOR: break_loop
@@ -99,7 +103,7 @@ fun test_break_loop() {
99103
}
100104
};
101105

102-
assert!(x == 5);
106+
assert_eq!(x, 5);
103107
}
104108
// ANCHOR_END: break_loop
105109
// ANCHOR: continue_loop
@@ -124,7 +128,7 @@ fun test_continue_loop() {
124128
}
125129
};
126130

127-
assert!(x == 10); // 10
131+
assert_eq!(x, 10) // 10
128132
}
129133
// ANCHOR_END: continue_loop
130134
// ANCHOR: return_statement
@@ -144,8 +148,8 @@ fun is_positive(x: u8): bool {
144148

145149
#[test]
146150
fun test_return() {
147-
assert!(is_positive(5) == false);
148-
assert!(is_positive(0) == false);
149-
assert!(is_positive(1) == true);
151+
assert_eq!(is_positive(5), false);
152+
assert_eq!(is_positive(0), false);
153+
assert_eq!(is_positive(1), true);
150154
}
151155
// ANCHOR_END: return_statement

0 commit comments

Comments
 (0)