feat(gobierno): spec 18 (RV17), quorum del voto ordinario y pago del tesoro atado a la propuesta
Gobierno (origin-chain-governance): - El voto ordinario exige un quorum de Aye, el 10 % de PILAR_4 §6.6. Se fija AL CREAR la propuesta (VoteQuorumOf) y se consume al decidirla: un set_code no mueve la meta de un voto abierto. Cuenta solo el Aye: con el Nay, un voto en contra podria aprobar; con la abstencion, el mismo OGC inflaria el quorum de muchas propuestas. - Un override del veto tiene que alcanzar ese quorum y superar el Nay original, las dos condiciones del voto ordinario. Sin ellas, vetar abarataba una aprobacion (dos bloqueantes de las revisiones adversariales). - submit_treasury_proposal (call 16) fija destinatario y monto (TreasuryActions), y treasury_disbursement solo paga exactamente eso, una vez. Rechaza montos bajo el deposito existencial y como destinatario la propia tesoreria o la cuenta-bond. - Sin entrada en VoteQuorumOf no hay quorum: la emergencia (que nunca lleva accion de tesoro) y lo creado antes de RV17, que se abrio y voto sin quorum. Runtime: los dos quorums son el 10 % de la emision VIGENTE, redondeado hacia arriba y nunca por debajo del bond (DiezPorCientoDeLaEmision). Con 100M fijos, en la testnet de la casa (100M emitidos, todos de Alice) nada se habria aprobado nunca; en mainnet sigue siendo ~100M. Spec 18, transaction_version 1: todo lo nuevo es aditivo, sin migracion. Node: pasa a opaque::Block. Decodificaba los extrinsics con tipos nativos y rechazaba en el pool la llamada que anadia el set_code (1040, el mismo error que una llamada inexistente). Los bytes y los hashes no cambian: el binario nuevo sincronizo desde cero los 39 273 bloques de la testnet de la casa con los mismos hashes en 8 alturas. El RPC sirve los extrinsics en hex. Pesos: seis extrinsics cambiaron de codigo y se midieron en la Pi 5 (smoke declarado: 5 procesos limpios, sin CI en ningun segundo, maximo de los 5). Los otros once siguen siendo los certificados por Laurha. Se descarto una medida contaminada: su muestreador no veia los tests de la CI. Pruebas: - 363 tests verdes en el workspace. - 24 contrafactuales, los 24 en rojo. - Ensayo en la rp1 sobre una cadena con el codigo vivo de spec 17: upgrade a 18 y E2E firmando como un wallet (scripts/e2e/rv17_tesoro.py). - Ejemplo firmar_como_wallet con tesoro, pagar, votar, depositar y finalizar; los eventos llevan su fase. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
1 parent
abe680e853
commit
b6d05eaf45
14 files changed
+1368
-155
No files matched your search
@@ -54,7 +54,9 @@ mod service;
|
||||
// las Command Line Tools declara la arquitectura `arm64e.x1`, que ld no reconoce.
|
||||
|
||||
use clap::{Parser, Subcommand};
|
||||
use origin_chain_runtime::{genesis_config_presets, Block, IMPL_NAME, RUNTIME_VERSION, SPEC_NAME};
|
||||
use origin_chain_runtime::{
|
||||
genesis_config_presets, opaque::Block, IMPL_NAME, RUNTIME_VERSION, SPEC_NAME,
|
||||
};
|
||||
use sc_cli::SubstrateCli;
|
||||
use sp_genesis_builder::PresetId;
|
||||
|
||||
|
||||
@@ -12,16 +12,18 @@ use crate::service::FullClient;
|
||||
|
||||
// El client es CONCRETO (`FullClient`), no un `C` genérico como en el template.
|
||||
//
|
||||
// El template puede ser genérico porque su node trabaja sobre `opaque::Block`, que no
|
||||
// menciona la cuenta. El nuestro trabaja sobre el `Block` completo del runtime (sobre
|
||||
// él están los `impl_runtime_apis!`), y ese tipo lleva dentro `ChainAccountId`, que es
|
||||
// una PROYECCIÓN: `<<MultiSignature as Verify>::Signer as IdentifyAccount>::AccountId`.
|
||||
// Dentro de un where-clause genérico rustc no la normaliza a `AccountId32`: el bound
|
||||
// `C: ProvideRuntimeApi<Block>` queda escrito con una forma del tipo y `System` lo
|
||||
// pide con la otra, y el compilador informa de que un bound declarado en la propia
|
||||
// firma «no se satisface» (6 errores, medido el 2026-09-23). Con el tipo concreto no
|
||||
// hay nada que normalizar en el param-env y los bounds se comprueban sobre el client
|
||||
// real — que es además el único que este node construye.
|
||||
// Hasta el 2026-10-28 el node trabajaba sobre el `Block` completo del runtime, y ese tipo
|
||||
// lleva dentro `ChainAccountId`, que es una PROYECCIÓN:
|
||||
// `<<MultiSignature as Verify>::Signer as IdentifyAccount>::AccountId`. Dentro de un
|
||||
// where-clause genérico rustc no la normalizaba a `AccountId32`: el bound
|
||||
// `C: ProvideRuntimeApi<Block>` quedaba escrito con una forma del tipo y `System` lo pedía
|
||||
// con la otra, y el compilador informaba de que un bound declarado en la propia firma «no
|
||||
// se satisface» (6 errores, medido el 2026-09-23). Con el tipo concreto los bounds se
|
||||
// comprueban sobre el client real, que es además el único que este node construye.
|
||||
//
|
||||
// Desde el 2026-10-28 el node trabaja sobre `opaque::Block` (ver
|
||||
// `origin_chain_runtime::opaque`: el node decodificaba las llamadas con tipos nativos y
|
||||
// rechazaba las que añadía un `set_code`). El client sigue concreto.
|
||||
|
||||
/// Dependencias completas para construir los RPC del node.
|
||||
pub struct FullDeps<P> {
|
||||
|
||||
@@ -12,11 +12,12 @@ use sc_consensus_grandpa::SharedVoterState;
|
||||
use sc_service::{error::Error as ServiceError, Configuration, TaskManager, WarpSyncConfig};
|
||||
use sc_telemetry::{Telemetry, TelemetryWorker};
|
||||
use sc_transaction_pool_api::OffchainTransactionPoolFactory;
|
||||
// El runtime implementa `impl_runtime_apis!` sobre el `Block` root (con
|
||||
// UncheckedExtrinsic), no sobre un opaque block separado → el node usa ese mismo
|
||||
// tipo para que `RuntimeApi` matchee. (El template solochain usa `opaque::Block`
|
||||
// porque su runtime expone las APIs así; el nuestro las expone sobre root Block.)
|
||||
use origin_chain_runtime::{Block, RuntimeApi};
|
||||
// El node trabaja sobre `opaque::Block`: los extrinsics son bytes y sólo el WASM los
|
||||
// decodifica. Con el `Block` completo del runtime (hasta el 2026-10-28) el node decodificaba
|
||||
// con sus tipos nativos y rechazaba toda llamada que un `set_code` hubiera añadido (ver
|
||||
// `origin_chain_runtime::opaque`). Las runtime APIs que genera `impl_runtime_apis!` son
|
||||
// genéricas en el bloque y cruzan la frontera en SCALE, así que valen igual sobre éste.
|
||||
use origin_chain_runtime::{opaque::Block, RuntimeApi};
|
||||
use sp_consensus_aura::sr25519::AuthorityPair as AuraPair;
|
||||
use std::{sync::Arc, time::Duration};
|
||||
|
||||
|
||||
Reference in new issue
Block a user