ink_macro/lib.rs
1// Copyright (C) Use Ink (UK) Ltd.
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
15#![doc(
16 html_logo_url = "https://use.ink/img/crate-docs/logo.png",
17 html_favicon_url = "https://use.ink/crate-docs/favicon.png"
18)]
19
20extern crate proc_macro;
21
22mod blake2b;
23mod chain_extension;
24mod contract;
25mod event;
26mod ink_test;
27mod scale;
28mod selector;
29mod storage;
30mod storage_item;
31mod trait_def;
32
33#[cfg(test)]
34mod tests;
35
36use proc_macro::TokenStream;
37
38/// Computes and expands into the BLAKE2b 256-bit hash of the string input.
39///
40/// # Note
41///
42/// - The computation takes place at compilation time of the crate.
43/// - The returned value is of type `[u8; 32]`.
44///
45/// # Example
46///
47/// ```
48/// # use ink_macro::blake2x256;
49/// # use ink_ir::blake2b_256;
50/// assert_eq!(blake2x256!("hello"), {
51/// let mut output = [0u8; 32];
52/// blake2b_256(b"hello", &mut output);
53/// output
54/// });
55/// ```
56#[proc_macro]
57pub fn blake2x256(input: TokenStream) -> TokenStream {
58 blake2b::generate_blake2x256_hash(input.into()).into()
59}
60
61/// Computes the ink! selector of the string and expands into its `u32` representation.
62///
63/// # Note
64///
65/// The computation takes place at compilation time of the crate.
66///
67/// # Example
68///
69/// ```
70/// # use ink_macro::selector_id;
71/// assert_eq!(selector_id!("hello"), 843960066,);
72/// ```
73#[proc_macro]
74pub fn selector_id(input: TokenStream) -> TokenStream {
75 selector::generate_selector_id(input.into()).into()
76}
77
78/// Computes the ink! selector of the string and expands into its byte representation.
79///
80/// # Note
81///
82/// The computation takes place at compilation time of the crate.
83///
84/// # Example
85///
86/// ```
87/// # use ink_macro::selector_bytes;
88/// assert_eq!(selector_bytes!("hello"), [50, 77, 207, 2],);
89/// ```
90#[proc_macro]
91pub fn selector_bytes(input: TokenStream) -> TokenStream {
92 selector::generate_selector_bytes(input.into()).into()
93}
94
95/// Entry point for writing ink! smart contracts.
96///
97/// If you are a beginner trying to learn ink! we recommend you to check out
98/// our extensive [ink! workshop](https://docs.substrate.io/tutorials/v3/ink-workshop/pt1).
99///
100/// # Description
101///
102/// The macro does analysis on the provided smart contract code and generates
103/// proper code.
104///
105/// ink! smart contracts can compile in several different modes.
106/// There are two main compilation models using either
107/// - on-chain mode: `no_std` and WebAssembly as target
108/// - off-chain mode: `std`
109///
110/// We generally use the on-chain mode for actual smart contract instantiation
111/// whereas we use the off-chain mode for smart contract testing using the
112/// off-chain environment provided by the `ink_env` crate.
113///
114/// # Usage
115///
116/// ## Header Arguments
117///
118/// The `#[ink::contract]` macro can be provided with some additional comma-separated
119/// header arguments:
120///
121/// - `keep_attr: String`
122///
123/// Tells the ink! code generator which attributes should be passed to call builders.
124/// Call builders are used for making cross-contract calls and are automatically
125/// generated for contracts.
126///
127/// **Usage Example:**
128/// ```
129/// #[ink::contract(keep_attr = "foo, bar")]
130/// mod my_contract {
131/// # #[ink(storage)]
132/// # pub struct MyStorage;
133/// # impl MyStorage {
134/// # #[ink(constructor)]
135/// // #[bar]
136/// # pub fn construct() -> Self { MyStorage {} }
137/// # #[ink(message)]
138/// // #[foo]
139/// # pub fn message(&self) {}
140/// # }
141/// // ...
142/// }
143/// ```
144///
145/// **Allowed attributes by default:** `cfg`, `cfg_attr`, `allow`, `warn`, `deny`,
146/// `forbid`, `deprecated`, `must_use`, `doc`, `rustfmt`.
147///
148/// - `env: impl Environment`
149///
150/// Tells the ink! code generator which environment to use for the ink! smart
151/// contract. The environment must implement the `Environment` (defined in `ink_env`)
152/// trait and provides all the necessary fundamental type definitions for `Balance`,
153/// `AccountId` etc.
154///
155/// When using a custom `Environment` implementation for a smart contract all types
156/// that it exposes to the ink! smart contract and the mirrored types used in the
157/// runtime must be aligned with respect to SCALE encoding and semantics.
158///
159/// **Usage Example:**
160///
161/// Given a custom `Environment` implementation:
162/// ```
163/// #[derive(Clone)]
164/// pub struct MyEnvironment;
165///
166/// impl ink_env::Environment for MyEnvironment {
167/// const MAX_EVENT_TOPICS: usize = 3;
168/// type AccountId = [u8; 16];
169/// type Balance = u128;
170/// type Hash = [u8; 32];
171/// type Timestamp = u64;
172/// type BlockNumber = u32;
173/// type ChainExtension = ::ink::env::NoChainExtension;
174/// type EventRecord = ();
175/// }
176/// ```
177/// A user might implement their ink! smart contract using the above custom
178/// `Environment` implementation as demonstrated below:
179/// ```
180/// #[ink::contract(env = MyEnvironment)]
181/// mod my_contract {
182/// # #[derive(Clone)]
183/// # pub struct MyEnvironment;
184/// #
185/// # impl ink_env::Environment for MyEnvironment {
186/// # const MAX_EVENT_TOPICS: usize = 3;
187/// # type AccountId = [u8; 16];
188/// # type Balance = u128;
189/// # type Hash = [u8; 32];
190/// # type Timestamp = u64;
191/// # type BlockNumber = u32;
192/// # type ChainExtension = ::ink::env::NoChainExtension;
193/// # type EventRecord = ();
194/// # }
195/// #
196/// # #[ink(storage)]
197/// # pub struct MyStorage;
198/// # impl MyStorage {
199/// # #[ink(constructor)]
200/// # pub fn construct() -> Self { MyStorage {} }
201/// # #[ink(message)]
202/// # pub fn message(&self) {}
203/// # }
204/// // ...
205/// }
206/// ```
207///
208/// **Default value:** `DefaultEnvironment` defined in `ink_env` crate.
209///
210/// ## Analysis
211///
212/// The `#[ink::contract]` macro fully analyses its input smart contract
213/// against invalid arguments and structure.
214///
215/// Some example rules include but are not limited to:
216///
217/// - There must be exactly one `#[ink(storage)]` struct.
218///
219/// This struct defines the layout of the storage that the ink! smart contract
220/// operates on. The user is able to use a variety of built-in facilities, combine
221/// them in various ways or even provide their own implementations of storage data
222/// structures.
223///
224/// For more information visit the `ink::storage` crate documentation.
225///
226/// **Example:**
227///
228/// ```
229/// #[ink::contract]
230/// mod flipper {
231/// #[ink(storage)]
232/// pub struct Flipper {
233/// value: bool,
234/// }
235/// # impl Flipper {
236/// # #[ink(constructor)]
237/// # pub fn construct() -> Self { Flipper { value: false } }
238/// # #[ink(message)]
239/// # pub fn message(&self) {}
240/// # }
241/// }
242/// ```
243///
244/// - There must be at least one `#[ink(constructor)]` defined method.
245///
246/// Methods flagged with `#[ink(constructor)]` are special in that they are
247/// dispatchable upon contract instantiation. A contract may define multiple such
248/// constructors which allow users of the contract to instantiate a contract in
249/// multiple different ways.
250///
251/// **Example:**
252///
253/// Given the `Flipper` contract definition above we add an `#[ink(constructor)]`
254/// as follows:
255///
256/// ```
257/// # #[ink::contract]
258/// # mod flipper {
259/// # #[ink(storage)]
260/// # pub struct Flipper {
261/// # value: bool,
262/// # }
263/// impl Flipper {
264/// #[ink(constructor)]
265/// pub fn new(initial_value: bool) -> Self {
266/// Flipper { value: false }
267/// }
268/// # #[ink(message)]
269/// # pub fn message(&self) {}
270/// }
271/// # }
272/// ```
273///
274/// - There must be at least one `#[ink(message)]` defined method.
275///
276/// Methods flagged with `#[ink(message)]` are special in that they are dispatchable
277/// upon contract invocation. The set of ink! messages defined for an ink! smart
278/// contract define its API surface with which users are allowed to interact.
279///
280/// An ink! smart contract can have multiple such ink! messages defined.
281///
282/// **Note:**
283///
284/// - An ink! message with a `&self` receiver may only read state whereas an ink!
285/// message with a `&mut self` receiver may mutate the contract's storage.
286///
287/// **Example:**
288///
289/// Given the `Flipper` contract definition above we add some `#[ink(message)]`
290/// definitions as follows:
291///
292/// ```
293/// # #[ink::contract]
294/// # mod flipper {
295/// # #[ink(storage)]
296/// # pub struct Flipper {
297/// # value: bool,
298/// # }
299/// impl Flipper {
300/// # #[ink(constructor)]
301/// # pub fn new(initial_value: bool) -> Self {
302/// # Flipper { value: false }
303/// # }
304/// /// Flips the current value.
305/// #[ink(message)]
306/// pub fn flip(&mut self) {
307/// self.value = !self.value;
308/// }
309///
310/// /// Returns the current value.
311/// #[ink(message)]
312/// pub fn get(&self) -> bool {
313/// self.value
314/// }
315/// }
316/// # }
317/// ```
318///
319/// **Payable Messages:**
320///
321/// An ink! message by default will reject calls that additional fund the smart
322/// contract. Authors of ink! smart contracts can make an ink! message payable by
323/// adding the `payable` flag to it. An example below:
324///
325/// Note that ink! constructors are always implicitly payable and thus cannot be
326/// flagged as such.
327///
328/// ```
329/// # #[ink::contract]
330/// # mod flipper {
331/// # #[ink(storage)]
332/// # pub struct Flipper {
333/// # value: bool,
334/// # }
335/// impl Flipper {
336/// # #[ink(constructor)]
337/// # pub fn new(initial_value: bool) -> Self {
338/// # Flipper { value: false }
339/// # }
340/// /// Flips the current value.
341/// #[ink(message)]
342/// #[ink(payable)] // You can either specify payable out-of-line.
343/// pub fn flip(&mut self) {
344/// self.value = !self.value;
345/// }
346///
347/// /// Returns the current value.
348/// #[ink(message, payable)] // ...or specify payable inline.
349/// pub fn get(&self) -> bool {
350/// self.value
351/// }
352/// }
353/// # }
354/// ```
355///
356/// **Controlling the messages selector:**
357///
358/// Every ink! message and ink! constructor has a unique selector with which the
359/// message or constructor can be uniquely identified within the ink! smart contract.
360/// These selectors are mainly used to drive the contract's dispatch upon calling it.
361///
362/// An ink! smart contract author can control the selector of an ink! message or ink!
363/// constructor using the `selector` flag. An example is shown below:
364///
365/// ```
366/// # #[ink::contract]
367/// # mod flipper {
368/// # #[ink(storage)]
369/// # pub struct Flipper {
370/// # value: bool,
371/// # }
372/// impl Flipper {
373/// #[ink(constructor)]
374/// #[ink(selector = 0xDEADBEEF)] // Works on constructors as well.
375/// pub fn new(initial_value: bool) -> Self {
376/// Flipper { value: false }
377/// }
378///
379/// /// Flips the current value.
380/// #[ink(message)]
381/// #[ink(selector = 0xCAFEBABE)] // You can either specify selector out-of-line.
382/// pub fn flip(&mut self) {
383/// self.value = !self.value;
384/// }
385///
386/// /// Returns the current value.
387/// #[ink(message, selector = 0xFEEDBEEF)] // ...or specify selector inline.
388/// pub fn get(&self) -> bool {
389/// self.value
390/// }
391/// }
392/// # }
393/// ```
394///
395/// ## Interacting with the Contract Executor
396///
397/// The `ink_env` crate provides facilities to interact with the contract executor that
398/// connects ink! smart contracts with the outer world.
399///
400/// For example it is possible to query the current call's caller via:
401/// ```
402/// # ink_env::test::run_test::<ink_env::DefaultEnvironment, _>(|_| {
403/// let caller = ink_env::caller();
404/// # let _caller = caller;
405/// # Ok(())
406/// # }).unwrap();
407/// ```
408///
409/// However, ink! provides a much simpler way to interact with the contract executor
410/// via its environment accessor. An example below:
411///
412/// ```
413/// #[ink::contract]
414/// mod greeter {
415/// #[ink(storage)]
416/// pub struct Greeter;
417///
418/// impl Greeter {
419/// #[ink(constructor)]
420/// pub fn new() -> Self {
421/// let caller = Self::env().caller();
422/// Greeter {}
423/// }
424///
425/// #[ink(message, payable)]
426/// pub fn fund(&self) {
427/// let caller = self.env().caller();
428/// let value = self.env().transferred_value();
429/// }
430/// }
431/// }
432/// ```
433///
434/// ## Events
435///
436/// An ink! smart contract may define events that it can emit during contract execution.
437/// Emitting events can be used by third party tools to query information about a
438/// contract's execution and state.
439///
440/// The following example ink! contract shows how an event `Transferred` is defined and
441/// emitted in the `#[ink(constructor)]`.
442///
443/// ```
444/// #[ink::contract]
445/// mod erc20 {
446/// use ink::U256;
447///
448/// /// Defines an event that is emitted every time value is transferred.
449/// #[ink(event)]
450/// pub struct Transferred {
451/// from: Option<Address>,
452/// to: Option<Address>,
453/// value: U256,
454/// }
455///
456/// #[ink(storage)]
457/// pub struct Erc20 {
458/// total_supply: U256,
459/// // more fields...
460/// }
461///
462/// impl Erc20 {
463/// #[ink(constructor)]
464/// pub fn new(initial_supply: U256) -> Self {
465/// let caller = Self::env().caller();
466/// Self::env().emit_event(Transferred {
467/// from: None,
468/// to: Some(caller),
469/// value: initial_supply,
470/// });
471/// Self {
472/// total_supply: initial_supply,
473/// }
474/// }
475///
476/// #[ink(message)]
477/// pub fn total_supply(&self) -> U256 {
478/// self.total_supply
479/// }
480/// }
481/// }
482/// ```
483///
484/// ## Example: Flipper
485///
486/// The below code shows the complete implementation of the so-called Flipper
487/// ink! smart contract.
488/// For us it acts as the "Hello, World!" of the ink! smart contracts because
489/// it is minimal while still providing some more or less useful functionality.
490///
491/// It controls a single `bool` value that can be either `false` or `true`
492/// and allows the user to flip this value using the `Flipper::flip` message
493/// or retrieve the current value using `Flipper::get`.
494///
495/// ```
496/// #[ink::contract]
497/// pub mod flipper {
498/// #[ink(storage)]
499/// pub struct Flipper {
500/// value: bool,
501/// }
502///
503/// impl Flipper {
504/// /// Creates a new flipper smart contract initialized with the given value.
505/// #[ink(constructor)]
506/// pub fn new(init_value: bool) -> Self {
507/// Self { value: init_value }
508/// }
509///
510/// /// Flips the current value of the Flipper's boolean.
511/// #[ink(message)]
512/// pub fn flip(&mut self) {
513/// self.value = !self.value;
514/// }
515///
516/// /// Returns the current value of the Flipper's boolean.
517/// #[ink(message)]
518/// pub fn get(&self) -> bool {
519/// self.value
520/// }
521/// }
522/// }
523/// ```
524#[proc_macro_attribute]
525pub fn contract(attr: TokenStream, item: TokenStream) -> TokenStream {
526 contract::generate(attr.into(), item.into()).into()
527}
528
529/// Marks trait definitions to ink! as special ink! trait definitions.
530///
531/// There are some restrictions that apply to ink! trait definitions that
532/// this macro checks. Also ink! trait definitions are required to have specialized
533/// structure so that the main [`#[ink::contract]`](`macro@crate::contract`) macro can
534/// properly generate code for its implementations.
535///
536/// # Example
537///
538/// # Trait definition:
539///
540/// ```
541/// #[ink::trait_definition]
542/// pub trait Erc20 {
543/// /// Returns the total supply of the ERC-20 smart contract.
544/// #[ink(message)]
545/// fn total_supply(&self) -> ink::U256;
546///
547/// /// Transfers balance from the caller to the given address.
548/// #[ink(message)]
549/// fn transfer(&mut self, amount: ink::U256, to: ink::Address) -> bool;
550///
551/// // etc.
552/// }
553/// ```
554///
555/// # Trait implementation
556///
557/// Given the above trait definition you can implement it as shown below:
558///
559/// ```
560/// #[ink::contract]
561/// mod base_erc20 {
562/// use ink::U256;
563/// # // We somehow cannot put the trait in the doc-test crate root due to bugs.
564/// # #[ink::trait_definition]
565/// # pub trait Erc20 {
566/// # /// Returns the total supply of the ERC-20 smart contract.
567/// # #[ink(message)]
568/// # fn total_supply(&self) -> U256;
569/// #
570/// # /// Transfers balance from the caller to the given address.
571/// # #[ink(message)]
572/// # fn transfer(&mut self, amount: U256, to: Address) -> bool;
573/// # }
574/// #
575/// #[ink(storage)]
576/// pub struct BaseErc20 {
577/// total_supply: U256,
578/// }
579///
580/// impl BaseErc20 {
581/// #[ink(constructor)]
582/// pub fn new(initial_supply: U256) -> Self {
583/// Self { total_supply: initial_supply }
584/// }
585/// }
586///
587/// impl Erc20 for BaseErc20 {
588/// /// Returns the total supply of the ERC-20 smart contract.
589/// #[ink(message)]
590/// fn total_supply(&self) -> U256 {
591/// self.total_supply
592/// }
593///
594/// #[ink(message)]
595/// fn transfer(&mut self, amount: U256, to: Address) -> bool {
596/// unimplemented!()
597/// }
598/// }
599/// }
600/// ```
601///
602/// ## Header Arguments
603///
604/// The `#[ink::trait_definition]` macro can be provided with some additional
605/// comma-separated header arguments:
606///
607/// - `namespace: String`
608///
609/// The namespace configuration parameter is used to influence the generated
610/// selectors of the ink! trait messages. This is useful to disambiguate
611/// ink! trait definitions with equal names.
612///
613/// **Usage Example:**
614/// ```
615/// #[ink::trait_definition(namespace = "foo")]
616/// pub trait TraitDefinition {
617/// #[ink(message)]
618/// fn message1(&self);
619///
620/// #[ink(message, selector = 42)]
621/// fn message2(&self);
622/// }
623/// ```
624///
625/// **Default value:** Empty.
626///
627/// - `keep_attr: String`
628///
629/// Tells the ink! code generator which attributes should be passed to call builders.
630/// Call builders are used for making cross-contract calls and are automatically
631/// generated for contracts.
632///
633/// **Usage Example:**
634/// ```
635/// #[ink::trait_definition(keep_attr = "foo, bar")]
636/// pub trait Storage {
637/// #[ink(message)]
638/// // #[foo]
639/// fn message1(&self);
640///
641/// #[ink(message)]
642/// // #[bar]
643/// fn message2(&self);
644/// }
645/// ```
646///
647/// **Allowed attributes by default:** `cfg`, `cfg_attr`, `allow`, `warn`, `deny`,
648/// `forbid`, `deprecated`, `must_use`, `doc`, `rustfmt`.
649#[proc_macro_attribute]
650pub fn trait_definition(attr: TokenStream, item: TokenStream) -> TokenStream {
651 trait_def::analyze(attr.into(), item.into()).into()
652}
653
654/// Implements the necessary traits for a `struct` to be emitted as an event from a
655/// contract.
656///
657/// By default, a signature topic will be generated for the event. This allows consumers
658/// to filter and identify events of this type. Marking an event with `anonymous`
659/// means no signature topic will be generated or emitted.
660/// Custom signature topic can be specified with `signature_topic = <32 byte hex string>`.
661///
662/// `signature_topic` and `anonymous` are conflicting arguments.
663///
664/// # Examples
665///
666/// ```
667/// #[ink::event]
668/// pub struct MyEvent {
669/// pub field: u32,
670/// #[ink(topic)]
671/// pub topic: [u8; 32],
672/// }
673///
674/// // Setting `anonymous` means no signature topic will be emitted for the event.
675/// #[ink::event(anonymous)]
676/// pub struct MyAnonEvent {
677/// pub field: u32,
678/// #[ink(topic)]
679/// pub topic: [u8; 32],
680/// }
681/// // Setting `signature_topic = <hex_string>` specifies custom signature topic.
682/// #[ink::event(
683/// signature_topic = "1111111111111111111111111111111111111111111111111111111111111111"
684/// )]
685/// pub struct MyCustomSignatureEvent {
686/// pub field: u32,
687/// #[ink(topic)]
688/// pub topic: [u8; 32],
689/// }
690/// ```
691#[proc_macro_attribute]
692pub fn event(attr: TokenStream, item: TokenStream) -> TokenStream {
693 event::generate(attr.into(), item.into()).into()
694}
695
696/// Prepares the type to be fully compatible and usable with the storage.
697/// It implements all necessary traits and calculates the storage key for types.
698/// `Packed` types don't have a storage key, but non-packed types (like `Mapping`, `Lazy`
699/// etc.) require calculating the storage key during compilation.
700///
701/// Consider annotating structs and enums that are intended to be a part of
702/// the storage with this macro. If the type is packed then the usage of the
703/// macro is optional.
704///
705/// If the type is non-packed it is best to rely on automatic storage key
706/// calculation via `ink::storage_item`.
707///
708/// The usage of `KEY: StorageKey` generic allows to propagate the parent's storage key to
709/// the type and offset the storage key of the type. It is helpful for non-packed types
710/// that can be used several times in the contract. Each field should have a unique
711/// storage key, so propagation of the parent's storage key allows one to achieve it.
712///
713/// The macro should be called before `derive` macros because it can change the type.
714///
715/// All required traits can be:
716/// - Derived manually via `#[derive(...)]`.
717/// - Derived automatically via deriving of `scale::Decode` and `scale::Encode`.
718/// - Derived via this macro.
719///
720/// # Example
721///
722/// ## Trait implementation
723///
724/// ```
725/// use ink_prelude::vec::Vec;
726/// use ink::storage::{
727/// Lazy,
728/// Mapping,
729/// };
730/// use ink::storage::traits::{
731/// StorageKey,
732/// StorableHint,
733/// };
734/// use ink::storage::traits::Storable;
735///
736/// // Deriving `scale::Decode` and `scale::Encode` also derives blanket implementation of all
737/// // required traits to be storable.
738/// #[derive(scale::Decode, scale::Encode)]
739/// #[cfg_attr(
740/// feature = "std",
741/// derive(scale_info::TypeInfo, ink::storage::traits::StorageLayout)
742/// )]
743/// #[derive(Default, Debug)]
744/// struct Packed {
745/// s1: u128,
746/// s2: Vec<u128>,
747/// // Fails because `StorableHint` is only implemented for `Vec` where `T: Packed`.
748/// // s3: Vec<NonPacked>,
749/// }
750///
751/// // Example of how to define the packed type with generic.
752/// #[derive(scale::Decode, scale::Encode)]
753/// #[cfg_attr(
754/// feature = "std",
755/// derive(scale_info::TypeInfo, ink::storage::traits::StorageLayout)
756/// )]
757/// #[derive(Default, Debug)]
758/// struct PackedGeneric<T: ink::storage::traits::Packed> {
759/// s1: (u128, bool),
760/// s2: Vec<T>,
761/// s3: String,
762/// }
763///
764/// // Example of how to define the non-packed type.
765/// #[ink::storage_item]
766/// #[derive(Default, Debug)]
767/// struct NonPacked {
768/// s1: Mapping<u32, u128>,
769/// s2: Lazy<u128>,
770/// }
771///
772/// // Example of how to define the non-packed generic type.
773/// #[ink::storage_item(derive = false)]
774/// #[derive(Storable, StorableHint, StorageKey)]
775/// #[cfg_attr(
776/// feature = "std",
777/// derive(scale_info::TypeInfo, ink::storage::traits::StorageLayout)
778/// )]
779/// #[derive(Default, Debug)]
780/// struct NonPackedGeneric<T>
781/// where
782/// T: Default + core::fmt::Debug,
783/// T: ink::storage::traits::Packed,
784/// {
785/// s1: u32,
786/// s2: T,
787/// s3: Mapping<u128, T>,
788/// }
789///
790/// // Example of how to define a complex packed type.
791/// #[derive(scale::Decode, scale::Encode)]
792/// #[cfg_attr(
793/// feature = "std",
794/// derive(scale_info::TypeInfo, ink::storage::traits::StorageLayout)
795/// )]
796/// #[derive(Default, Debug)]
797/// struct PackedComplex {
798/// s1: u128,
799/// s2: Vec<u128>,
800/// s3: Vec<Packed>,
801/// }
802///
803/// // Example of how to define a complex non-packed type.
804/// #[ink::storage_item]
805/// #[derive(Default, Debug)]
806/// struct NonPackedComplex<KEY: StorageKey> {
807/// s1: (String, u128, Packed),
808/// s2: Mapping<u128, u128>,
809/// s3: Lazy<u128>,
810/// s4: Mapping<u128, Packed>,
811/// s5: Lazy<NonPacked>,
812/// s6: PackedGeneric<Packed>,
813/// s7: NonPackedGeneric<Packed>,
814/// // Fails because: the trait `ink::storage::traits::Packed` is not implemented for `NonPacked`
815/// // s8: Mapping<u128, NonPacked>,
816/// }
817/// ```
818///
819/// ## Header Arguments
820///
821/// The `#[ink::storage_item]` macro can be provided with an additional comma-separated
822/// header argument:
823///
824/// - `derive: bool`
825///
826/// The `derive` configuration parameter is used to enable/disable auto deriving of
827/// all required storage traits.
828///
829/// **Usage Example:**
830/// ```
831/// use ink::storage::Mapping;
832/// use ink::storage::traits::{
833/// StorableHint,
834/// StorageKey,
835/// Storable,
836/// };
837///
838/// #[ink::storage_item(derive = false)]
839/// #[derive(StorableHint, Storable, StorageKey)]
840/// struct NonPackedGeneric<T: ink::storage::traits::Packed> {
841/// s1: u32,
842/// s2: Mapping<u128, T>,
843/// }
844/// ```
845///
846/// **Default value:** true.
847#[proc_macro_attribute]
848pub fn storage_item(attr: TokenStream, item: TokenStream) -> TokenStream {
849 storage_item::generate(attr.into(), item.into()).into()
850}
851
852/// Defines a unit test that makes use of ink!'s off-chain testing capabilities.
853///
854/// If your unit test does not require the existence of an off-chain environment
855/// it is fine to not use this macro since it bears some overhead with the test.
856///
857/// Note that this macro is not required to run unit tests that require ink!'s
858/// off-chain testing capabilities but merely improves code readability.
859///
860/// ## How do you find out if your test requires the off-chain environment?
861///
862/// Normally if the test recursively uses or invokes some contract methods that
863/// call a method defined in `self.env()` or `Self::env()`.
864///
865/// An examples is the following:
866///
867/// ```no_compile
868/// let caller: AccountId = self.env().caller();
869/// ```
870///
871/// # Example
872///
873/// ```
874/// #[cfg(test)]
875/// mod tests {
876/// // Conventional unit test that works with assertions.
877/// #[ink::test]
878/// fn test1() {
879/// // test code comes here as usual
880/// }
881///
882/// // Conventional unit test that returns some Result.
883/// // The test code can make use of operator-`?`.
884/// #[ink::test]
885/// fn test2() -> Result<(), ink_env::Error> {
886/// // test code that returns a Rust Result type
887/// }
888/// }
889/// ```
890#[proc_macro_attribute]
891pub fn test(attr: TokenStream, item: TokenStream) -> TokenStream {
892 ink_test::generate(attr.into(), item.into()).into()
893}
894
895/// Defines the interface for a chain extension.
896///
897/// # Structure
898///
899/// The interface consists of an error code that indicates lightweight errors
900/// as well as the definition of some chain extension methods.
901///
902/// The overall structure follows that of a simple Rust trait definition.
903/// The error code is defined as an associated type definition of the trait definition.
904/// The methods are defined as associated trait methods without implementation.
905///
906/// Chain extension methods must not have a `self` receiver such as `&self` or `&mut self`
907/// and must have inputs and output that implement the SCALE encoding and decoding.
908/// Their return value follows specific rules that can be altered using the
909/// `handle_status` attribute which is described in more detail below.
910///
911/// # Usage
912///
913/// Usually the chain extension definition using this procedural macro is provided
914/// by the author of the chain extension in a separate crate.
915/// ink! smart contracts using this chain extension simply depend on this crate
916/// and use its associated environment definition in order to make use of
917/// the methods provided by the chain extension.
918///
919/// # Macro Attributes
920///
921/// The macro supports only one required argument:
922///
923/// - `extension = N: u16`:
924///
925/// The runtime may have several chain extensions at the same time. The `extension`
926/// identifier points to the corresponding chain extension in the runtime.
927/// The value should be the same as during the definition of the chain extension.
928///
929/// # Method Attributes
930///
931/// There are three different attributes with which the chain extension methods
932/// can be flagged:
933///
934/// | Attribute | Required | Default Value | Description |
935/// |:----------|:--------:|:--------------|:-----------:|
936/// | `ink(function = N: u16)` | Yes | - | Determines the unique function ID within the
937/// chain extension. | | `ink(handle_status = flag: bool)` | Optional | `true` | Assumes
938/// that the returned status code of the chain extension method always indicates success
939/// and therefore always loads and decodes the output buffer of the call. |
940///
941/// As with all ink! attributes multiple of them can either appear in a contiguous list:
942/// ```
943/// # type Access = i32;
944/// # #[ink::chain_extension(extension = 1)]
945/// # pub trait MyChainExtension {
946/// # type ErrorCode = i32;
947/// #[ink(function = 5, handle_status = false)]
948/// fn key_access_for_account(key: &[u8], account: &[u8]) -> Access;
949/// # }
950/// ```
951/// …or as multiple stand alone ink! attributes applied to the same item:
952/// ```
953/// # type Access = i32;
954/// # #[ink::chain_extension(extension = 1)]
955/// # pub trait MyChainExtension {
956/// # type ErrorCode = i32;
957/// #[ink(function = 5)]
958/// #[ink(handle_status = false)]
959/// fn key_access_for_account(key: &[u8], account: &[u8]) -> Access;
960/// # }
961/// ```
962///
963/// ## Details: `handle_status`
964///
965/// Default value: `true`
966///
967/// By default all chain extension methods should return a `Result<T, E>` where `E:
968/// From<Self::ErrorCode>`. The `Self::ErrorCode` represents the error code of the chain
969/// extension. This means that a smart contract calling such a chain extension method
970/// first queries the returned status code of the chain extension method and only loads
971/// and decodes the output if the returned status code indicates a successful call.
972/// This design was chosen as it is more efficient when no output besides the error
973/// code is required for a chain extension call. When designing a chain extension try to
974/// utilize the error code to return errors and only use the output buffer for information
975/// that does not fit in a single `u32` value.
976///
977/// A chain extension method that is flagged with `handle_status = false` assumes that the
978/// returned error code will always indicate success. Therefore it will always load and
979/// decode the output buffer and loses the `E: From<Self::ErrorCode>` constraint for the
980/// call.
981///
982/// Note that if a chain extension method does not return `Result<T, E>` where `E:
983/// From<Self::ErrorCode>` but `handle_status = true` it will still return a value of type
984/// `Result<T, Self::ErrorCode>`.
985///
986/// ## Usage: `handle_status`
987///
988/// Use both `handle_status = false` and non-`Result<T, E>` return type for the same chain
989/// extension method if a call to it may never fail and never returns a `Result` type.
990///
991/// # Combinations
992///
993/// Due to the possibility to flag a chain extension method with `handle_status` and
994/// return or not `Result<T, E>` there are 4 different cases with slightly varying
995/// semantics:
996///
997/// | `handle_status` | Returns `Result<T, E>` | Effects |
998/// |:---------------:|:----------------:|:--------|
999/// | `true` | `true` | The chain extension method is required to return a value of type
1000/// `Result<T, E>` where `E: From<Self::ErrorCode>`. A call will always check if the
1001/// returned status code indicates success and only then will load and decode the value in
1002/// the output buffer. | | `true` | `false` | The chain extension method may return any
1003/// non-`Result` type. A call will always check if the returned status code indicates
1004/// success and only then will load and decode the value in the output buffer. The actual
1005/// return type of the chain extension method is still `Result<T, Self::ErrorCode>` when
1006/// the chain extension method was defined to return a value of type `T`. | | `false` |
1007/// `true` | The chain extension method is required to return a value of type `Result<T,
1008/// E>`. A call will always assume that the returned status code indicates success and
1009/// therefore always load and decode the output buffer directly. | | `false` | `false` |
1010/// The chain extension method may return any non-`Result` type. A call will always assume
1011/// that the returned status code indicates success and therefore always load and decode
1012/// the output buffer directly. |
1013///
1014/// # Error Code
1015///
1016/// Every chain extension defines exactly one `ErrorCode` using the following syntax:
1017///
1018/// ```
1019/// #[ink::chain_extension(extension = 0)]
1020/// pub trait MyChainExtension {
1021/// type ErrorCode = MyErrorCode;
1022///
1023/// // more definitions
1024/// }
1025/// ```
1026///
1027/// The defined `ErrorCode` must implement `FromStatusCode` which should be implemented as
1028/// a more or less trivial conversion from the `u32` status code to a `Result<(),
1029/// Self::ErrorCode>`. The `Ok(())` value indicates that the call to the chain extension
1030/// method was successful.
1031///
1032/// By convention an error code of `0` represents success.
1033/// However, chain extension authors may use whatever suits their needs.
1034///
1035/// # Example: Definition
1036///
1037/// In the below example a chain extension is defined that allows its users to read and
1038/// write from and to the runtime storage using access privileges:
1039///
1040/// ```
1041/// /// Custom chain extension to read to and write from the runtime.
1042/// #[ink::chain_extension(extension = 0)]
1043/// pub trait RuntimeReadWrite {
1044/// type ErrorCode = ReadWriteErrorCode;
1045///
1046/// /// Reads from runtime storage.
1047/// ///
1048/// /// # Note
1049/// ///
1050/// /// Actually returns a value of type `Result<Vec<u8>, Self::ErrorCode>`.
1051/// #[ink(function = 1)]
1052/// fn read(key: &[u8]) -> Vec<u8>;
1053///
1054/// /// Reads from runtime storage.
1055/// ///
1056/// /// Returns the number of bytes read and up to 32 bytes of the
1057/// /// read value. Unused bytes in the output are set to 0.
1058/// ///
1059/// /// # Errors
1060/// ///
1061/// /// If the runtime storage cell stores a value that requires more than
1062/// /// 32 bytes.
1063/// ///
1064/// /// # Note
1065/// ///
1066/// /// This requires `ReadWriteError` to implement `From<ReadWriteErrorCode>`
1067/// /// and may potentially return any `Self::ErrorCode` through its return value.
1068/// #[ink(function = 2)]
1069/// fn read_small(key: &[u8]) -> Result<(u32, [u8; 32]), ReadWriteError>;
1070///
1071/// /// Writes into runtime storage.
1072/// ///
1073/// /// # Note
1074/// ///
1075/// /// Actually returns a value of type `Result<(), Self::ErrorCode>`.
1076/// #[ink(function = 3)]
1077/// fn write(key: &[u8], value: &[u8]);
1078///
1079/// /// Returns the access allowed for the key for the caller.
1080/// ///
1081/// /// # Note
1082/// ///
1083/// /// Assumes to never fail the call and therefore always returns `Option<Access>`.
1084/// #[ink(function = 4, handle_status = false)]
1085/// fn access(key: &[u8]) -> Option<Access>;
1086///
1087/// /// Unlocks previously acquired permission to access key.
1088/// ///
1089/// /// # Errors
1090/// ///
1091/// /// If the permission was not granted.
1092/// ///
1093/// /// # Note
1094/// ///
1095/// /// Assumes the call to never fail and therefore does _NOT_ require `UnlockAccessError`
1096/// /// to implement `From<Self::ErrorCode>` as in the `read_small` method above.
1097/// #[ink(function = 5, handle_status = false)]
1098/// fn unlock_access(key: &[u8], access: Access) -> Result<(), UnlockAccessError>;
1099/// }
1100/// # #[derive(scale::Encode, scale::Decode, scale_info::TypeInfo)]
1101/// # pub enum ReadWriteErrorCode {
1102/// # InvalidKey,
1103/// # CannotWriteToKey,
1104/// # CannotReadFromKey,
1105/// # }
1106/// # #[derive(scale::Encode, scale::Decode, scale_info::TypeInfo)]
1107/// # pub enum ReadWriteError {
1108/// # ErrorCode(ReadWriteErrorCode),
1109/// # BufferTooSmall { required_bytes: u32 },
1110/// # }
1111/// # impl From<ReadWriteErrorCode> for ReadWriteError {
1112/// # fn from(error_code: ReadWriteErrorCode) -> Self {
1113/// # Self::ErrorCode(error_code)
1114/// # }
1115/// # }
1116/// # impl From<scale::Error> for ReadWriteError {
1117/// # fn from(_: scale::Error) -> Self {
1118/// # panic!("encountered unexpected invalid SCALE encoding")
1119/// # }
1120/// # }
1121/// # #[derive(scale::Encode, scale::Decode, scale_info::TypeInfo)]
1122/// # pub struct UnlockAccessError {
1123/// # reason: String,
1124/// # }
1125/// # impl From<scale::Error> for UnlockAccessError {
1126/// # fn from(_: scale::Error) -> Self {
1127/// # panic!("encountered unexpected invalid SCALE encoding")
1128/// # }
1129/// # }
1130/// # #[derive(scale::Encode, scale::Decode, scale_info::TypeInfo, Clone)]
1131/// # pub enum Access {
1132/// # ReadWrite,
1133/// # ReadOnly,
1134/// # WriteOnly,
1135/// # }
1136/// # impl ink_env::chain_extension::FromStatusCode for ReadWriteErrorCode {
1137/// # fn from_status_code(status_code: u32) -> Result<(), Self> {
1138/// # match status_code {
1139/// # 0 => Ok(()),
1140/// # 1 => Err(Self::InvalidKey),
1141/// # 2 => Err(Self::CannotWriteToKey),
1142/// # 3 => Err(Self::CannotReadFromKey),
1143/// # _ => panic!("encountered unknown status code"),
1144/// # }
1145/// # }
1146/// # }
1147/// ```
1148///
1149/// All the error types and other utility types used in the chain extension definition
1150/// above are often required to implement various traits such as SCALE's `Encode` and
1151/// `Decode` as well as `scale-info`'s `TypeInfo` trait.
1152///
1153/// A full example of the above chain extension definition can be seen
1154/// [here](https://github.com/use-ink/ink/blob/017f71d60799b764425334f86b732cc7b7065fe6/crates/lang/macro/tests/ui/chain_extension/simple.rs).
1155///
1156/// # Example: Environment
1157///
1158/// In order to allow ink! smart contracts to use the above defined chain extension it
1159/// needs to be integrated into an `Environment` definition as shown below:
1160///
1161/// ```
1162/// # type RuntimeReadWrite = i32;
1163/// #
1164/// use ink_env::{
1165/// DefaultEnvironment,
1166/// Environment,
1167/// };
1168///
1169/// #[derive(Clone)]
1170/// pub enum CustomEnvironment {}
1171///
1172/// impl Environment for CustomEnvironment {
1173/// const MAX_EVENT_TOPICS: usize =
1174/// <DefaultEnvironment as Environment>::MAX_EVENT_TOPICS;
1175///
1176/// type AccountId = <DefaultEnvironment as Environment>::AccountId;
1177/// type Balance = <DefaultEnvironment as Environment>::Balance;
1178/// type Hash = <DefaultEnvironment as Environment>::Hash;
1179/// type BlockNumber = <DefaultEnvironment as Environment>::BlockNumber;
1180/// type Timestamp = <DefaultEnvironment as Environment>::Timestamp;
1181/// type EventRecord = <DefaultEnvironment as Environment>::EventRecord;
1182///
1183/// type ChainExtension = RuntimeReadWrite;
1184/// }
1185/// ```
1186///
1187/// Above we defined the `CustomEnvironment` which defaults to ink!'s `DefaultEnvironment`
1188/// for all constants and types but the `ChainExtension` type which is assigned to our
1189/// newly defined chain extension.
1190///
1191/// # Example: Usage
1192///
1193/// An ink! smart contract can use the above defined chain extension through the
1194/// `Environment` definition defined in the last example section using the `env` macro
1195/// parameter as shown below.
1196///
1197/// Note that chain extension methods are accessible through `Self::extension()` or
1198/// `self.extension()`. For example as in `Self::extension().read(...)` or
1199/// `self.extension().read(...)`.
1200///
1201/// ```
1202/// #[ink::contract(env = CustomEnvironment)]
1203/// mod read_writer {
1204/// #[ink(storage)]
1205/// pub struct ReadWriter {}
1206///
1207/// impl ReadWriter {
1208/// #[ink(constructor)]
1209/// pub fn new() -> Self { Self {} }
1210///
1211/// #[ink(message)]
1212/// pub fn read(&self, key: Vec<u8>) -> Result<Vec<u8>, ReadWriteErrorCode> {
1213/// self.env()
1214/// .extension()
1215/// .read(&key)
1216/// }
1217///
1218/// #[ink(message)]
1219/// pub fn read_small(&self, key: Vec<u8>) -> Result<(u32, [u8; 32]), ReadWriteError> {
1220/// self.env()
1221/// .extension()
1222/// .read_small(&key)
1223/// }
1224///
1225/// #[ink(message)]
1226/// pub fn write(
1227/// &self,
1228/// key: Vec<u8>,
1229/// value: Vec<u8>,
1230/// ) -> Result<(), ReadWriteErrorCode> {
1231/// self.env()
1232/// .extension()
1233/// .write(&key, &value)
1234/// }
1235///
1236/// #[ink(message)]
1237/// pub fn access(&self, key: Vec<u8>) -> Option<Access> {
1238/// self.env()
1239/// .extension()
1240/// .access(&key)
1241/// }
1242///
1243/// #[ink(message)]
1244/// pub fn unlock_access(&self, key: Vec<u8>, access: Access) -> Result<(), UnlockAccessError> {
1245/// self.env()
1246/// .extension()
1247/// .unlock_access(&key, access)
1248/// }
1249/// }
1250/// # /// Custom chain extension to read to and write from the runtime.
1251/// # #[ink::chain_extension(extension = 13)]
1252/// # pub trait RuntimeReadWrite {
1253/// # type ErrorCode = ReadWriteErrorCode;
1254/// # #[ink(function = 1)]
1255/// # fn read(key: &[u8]) -> Vec<u8>;
1256/// # #[ink(function = 2)]
1257/// # fn read_small(key: &[u8]) -> Result<(u32, [u8; 32]), ReadWriteError>;
1258/// # #[ink(function = 3)]
1259/// # fn write(key: &[u8], value: &[u8]);
1260/// # #[ink(function = 4, handle_status = false)]
1261/// # fn access(key: &[u8]) -> Option<Access>;
1262/// # #[ink(function = 5, handle_status = false)]
1263/// # fn unlock_access(key: &[u8], access: Access) -> Result<(), UnlockAccessError>;
1264/// # }
1265/// # #[derive(scale::Encode, scale::Decode, scale_info::TypeInfo)]
1266/// # pub enum ReadWriteErrorCode {
1267/// # InvalidKey,
1268/// # CannotWriteToKey,
1269/// # CannotReadFromKey,
1270/// # }
1271/// # #[derive(scale::Encode, scale::Decode, scale_info::TypeInfo)]
1272/// # pub enum ReadWriteError {
1273/// # ErrorCode(ReadWriteErrorCode),
1274/// # BufferTooSmall { required_bytes: u32 },
1275/// # }
1276/// # impl From<ReadWriteErrorCode> for ReadWriteError {
1277/// # fn from(error_code: ReadWriteErrorCode) -> Self {
1278/// # Self::ErrorCode(error_code)
1279/// # }
1280/// # }
1281/// # impl From<scale::Error> for ReadWriteError {
1282/// # fn from(_: scale::Error) -> Self {
1283/// # panic!("encountered unexpected invalid SCALE encoding")
1284/// # }
1285/// # }
1286/// # #[derive(scale::Encode, scale::Decode, scale_info::TypeInfo)]
1287/// # pub struct UnlockAccessError {
1288/// # reason: String,
1289/// # }
1290/// # impl From<scale::Error> for UnlockAccessError {
1291/// # fn from(_: scale::Error) -> Self {
1292/// # panic!("encountered unexpected invalid SCALE encoding")
1293/// # }
1294/// # }
1295/// # #[derive(scale::Encode, scale::Decode, scale_info::TypeInfo, Clone)]
1296/// # pub enum Access {
1297/// # ReadWrite,
1298/// # ReadOnly,
1299/// # WriteOnly,
1300/// # }
1301/// # impl ink_env::chain_extension::FromStatusCode for ReadWriteErrorCode {
1302/// # fn from_status_code(status_code: u32) -> Result<(), Self> {
1303/// # match status_code {
1304/// # 0 => Ok(()),
1305/// # 1 => Err(Self::InvalidKey),
1306/// # 2 => Err(Self::CannotWriteToKey),
1307/// # 3 => Err(Self::CannotReadFromKey),
1308/// # _ => panic!("encountered unknown status code"),
1309/// # }
1310/// # }
1311/// # }
1312/// # #[derive(Clone)]
1313/// # pub enum CustomEnvironment {}
1314/// # impl ink_env::Environment for CustomEnvironment {
1315/// # const MAX_EVENT_TOPICS: usize =
1316/// # <ink_env::DefaultEnvironment as ink_env::Environment>::MAX_EVENT_TOPICS;
1317/// #
1318/// # type AccountId = <ink_env::DefaultEnvironment as ink_env::Environment>::AccountId;
1319/// # type Balance = <ink_env::DefaultEnvironment as ink_env::Environment>::Balance;
1320/// # type Hash = <ink_env::DefaultEnvironment as ink_env::Environment>::Hash;
1321/// # type BlockNumber = <ink_env::DefaultEnvironment as ink_env::Environment>::BlockNumber;
1322/// # type Timestamp = <ink_env::DefaultEnvironment as ink_env::Environment>::Timestamp;
1323/// # type EventRecord = <ink_env::DefaultEnvironment as ink_env::Environment>::EventRecord;
1324/// #
1325/// # type ChainExtension = RuntimeReadWrite;
1326/// # }
1327/// }
1328/// ```
1329///
1330/// # Technical Limitations
1331///
1332/// - Due to technical limitations it is not possible to refer to the `ErrorCode`
1333/// associated type using `Self::ErrorCode` anywhere within the chain extension and its
1334/// defined methods. Instead chain extension authors should directly use the error code
1335/// type when required. This limitation might be lifted in future versions of ink!.
1336/// - It is not possible to declare other chain extension traits as super traits or super
1337/// chain extensions of another.
1338#[proc_macro_attribute]
1339pub fn chain_extension(attr: TokenStream, item: TokenStream) -> TokenStream {
1340 chain_extension::generate(attr.into(), item.into()).into()
1341}
1342
1343synstructure::decl_derive!(
1344 [Event, attributes(ink)] =>
1345 /// Derives an implementation of the [`ink::Event`] trait for the given `struct`.
1346 ///
1347 /// **Note** [`ink::Event`] requires [`scale::Encode`] implementation.
1348 ///
1349 /// Usually this is used in conjunction with the [`EventMetadata`] derive.
1350 ///
1351 /// For convenience there is the [`event`] attribute macro that will expand to all the necessary
1352 /// derives for an event implementation, including this one.
1353 ///
1354 /// # Example
1355 ///
1356 /// ```
1357 /// use ink::{
1358 /// Event,
1359 /// env::DefaultEnvironment,
1360 /// };
1361 /// use scale::Encode;
1362 ///
1363 /// #[derive(Event, Encode)]
1364 /// struct MyEvent {
1365 /// a: u32,
1366 /// #[ink(topic)]
1367 /// b: [u8; 32],
1368 /// }
1369 ///
1370 /// #[derive(Event, Encode)]
1371 /// #[ink(anonymous)] // anonymous events do not have a signature topic
1372 /// struct MyAnonEvent {
1373 /// a: u32,
1374 /// #[ink(topic)]
1375 /// b: [u8; 32],
1376 /// }
1377 ///
1378 /// ink_env::emit_event::<DefaultEnvironment, _>(MyEvent { a: 42, b: [0x42; 32] });
1379 /// ink_env::emit_event::<DefaultEnvironment, _>(MyAnonEvent { a: 42, b: [0x42; 32] });
1380 /// ```
1381 ///
1382 /// # The Signature Topic
1383 ///
1384 /// By default, the [`ink::Event::SIGNATURE_TOPIC`] is calculated as follows:
1385 ///
1386 /// `blake2b("EventStructName(field1_type_name,field2_type_name)")`
1387 ///
1388 /// The hashing of the topic is done at codegen time in the derive macro, and as such only has
1389 /// access to the **names** of the field types as they appear in the code. As such, if the
1390 /// name of a field of a struct changes, the signature topic will change too, even if the
1391 /// concrete type itself has not changed. This can happen with type aliases, generics, or a
1392 /// change in the use of a `path::to::Type` qualification.
1393 ///
1394 /// Practically this means that two otherwise identical event definitions will have different
1395 /// signature topics if the name of a field type differs. For example, the following two events
1396 /// will have different signature topics:
1397 ///
1398 /// ```
1399 /// #[derive(ink::Event, scale::Encode)]
1400 /// pub struct MyEvent {
1401 /// a: u32,
1402 /// }
1403 ///
1404 /// mod other_event {
1405 /// type MyU32 = u32;
1406 ///
1407 /// #[derive(ink::Event, scale::Encode)]
1408 /// pub struct MyEvent {
1409 /// a: MyU32,
1410 /// }
1411 /// }
1412 ///
1413 /// assert_ne!(<MyEvent as ink::env::Event>::SIGNATURE_TOPIC, <other_event::MyEvent as ink::env::Event>::SIGNATURE_TOPIC);
1414 /// ```
1415 ///
1416 /// ## Custom Signature
1417 ///
1418 /// Sometimes it is useful to specify the custom signature topic.
1419 /// For example, when the event definition from the other contract is not accessible.
1420 ///
1421 /// The macro provides `#[ink(signature_topic = _)]` nested macro that allows to provide
1422 /// 32 byte hex string of the custom signature topic.
1423 ///
1424 /// Generates custom signature topic
1425 /// ```
1426 /// #[derive(ink::Event, scale::Encode)]
1427 /// #[ink(signature_topic = "1111111111111111111111111111111111111111111111111111111111111111")]
1428 /// pub struct MyCustomSignatureEvent {
1429 /// pub field: u32,
1430 /// pub topic: [u8; 32],
1431 /// }
1432 ///
1433 /// assert_eq!(Some([17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17]),
1434 /// <MyCustomSignatureEvent as ink::env::Event>::SIGNATURE_TOPIC)
1435 ///```
1436 /// ## Anonymous Events
1437 ///
1438 /// If the event is annotated with `#[ink(anonymous)]` then no signature topic is generated.
1439 /// `#[ink(signature_topic = _)]` should not be used.
1440 event::event_derive
1441);
1442
1443synstructure::decl_derive!(
1444 [EventMetadata] =>
1445 /// Derives the [`ink::EventMetadata`] trait for the given `struct`, which provides metadata
1446 /// about the event definition.
1447 ///
1448 /// Requires that the `struct` also implements the [`ink::Event`] trait,
1449 /// so this derive is usually used in combination with the [`Event`] derive.
1450 ///
1451 /// Metadata is not embedded into the contract binary, it is generated from a separate
1452 /// compilation of the contract with the `std` feature, therefore this derive must be
1453 /// conditionally compiled e.g. `#[cfg_attr(feature = "std", derive(::ink::EventMetadata))]`
1454 /// (see example below).
1455 ///
1456 /// For convenience there is the [`event`] attribute macro that will expand to all the necessary
1457 /// derives for an event implementation, including this one.
1458 ///
1459 /// # Example
1460 ///
1461 /// ```
1462 /// use ink::{
1463 /// Event,
1464 /// env::DefaultEnvironment,
1465 /// };
1466 /// use scale::Encode;
1467 ///
1468 /// #[cfg_attr(feature = "std", derive(::ink::EventMetadata))]
1469 /// #[derive(Event, Encode)]
1470 /// struct MyEvent {
1471 /// a: u32,
1472 /// #[ink(topic)]
1473 /// b: [u8; 32],
1474 /// }
1475 ///
1476 /// assert_eq!(<MyEvent as ink::metadata::EventMetadata>::event_spec().args().len(), 2);
1477 /// ```
1478 ///
1479 /// The generated code will also register this implementation with the global static distributed
1480 /// slice [`ink::metadata::EVENTS`], in order that the metadata of all events used in a contract
1481 /// can be collected.
1482 event::event_metadata_derive
1483);
1484
1485synstructure::decl_derive!(
1486 [Storable] =>
1487 /// Derives `ink::storage`'s `Storable` trait for the given `struct`, `enum` or `union`.
1488 ///
1489 /// # Examples
1490 ///
1491 /// ```
1492 /// use ink::storage::traits::Storable;
1493 ///
1494 /// #[derive(Storable)]
1495 /// struct NamedFields {
1496 /// a: u32,
1497 /// b: [u32; 1],
1498 /// }
1499 ///
1500 /// let value = <NamedFields as Storable>::decode(&mut &[123, 123][..]);
1501 /// ```
1502 storage::storable_derive
1503);
1504synstructure::decl_derive!(
1505 [StorableHint] =>
1506 /// Derives `ink::storage`'s `StorableHint` trait for the given `struct` or `enum`.
1507 ///
1508 /// If the type declaration contains generic `StorageKey`,
1509 /// it will use it as salt to generate a combined storage key.
1510 ///
1511 /// # Examples
1512 ///
1513 /// ```
1514 /// use ink::storage::traits::{
1515 /// Storable,
1516 /// StorableHint,
1517 /// StorageKey,
1518 /// AutoStorableHint,
1519 /// AutoKey,
1520 /// ManualKey,
1521 /// };
1522 ///
1523 /// #[derive(Default, StorableHint, Storable)]
1524 /// struct NamedFields {
1525 /// a: u32,
1526 /// b: [u32; 32],
1527 /// }
1528 ///
1529 /// let _: NamedFields = <NamedFields as StorableHint<AutoKey>>::Type::default();
1530 /// let _: NamedFields = <NamedFields as StorableHint<ManualKey<123>>>::Type::default();
1531 /// ```
1532 storage::storable_hint_derive
1533);
1534synstructure::decl_derive!(
1535 [StorageKey] =>
1536 /// Derives `ink::storage`'s `StorageKey` trait for the given `struct` or `enum`.
1537 ///
1538 /// # Examples
1539 ///
1540 /// ```
1541 /// use ink::storage::traits::{
1542 /// AutoStorableHint,
1543 /// StorageKey,
1544 /// ManualKey,
1545 /// AutoKey,
1546 /// };
1547 ///
1548 /// #[derive(StorageKey)]
1549 /// struct NamedFields {
1550 /// a: u32,
1551 /// b: [u32; 32],
1552 /// }
1553 ///
1554 /// assert_eq!(<NamedFields as StorageKey>::KEY, 0);
1555 ///
1556 /// #[derive(StorageKey)]
1557 /// struct NamedFieldsManualKey<KEY: StorageKey> {
1558 /// a: <u32 as AutoStorableHint<ManualKey<0, KEY>>>::Type,
1559 /// b: <[u32; 32] as AutoStorableHint<ManualKey<1, KEY>>>::Type,
1560 /// }
1561 ///
1562 /// assert_eq!(<NamedFieldsManualKey<()> as StorageKey>::KEY, 0);
1563 /// assert_eq!(<NamedFieldsManualKey<AutoKey> as StorageKey>::KEY, 0);
1564 /// assert_eq!(<NamedFieldsManualKey<ManualKey<123>> as StorageKey>::KEY, 123);
1565 /// ```
1566 storage::storage_key_derive
1567);
1568synstructure::decl_derive!(
1569 [StorageLayout] =>
1570 /// Derives `ink::storage`'s `StorageLayout` trait for the given `struct` or `enum`.
1571 ///
1572 /// # Examples
1573 ///
1574 /// ```
1575 /// use ink_metadata::layout::Layout::Struct;
1576 /// use ink::storage::traits::StorageLayout;
1577 ///
1578 /// #[derive(StorageLayout)]
1579 /// struct NamedFields {
1580 /// a: u32,
1581 /// b: [u32; 32],
1582 /// }
1583 ///
1584 /// let key = 0x123;
1585 /// let mut value = NamedFields {
1586 /// a: 123,
1587 /// b: [22; 32],
1588 /// };
1589 ///
1590 /// if let Struct(layout) = <NamedFields as StorageLayout>::layout(&key) {
1591 /// assert_eq!(*layout.fields()[0].name(), "a");
1592 /// assert_eq!(*layout.fields()[1].name(), "b");
1593 /// }
1594 /// ```
1595 storage::storage_layout_derive
1596);
1597
1598/// Derive the re-exported traits `ink::scale::Encode`, `ink::scale::Decode` and
1599/// `ink::scale_info::TypeInfo`. It enables using the built in derive macros for these
1600/// traits without depending directly on the `parity-scale-codec` and `scale-info` crates.
1601///
1602/// # Options
1603/// - `Encode`: derives `ink::scale::Encode`
1604/// - `Decode`: derives `ink::scale::Decode`
1605/// - `TypeInfo`: derives `ink::scale_info::TypeInfo`
1606///
1607/// # Examples
1608///
1609/// ```
1610/// #[ink::scale_derive(Encode, Decode, TypeInfo)]
1611/// pub enum Error {}
1612/// ```
1613/// This is a convenience macro that expands to include the additional `crate` attributes
1614/// required for the path of the re-exported crates.
1615///
1616/// ```
1617/// #[derive(::ink::scale::Encode, ::ink::scale::Decode)]
1618/// #[codec(crate = ::ink::scale)]
1619/// #[cfg_attr(
1620/// feature = "std",
1621/// derive(::scale_info::TypeInfo),
1622/// scale_info(crate = ::ink::scale_info)
1623/// )]
1624/// pub enum Error {}
1625/// ```
1626#[proc_macro_attribute]
1627pub fn scale_derive(attr: TokenStream, item: TokenStream) -> TokenStream {
1628 match scale::derive(attr.into(), item.into()) {
1629 Ok(output) => output.into(),
1630 Err(err) => err.to_compile_error().into(),
1631 }
1632}
1633
1634#[cfg(test)]
1635pub use contract::generate_or_err;