Skip to content

Commit 737e4ac

Browse files
authored
Merge pull request #1988 from opentensor/testnet
mainnet deploy 8/27/2025
2 parents 67c7ac6 + a39a7a2 commit 737e4ac

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

47 files changed

+1721
-819
lines changed

Cargo.lock

Lines changed: 1 addition & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Dockerfile-localnet

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,10 @@ COPY --from=builder /build/snapshot.json /snapshot.json
5252
COPY --from=builder /build/scripts/localnet.sh scripts/localnet.sh
5353
RUN chmod +x /scripts/localnet.sh
5454

55+
# Copy WebAssembly artifacts
56+
COPY --from=builder /build/target/fast-runtime/release/wbuild/node-subtensor-runtime/node_subtensor_runtime.compact.compressed.wasm target/fast-runtime/release/node_subtensor_runtime.compact.compressed.wasm
57+
COPY --from=builder /build/target/non-fast-runtime/release/wbuild/node-subtensor-runtime/node_subtensor_runtime.compact.compressed.wasm target/non-fast-runtime/release/node_subtensor_runtime.compact.compressed.wasm
58+
5559
## Ubdate certificates
5660
RUN apt-get update && apt-get install -y ca-certificates
5761

docs/transaction-priority.md

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
## Transaction Priority
2+
3+
### Overview
4+
In Subtensor, transaction priority is determined by custom transaction extensions, which alter or override the default Substrate SDK behavior. Extensions affecting transaction priority are:
5+
6+
- **`ChargeTransactionPaymentWrapper`** (wraps `ChargeTransactionPayment`)
7+
- **`DrandPriority`**
8+
9+
Substrate SDK combines priorities from all transaction extensions using addition.
10+
11+
---
12+
13+
### 1. `ChargeTransactionPaymentWrapper`
14+
In the Substrate SDK, `ChargeTransactionPayment` normally calculates transaction priority based on:
15+
- **Tip** — an extra fee paid by the sender.
16+
- **Weight** — computational complexity of the transaction.
17+
- **Dispatch class** — category of the transaction (`Normal`, `Operational`, `Mandatory`).
18+
19+
However, in Subtensor, `ChargeTransactionPaymentWrapper` **overrides** this logic.
20+
It replaces the dynamic calculation with a **flat priority scale** based only on the dispatch class.
21+
22+
#### Current priority values:
23+
| Dispatch Class | Priority Value | Notes |
24+
|---------------------|-------------------|--------------------------------------------------------------|
25+
| `Normal` | `1` | Standard transactions |
26+
| `Mandatory` | `1` | Rarely used, same as `Normal` |
27+
| `Operational` | `10_000_000_000` | Reserved for critical system extrinsics (e.g.: `sudo` calls) |
28+
29+
30+
---
31+
32+
### 2. `DrandPriority`
33+
34+
Special pallet_drand priority: 10_000 for `write_pulse` extrinsic.
35+
36+
---

evm-tests/src/substrate.ts

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -168,30 +168,31 @@ export async function waitForTransactionCompletion(api: TypedApi<typeof devnet>,
168168
// })
169169
}
170170

171+
171172
export async function getTransactionWatchPromise(tx: Transaction<{}, string, string, void>, signer: PolkadotSigner,) {
172173
return new Promise<void>((resolve, reject) => {
173174
// store the txHash, then use it in timeout. easier to know which tx is not finalized in time
174175
let txHash = ""
175176
const subscription = tx.signSubmitAndWatch(signer).subscribe({
176177
next(value) {
177-
console.log("Event:", value);
178178
txHash = value.txHash
179179

180180
// TODO investigate why finalized not for each extrinsic
181181
if (value.type === "finalized") {
182182
console.log("Transaction is finalized in block:", value.txHash);
183183
subscription.unsubscribe();
184+
clearTimeout(timeoutId);
184185
if (!value.ok) {
185186
console.log("Transaction threw an error:", value.dispatchError)
186187
}
187188
// Resolve the promise when the transaction is finalized
188189
resolve();
189-
190190
}
191191
},
192192
error(err) {
193193
console.error("Transaction failed:", err);
194194
subscription.unsubscribe();
195+
clearTimeout(timeoutId);
195196
// Reject the promise in case of an error
196197
reject(err);
197198

@@ -201,7 +202,7 @@ export async function getTransactionWatchPromise(tx: Transaction<{}, string, str
201202
}
202203
});
203204

204-
setTimeout(() => {
205+
const timeoutId = setTimeout(() => {
205206
subscription.unsubscribe();
206207
console.log('unsubscribed because of timeout for tx {}', txHash);
207208
reject()

evm-tests/src/subtensor.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,7 @@ export async function addNewSubnetwork(api: TypedApi<typeof devnet>, hotkey: Key
3232
// force set balance for a ss58 address
3333
export async function forceSetBalanceToSs58Address(api: TypedApi<typeof devnet>, ss58Address: string) {
3434
const alice = getAliceSigner()
35-
const balance = tao(1e8)
35+
const balance = tao(1e10)
3636
const internalCall = api.tx.Balances.force_set_balance({ who: MultiAddress.Id(ss58Address), new_free: balance })
3737
const tx = api.tx.Sudo.sudo({ call: internalCall.decodedCall })
3838

evm-tests/test/neuron.precompile.reveal-weights.test.ts

Lines changed: 27 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -11,9 +11,9 @@ import { generateRandomEthersWallet } from "../src/utils"
1111
import { convertH160ToPublicKey } from "../src/address-utils"
1212
import { blake2AsU8a } from "@polkadot/util-crypto"
1313
import {
14-
forceSetBalanceToEthAddress, forceSetBalanceToSs58Address, addNewSubnetwork, setCommitRevealWeightsEnabled, setWeightsSetRateLimit, burnedRegister,
14+
forceSetBalanceToEthAddress, forceSetBalanceToSs58Address, addNewSubnetwork, setWeightsSetRateLimit, burnedRegister,
1515
setTempo, setCommitRevealWeightsInterval,
16-
startCall
16+
startCall,
1717
} from "../src/subtensor"
1818

1919
// hardcode some values for reveal hash
@@ -52,6 +52,7 @@ describe("Test neuron precompile reveal weights", () => {
5252
const coldkey = getRandomSubstrateKeypair();
5353

5454
let api: TypedApi<typeof devnet>
55+
let commitEpoch: number;
5556

5657
// sudo account alice as signer
5758
let alice: PolkadotSigner;
@@ -65,13 +66,11 @@ describe("Test neuron precompile reveal weights", () => {
6566
await forceSetBalanceToSs58Address(api, convertPublicKeyToSs58(coldkey.publicKey))
6667
await forceSetBalanceToEthAddress(api, wallet.address)
6768
let netuid = await addNewSubnetwork(api, hotkey, coldkey)
69+
// await disableCommitRevealWeights(api, netuid)
6870
await startCall(api, netuid, coldkey)
6971

7072
console.log("test the case on subnet ", netuid)
7173

72-
// enable commit reveal feature
73-
await setCommitRevealWeightsEnabled(api, netuid, true)
74-
// set it as 0, we can set the weight anytime
7574
await setWeightsSetRateLimit(api, netuid, BigInt(0))
7675

7776
const ss58Address = convertH160ToSS58(wallet.address)
@@ -90,8 +89,15 @@ describe("Test neuron precompile reveal weights", () => {
9089
const subnetId = totalNetworks - 1
9190
const commitHash = getCommitHash(subnetId, wallet.address)
9291
const contract = new ethers.Contract(INEURON_ADDRESS, INeuronABI, wallet);
93-
const tx = await contract.commitWeights(subnetId, commitHash)
94-
await tx.wait()
92+
try {
93+
const tx = await contract.commitWeights(subnetId, commitHash)
94+
await tx.wait()
95+
} catch (e) {
96+
console.log("commitWeights failed", e)
97+
}
98+
99+
const commitBlock = await api.query.System.Number.getValue()
100+
commitEpoch = Math.trunc(commitBlock / (100 + 1))
95101

96102
const ss58Address = convertH160ToSS58(wallet.address)
97103

@@ -108,9 +114,19 @@ describe("Test neuron precompile reveal weights", () => {
108114
const netuid = totalNetworks - 1
109115
const contract = new ethers.Contract(INEURON_ADDRESS, INeuronABI, wallet);
110116
// set tempo or epoch large, then enough time to reveal weight
111-
await setTempo(api, netuid, 60000)
112-
// set interval epoch as 0, we can reveal at the same epoch
113-
await setCommitRevealWeightsInterval(api, netuid, BigInt(0))
117+
await setTempo(api, netuid, 100)
118+
// set interval epoch as 1, it is the minimum value now
119+
await setCommitRevealWeightsInterval(api, netuid, BigInt(1))
120+
121+
while (true) {
122+
const currentBlock = await api.query.System.Number.getValue()
123+
const currentEpoch = Math.trunc(currentBlock / (100 + 1))
124+
// wait for one second for fast blocks
125+
if (currentEpoch > commitEpoch) {
126+
break
127+
}
128+
await new Promise(resolve => setTimeout(resolve, 1000))
129+
}
114130

115131
const tx = await contract.revealWeights(
116132
netuid,
@@ -120,6 +136,7 @@ describe("Test neuron precompile reveal weights", () => {
120136
version_key
121137
);
122138
await tx.wait()
139+
123140
const ss58Address = convertH160ToSS58(wallet.address)
124141

125142
// check the weight commit is removed after reveal successfully

node/src/benchmarking.rs

Lines changed: 23 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,8 @@
55
use crate::client::FullClient;
66

77
use node_subtensor_runtime as runtime;
8-
use node_subtensor_runtime::check_nonce;
98
use node_subtensor_runtime::pallet_subtensor;
9+
use node_subtensor_runtime::{check_nonce, transaction_payment_wrapper};
1010
use runtime::{BalancesCall, SystemCall};
1111
use sc_cli::Result;
1212
use sc_client_api::BlockBackend;
@@ -123,21 +123,27 @@ pub fn create_benchmark_extrinsic(
123123
.checked_next_power_of_two()
124124
.map(|c| c / 2)
125125
.unwrap_or(2) as u64;
126-
let extra: runtime::TransactionExtensions = (
127-
frame_system::CheckNonZeroSender::<runtime::Runtime>::new(),
128-
frame_system::CheckSpecVersion::<runtime::Runtime>::new(),
129-
frame_system::CheckTxVersion::<runtime::Runtime>::new(),
130-
frame_system::CheckGenesis::<runtime::Runtime>::new(),
131-
frame_system::CheckEra::<runtime::Runtime>::from(sp_runtime::generic::Era::mortal(
132-
period,
133-
best_block.saturated_into(),
134-
)),
135-
check_nonce::CheckNonce::<runtime::Runtime>::from(nonce),
136-
frame_system::CheckWeight::<runtime::Runtime>::new(),
137-
pallet_transaction_payment::ChargeTransactionPayment::<runtime::Runtime>::from(0),
138-
pallet_subtensor::SubtensorTransactionExtension::<runtime::Runtime>::new(),
139-
frame_metadata_hash_extension::CheckMetadataHash::<runtime::Runtime>::new(true),
140-
);
126+
let extra: runtime::TransactionExtensions =
127+
(
128+
frame_system::CheckNonZeroSender::<runtime::Runtime>::new(),
129+
frame_system::CheckSpecVersion::<runtime::Runtime>::new(),
130+
frame_system::CheckTxVersion::<runtime::Runtime>::new(),
131+
frame_system::CheckGenesis::<runtime::Runtime>::new(),
132+
frame_system::CheckEra::<runtime::Runtime>::from(sp_runtime::generic::Era::mortal(
133+
period,
134+
best_block.saturated_into(),
135+
)),
136+
check_nonce::CheckNonce::<runtime::Runtime>::from(nonce),
137+
frame_system::CheckWeight::<runtime::Runtime>::new(),
138+
transaction_payment_wrapper::ChargeTransactionPaymentWrapper::new(
139+
pallet_transaction_payment::ChargeTransactionPayment::<runtime::Runtime>::from(0),
140+
),
141+
pallet_subtensor::transaction_extension::SubtensorTransactionExtension::<
142+
runtime::Runtime,
143+
>::new(),
144+
pallet_drand::drand_priority::DrandPriority::<runtime::Runtime>::new(),
145+
frame_metadata_hash_extension::CheckMetadataHash::<runtime::Runtime>::new(true),
146+
);
141147

142148
let raw_payload = runtime::SignedPayload::from_raw(
143149
call.clone(),
@@ -152,6 +158,7 @@ pub fn create_benchmark_extrinsic(
152158
(),
153159
(),
154160
(),
161+
(),
155162
None,
156163
),
157164
);

node/src/command.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -318,14 +318,14 @@ fn customise_config(arg_matches: &ArgMatches, config: Configuration) -> Configur
318318

319319
// If the operator did **not** supply `--rpc-max-subscriptions-per-connection` set to high value.
320320
config.rpc.max_subs_per_conn = match arg_matches
321-
.value_source("rpc-max-subscriptions-per-connection")
321+
.value_source("rpc_max_subscriptions_per_connection")
322322
{
323323
Some(ValueSource::CommandLine) => cli.run.rpc_params.rpc_max_subscriptions_per_connection,
324324
_ => 10000,
325325
};
326326

327327
// If the operator did **not** supply `--rpc-max-connections` set to high value.
328-
config.rpc.max_connections = match arg_matches.value_source("rpc-max-connections") {
328+
config.rpc.max_connections = match arg_matches.value_source("rpc_max_connections") {
329329
Some(ValueSource::CommandLine) => cli.run.rpc_params.rpc_max_connections,
330330
_ => 10000,
331331
};

pallets/admin-utils/src/lib.rs

Lines changed: 18 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -107,8 +107,6 @@ pub mod pallet {
107107
BondsMovingAverageMaxReached,
108108
/// Only root can set negative sigmoid steepness values
109109
NegativeSigmoidSteepness,
110-
/// Reveal Peroid is not within the valid range.
111-
RevealPeriodOutOfBounds,
112110
}
113111
/// Enum for specifying the type of precompile operation.
114112
#[derive(
@@ -1311,14 +1309,10 @@ pub mod pallet {
13111309
Error::<T>::SubnetDoesNotExist
13121310
);
13131311

1314-
const MAX_COMMIT_REVEAL_PEROIDS: u64 = 100;
1315-
ensure!(
1316-
interval <= MAX_COMMIT_REVEAL_PEROIDS,
1317-
Error::<T>::RevealPeriodOutOfBounds
1318-
);
1319-
1320-
pallet_subtensor::Pallet::<T>::set_reveal_period(netuid, interval);
13211312
log::debug!("SetWeightCommitInterval( netuid: {netuid:?}, interval: {interval:?} ) ");
1313+
1314+
pallet_subtensor::Pallet::<T>::set_reveal_period(netuid, interval)?;
1315+
13221316
Ok(())
13231317
}
13241318

@@ -1673,6 +1667,21 @@ pub mod pallet {
16731667
pallet_subtensor::Pallet::<T>::set_commit_reveal_weights_version(version);
16741668
Ok(())
16751669
}
1670+
1671+
/// Sets the number of immune owner neurons
1672+
#[pallet::call_index(72)]
1673+
#[pallet::weight(Weight::from_parts(15_000_000, 0)
1674+
.saturating_add(<T as frame_system::Config>::DbWeight::get().reads(1_u64))
1675+
.saturating_add(<T as frame_system::Config>::DbWeight::get().writes(1_u64)))]
1676+
pub fn sudo_set_owner_immune_neuron_limit(
1677+
origin: OriginFor<T>,
1678+
netuid: NetUid,
1679+
immune_neurons: u16,
1680+
) -> DispatchResult {
1681+
pallet_subtensor::Pallet::<T>::ensure_subnet_owner_or_root(origin, netuid)?;
1682+
pallet_subtensor::Pallet::<T>::set_owner_immune_neuron_limit(netuid, immune_neurons)?;
1683+
Ok(())
1684+
}
16761685
}
16771686
}
16781687

0 commit comments

Comments
 (0)