Construct Runtime v2 (#1378)

Moved from https://github.com/paritytech/substrate/pull/14788

----

Fixes https://github.com/paritytech/polkadot-sdk/issues/232

This PR introduces outer-macro approach for `construct_runtime` as
discussed in the linked issue. It looks like the following:
```rust
#[frame_support::runtime]
mod runtime {
	#[runtime::runtime]
        #[runtime::derive(
		RuntimeCall,
		RuntimeEvent,
		RuntimeError,
		RuntimeOrigin,
		RuntimeFreezeReason,
		RuntimeHoldReason,
		RuntimeSlashReason,
		RuntimeLockId,
                RuntimeTask,
	)]
	pub struct Runtime;

	#[runtime::pallet_index(0)]
	pub type System = frame_system;

	#[runtime::pallet_index(1)]
	pub type Timestamp = pallet_timestamp;

	#[runtime::pallet_index(2)]
	pub type Aura = pallet_aura;

	#[runtime::pallet_index(3)]
	pub type Grandpa = pallet_grandpa;

	#[runtime::pallet_index(4)]
	pub type Balances = pallet_balances;

	#[runtime::pallet_index(5)]
	pub type TransactionPayment = pallet_transaction_payment;

	#[runtime::pallet_index(6)]
	pub type Sudo = pallet_sudo;

	// Include the custom logic from the pallet-template in the runtime.
	#[runtime::pallet_index(7)]
	pub type TemplateModule = pallet_template;
}
```

## Features
- `#[runtime::runtime]` attached to a struct defines the main runtime
- `#[runtime::derive]` attached to this struct defines the types
generated by runtime
- `#[runtime::pallet_index]` must be attached to a pallet to define its
index
- `#[runtime::disable_call]` can be optionally attached to a pallet to
disable its calls
- `#[runtime::disable_unsigned]` can be optionally attached to a pallet
to disable unsigned calls
- A pallet instance can be defined as `TemplateModule:
pallet_template<Instance>`
- An optional attribute can be defined as
`#[frame_support::runtime(legacy_ordering)]` to ensure that the order of
hooks is same as the order of pallets (and not based on the
pallet_index). This is to support legacy runtimes and should be avoided
for new ones.

## Todo
- [x] Update the latest syntax in kitchensink and tests
- [x] Update UI tests
- [x] Docs

## Extension
- Abstract away the Executive similar to
https://github.com/paritytech/substrate/pull/14742
- Optionally avoid the need to specify all runtime types (TBD)

---------

Co-authored-by: Francisco Aguirre <franciscoaguirreperez@gmail.com>
Co-authored-by: Nikhil Gupta <>
This commit is contained in:
gupnik
2024-03-13 12:31:01 +05:30
committed by GitHub
parent a756baf3b2
commit 82f3c3e2e8
45 changed files with 3211 additions and 204 deletions
@@ -31,6 +31,7 @@ mod match_and_insert;
mod no_bound;
mod pallet;
mod pallet_error;
mod runtime;
mod storage_alias;
mod transactional;
mod tt_macro;
@@ -1220,6 +1221,73 @@ pub fn import_section(attr: TokenStream, tokens: TokenStream) -> TokenStream {
.into()
}
/// Construct a runtime, with the given name and the given pallets.
///
/// # Example:
///
/// ```ignore
/// #[frame_support::runtime]
/// mod runtime {
/// // The main runtime
/// #[runtime::runtime]
/// // Runtime Types to be generated
/// #[runtime::derive(
/// RuntimeCall,
/// RuntimeEvent,
/// RuntimeError,
/// RuntimeOrigin,
/// RuntimeFreezeReason,
/// RuntimeHoldReason,
/// RuntimeSlashReason,
/// RuntimeLockId,
/// RuntimeTask,
/// )]
/// pub struct Runtime;
///
/// #[runtime::pallet_index(0)]
/// pub type System = frame_system;
///
/// #[runtime::pallet_index(1)]
/// pub type Test = path::to::test;
///
/// // Pallet with instance.
/// #[runtime::pallet_index(2)]
/// pub type Test2_Instance1 = test2<Instance1>;
///
/// // Pallet with calls disabled.
/// #[runtime::pallet_index(3)]
/// #[runtime::disable_call]
/// pub type Test3 = test3;
///
/// // Pallet with unsigned extrinsics disabled.
/// #[runtime::pallet_index(4)]
/// #[runtime::disable_unsigned]
/// pub type Test4 = test4;
/// }
/// ```
///
/// # Legacy Ordering
///
/// An optional attribute can be defined as #[frame_support::runtime(legacy_ordering)] to
/// ensure that the order of hooks is same as the order of pallets (and not based on the
/// pallet_index). This is to support legacy runtimes and should be avoided for new ones.
///
/// # Note
///
/// The population of the genesis storage depends on the order of pallets. So, if one of your
/// pallets depends on another pallet, the pallet that is depended upon needs to come before
/// the pallet depending on it.
///
/// # Type definitions
///
/// * The macro generates a type alias for each pallet to their `Pallet`. E.g. `type System =
/// frame_system::Pallet<Runtime>`
#[cfg(feature = "experimental")]
#[proc_macro_attribute]
pub fn runtime(attr: TokenStream, item: TokenStream) -> TokenStream {
runtime::runtime(attr, item)
}
/// Mark a module that contains dynamic parameters.
///
/// See the `pallet_parameters` for a full example.