From 568a276b7f4fba49e55f54159d10ecf039e8bebb Mon Sep 17 00:00:00 2001
From: "hinto.janai" <hinto.janai@protonmail.com>
Date: Thu, 5 Dec 2024 20:45:27 -0500
Subject: [PATCH] `rpc-types` -> `types` pt. 2

---
 Cargo.lock                                   |   4 +
 binaries/cuprated/src/rpc/bin.rs             |   2 +-
 binaries/cuprated/src/rpc/helper.rs          |  20 +-
 binaries/cuprated/src/rpc/json.rs            |  66 +-
 binaries/cuprated/src/rpc/other.rs           |   3 +-
 binaries/cuprated/src/rpc/request/txpool.rs  |   5 +-
 rpc/types/Cargo.toml                         |  10 +-
 rpc/types/src/base.rs                        |   6 +-
 rpc/types/src/bin.rs                         |   7 +-
 rpc/types/src/constants.rs                   |  14 +-
 rpc/types/src/from.rs                        | 518 ++++++---------
 rpc/types/src/json.rs                        |   7 +-
 rpc/types/src/lib.rs                         |   1 +
 rpc/types/src/macros.rs                      |   4 +-
 rpc/types/src/misc/distribution.rs           |   6 +-
 rpc/types/src/misc/key_image_spent_status.rs |   2 +-
 rpc/types/src/misc/mod.rs                    |   6 +-
 rpc/types/src/misc/requested_info.rs         |   2 +-
 rpc/types/src/misc/tx_entry.rs               |   2 +-
 rpc/types/src/misc/types.rs                  | 242 +------
 rpc/types/src/other.rs                       |   7 +-
 storage/txpool/Cargo.toml                    |   2 +-
 storage/txpool/src/service/interface.rs      |   2 +-
 types/Cargo.toml                             |   8 +-
 types/src/hard_fork.rs                       |  24 +
 types/src/hex.rs                             |  12 +-
 types/src/json/block.rs                      |  58 +-
 types/src/json/output.rs                     |  10 +-
 types/src/json/tx.rs                         | 641 ++++++++++---------
 types/src/lib.rs                             |  12 +-
 types/src/rpc/mod.rs                         |  24 +
 types/src/{ => rpc}/pool_info.rs             |   2 +-
 types/src/{ => rpc}/pool_info_extent.rs      |   0
 types/src/{rpc.rs => rpc/types.rs}           |  49 +-
 zmq/types/src/json_message_types.rs          |  58 +-
 35 files changed, 797 insertions(+), 1039 deletions(-)
 create mode 100644 types/src/rpc/mod.rs
 rename types/src/{ => rpc}/pool_info.rs (99%)
 rename types/src/{ => rpc}/pool_info_extent.rs (100%)
 rename types/src/{rpc.rs => rpc/types.rs} (92%)

diff --git a/Cargo.lock b/Cargo.lock
index 864d4b5a..19972672 100644
--- a/Cargo.lock
+++ b/Cargo.lock
@@ -1067,8 +1067,11 @@ version = "0.0.0"
 dependencies = [
  "cuprate-epee-encoding",
  "cuprate-fixed-bytes",
+ "cuprate-helper",
+ "cuprate-p2p-core",
  "cuprate-test-utils",
  "cuprate-types",
+ "hex",
  "paste",
  "serde",
  "serde_json",
@@ -1127,6 +1130,7 @@ name = "cuprate-types"
 version = "0.0.0"
 dependencies = [
  "bytes",
+ "cfg-if",
  "cuprate-epee-encoding",
  "cuprate-fixed-bytes",
  "cuprate-helper",
diff --git a/binaries/cuprated/src/rpc/bin.rs b/binaries/cuprated/src/rpc/bin.rs
index d1b8f22f..c07cca82 100644
--- a/binaries/cuprated/src/rpc/bin.rs
+++ b/binaries/cuprated/src/rpc/bin.rs
@@ -15,7 +15,7 @@ use cuprate_rpc_types::{
     json::{GetOutputDistributionRequest, GetOutputDistributionResponse},
     misc::RequestedInfo,
 };
-use cuprate_types::{BlockCompleteEntry, PoolInfoExtent};
+use cuprate_types::{rpc::PoolInfoExtent, BlockCompleteEntry};
 
 use crate::rpc::{helper, request::blockchain, CupratedRpcHandler};
 
diff --git a/binaries/cuprated/src/rpc/helper.rs b/binaries/cuprated/src/rpc/helper.rs
index 8f7c671a..cf5bbc49 100644
--- a/binaries/cuprated/src/rpc/helper.rs
+++ b/binaries/cuprated/src/rpc/helper.rs
@@ -65,9 +65,9 @@ pub(super) async fn block_header(
         )
         .await?;
 
-        hex::encode(pow_hash)
+        pow_hash
     } else {
-        String::new()
+        [0; 32]
     };
 
     let block_weight = usize_to_u64(header.block_weight);
@@ -86,30 +86,28 @@ pub(super) async fn block_header(
         .map(|o| o.amount.expect("coinbase is transparent"))
         .sum::<u64>();
 
-    Ok(BlockHeader {
-        block_size: block_weight,
+    Ok(cuprate_types::rpc::BlockHeader {
         block_weight,
         cumulative_difficulty_top64,
         cumulative_difficulty,
         depth,
         difficulty_top64,
         difficulty,
-        hash: hex::encode(block.hash()),
+        hash: block.hash(),
         height,
         long_term_weight: usize_to_u64(header.long_term_weight),
-        major_version: header.version.as_u8(),
-        miner_tx_hash: hex::encode(block.miner_transaction.hash()),
+        major_version: header.version,
+        miner_tx_hash: block.miner_transaction.hash(),
         minor_version: header.vote,
         nonce: block.header.nonce,
         num_txes: usize_to_u64(block.transactions.len()),
         orphan_status,
         pow_hash,
-        prev_hash: hex::encode(block.header.previous),
+        prev_hash: block.header.previous,
         reward,
         timestamp: block.header.timestamp,
-        wide_cumulative_difficulty: hex::encode(u128::to_le_bytes(header.cumulative_difficulty)),
-        wide_difficulty,
-    })
+    }
+    .into())
 }
 
 /// Same as [`block_header`] but with the block's hash.
diff --git a/binaries/cuprated/src/rpc/json.rs b/binaries/cuprated/src/rpc/json.rs
index d82235ea..7ee16387 100644
--- a/binaries/cuprated/src/rpc/json.rs
+++ b/binaries/cuprated/src/rpc/json.rs
@@ -47,13 +47,13 @@ use cuprate_rpc_types::{
         SetBansRequest, SetBansResponse, SubmitBlockRequest, SubmitBlockResponse, SyncInfoRequest,
         SyncInfoResponse,
     },
-    misc::{
-        AuxPow, BlockHeader, ChainInfo, Distribution, GetBan, GetMinerDataTxBacklogEntry,
-        HardforkEntry, HistogramEntry, Status, SyncInfoPeer, TxBacklogEntry,
-    },
+    misc::{BlockHeader, ChainInfo, Distribution, GetBan, HistogramEntry, Status, SyncInfoPeer},
     CORE_RPC_VERSION,
 };
-use cuprate_types::HardFork;
+use cuprate_types::{
+    rpc::{AuxPow, CoinbaseTxSum, GetMinerDataTxBacklogEntry, HardforkEntry, TxBacklogEntry},
+    HardFork,
+};
 
 use crate::{
     constants::VERSION_BUILD,
@@ -699,17 +699,17 @@ async fn get_coinbase_tx_sum(
     mut state: CupratedRpcHandler,
     request: GetCoinbaseTxSumRequest,
 ) -> Result<GetCoinbaseTxSumResponse, Error> {
-    let sum =
-        blockchain::coinbase_tx_sum(&mut state.blockchain_read, request.height, request.count)
-            .await?;
+    let CoinbaseTxSum {
+        emission_amount_top64,
+        emission_amount,
+        fee_amount_top64,
+        fee_amount,
+    } = blockchain::coinbase_tx_sum(&mut state.blockchain_read, request.height, request.count)
+        .await?;
 
     // Formats `u128` as hexadecimal strings.
-    let wide_emission_amount = format!("{:#x}", sum.fee_amount);
-    let wide_fee_amount = format!("{:#x}", sum.emission_amount);
-
-    let (emission_amount, emission_amount_top64) =
-        split_u128_into_low_high_bits(sum.emission_amount);
-    let (fee_amount, fee_amount_top64) = split_u128_into_low_high_bits(sum.fee_amount);
+    let wide_emission_amount = format!("{fee_amount:#x}");
+    let wide_fee_amount = format!("{emission_amount:#x}");
 
     Ok(GetCoinbaseTxSumResponse {
         base: AccessResponseBase::OK,
@@ -738,7 +738,8 @@ async fn get_version(
         {
             let entry = HardforkEntry {
                 height: hf.earliest_height,
-                hf_version: hf.version,
+                hf_version: HardFork::from_version(hf.version)
+                    .expect("blockchain context should not be responding with invalid hardforks"),
             };
 
             hard_forks.push(entry);
@@ -780,21 +781,7 @@ async fn get_alternate_chains(
     let chains = blockchain::alt_chains(&mut state.blockchain_read)
         .await?
         .into_iter()
-        .map(|info| {
-            let block_hashes = info.block_hashes.into_iter().map(hex::encode).collect();
-            let (difficulty, difficulty_top64) = split_u128_into_low_high_bits(info.difficulty);
-
-            ChainInfo {
-                block_hash: hex::encode(info.block_hash),
-                block_hashes,
-                difficulty,
-                difficulty_top64,
-                height: info.height,
-                length: info.length,
-                main_chain_parent_block: hex::encode(info.main_chain_parent_block),
-                wide_difficulty: hex::encode(u128::to_ne_bytes(info.difficulty)),
-            }
-        })
+        .map(Into::into)
         .collect();
 
     Ok(GetAlternateChainsResponse {
@@ -1036,19 +1023,11 @@ fn add_aux_pow_inner(
         return Err(anyhow!("Empty `aux_pow` vector"));
     };
 
-    let aux_pow = request
-        .aux_pow
-        .into_iter()
-        .map(|aux| {
-            let id = helper::hex_to_hash(aux.id)?;
-            let hash = helper::hex_to_hash(aux.hash)?;
-            Ok(cuprate_types::rpc::AuxPow { id, hash })
-        })
-        .collect::<Result<Box<[_]>, Error>>()?;
     // Some of the code below requires that the
     // `.len()` of certain containers are the same.
     // Boxed slices are used over `Vec` to slightly
     // safe-guard against accidently pushing to it.
+    let aux_pow = request.aux_pow.into_boxed_slice();
 
     // TODO: why is this here? it does nothing:
     // <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L2110-L2112>
@@ -1058,7 +1037,7 @@ fn add_aux_pow_inner(
     // }
 
     fn find_nonce(
-        aux_pow: &[cuprate_types::rpc::AuxPow],
+        aux_pow: &[AuxPow],
         non_zero_len: NonZero<usize>,
         aux_pow_len: usize,
     ) -> Result<(u32, Box<[u32]>), Error> {
@@ -1219,11 +1198,8 @@ fn add_aux_pow_inner(
     let blockhashing_blob = hex::encode(blockhashing_blob);
     let merkle_root = hex::encode(merkle_root);
     let aux_pow = IntoIterator::into_iter(aux_pow) // must be explicit due to `boxed_slice_into_iter`
-        .map(|aux| AuxPow {
-            id: hex::encode(aux.id),
-            hash: hex::encode(aux.hash),
-        })
-        .collect::<Vec<AuxPow>>();
+        .map(Into::into)
+        .collect::<Vec<cuprate_rpc_types::misc::AuxPow>>();
 
     Ok(AddAuxPowResponse {
         base: ResponseBase::OK,
diff --git a/binaries/cuprated/src/rpc/other.rs b/binaries/cuprated/src/rpc/other.rs
index 00ee0c7e..ca23190c 100644
--- a/binaries/cuprated/src/rpc/other.rs
+++ b/binaries/cuprated/src/rpc/other.rs
@@ -11,7 +11,7 @@ use cuprate_helper::cast::usize_to_u64;
 use cuprate_rpc_interface::RpcHandler;
 use cuprate_rpc_types::{
     base::{AccessResponseBase, ResponseBase},
-    misc::{KeyImageSpentStatus, OutKey, Status},
+    misc::{KeyImageSpentStatus, Status},
     other::{
         GetAltBlocksHashesRequest, GetAltBlocksHashesResponse, GetHeightRequest, GetHeightResponse,
         GetLimitRequest, GetLimitResponse, GetNetStatsRequest, GetNetStatsResponse, GetOutsRequest,
@@ -30,6 +30,7 @@ use cuprate_rpc_types::{
         UpdateRequest, UpdateResponse,
     },
 };
+use cuprate_types::rpc::OutKey;
 
 use crate::{
     rpc::CupratedRpcHandler,
diff --git a/binaries/cuprated/src/rpc/request/txpool.rs b/binaries/cuprated/src/rpc/request/txpool.rs
index 91a9f7d4..0b8add64 100644
--- a/binaries/cuprated/src/rpc/request/txpool.rs
+++ b/binaries/cuprated/src/rpc/request/txpool.rs
@@ -13,10 +13,7 @@ use cuprate_txpool::{
     },
     TxEntry,
 };
-use cuprate_types::{
-    rpc::{PoolInfoFull, PoolInfoIncremental, PoolTxInfo},
-    PoolInfo,
-};
+use cuprate_types::rpc::{PoolInfo, PoolInfoFull, PoolInfoIncremental, PoolTxInfo};
 
 // FIXME: use `anyhow::Error` over `tower::BoxError` in txpool.
 
diff --git a/rpc/types/Cargo.toml b/rpc/types/Cargo.toml
index 6d8797b2..1f4e62bc 100644
--- a/rpc/types/Cargo.toml
+++ b/rpc/types/Cargo.toml
@@ -9,17 +9,21 @@ repository  = "https://github.com/Cuprate/cuprate/tree/main/rpc/types"
 keywords    = ["cuprate", "rpc", "types", "monero"]
 
 [features]
-default = ["serde", "epee"]
+default = ["serde", "epee", "from"]
 serde   = ["dep:serde", "cuprate-fixed-bytes/serde", "cuprate-types/serde"]
 epee    = ["dep:cuprate-epee-encoding", "cuprate-types/epee"]
+from    = ["dep:cuprate-helper", "cuprate-helper/map", "dep:cuprate-p2p-core", "dep:hex"]
 
 [dependencies]
 cuprate-epee-encoding = { workspace = true, optional = true }
 cuprate-fixed-bytes   = { workspace = true }
 cuprate-types         = { workspace = true, default-features = false }
+cuprate-helper        = { workspace = true, optional = true, default-features = false }
+cuprate-p2p-core      = { workspace = true, optional = true, default-features = false }
 
-paste = { workspace = true }
-serde = { workspace = true, optional = true }
+paste      = { workspace = true }
+serde      = { workspace = true, optional = true }
+hex        = { workspace = true, optional = true }
 
 [dev-dependencies]
 cuprate-test-utils = { workspace = true }
diff --git a/rpc/types/src/base.rs b/rpc/types/src/base.rs
index 89eafc5b..1793cfaa 100644
--- a/rpc/types/src/base.rs
+++ b/rpc/types/src/base.rs
@@ -29,7 +29,7 @@ use crate::{macros::monero_definition_link, misc::Status};
 //---------------------------------------------------------------------------------------------------- Requests
 /// A base for RPC request types that support RPC payment.
 ///
-#[doc = monero_definition_link!(cc73fe71162d564ffda8e549b79a350bca53c454, "rpc/core_rpc_server_commands_defs.h", 114..=122)]
+#[doc = monero_definition_link!("cc73fe71162d564ffda8e549b79a350bca53c454", "rpc/core_rpc_server_commands_defs.h", 114..=122)]
 #[derive(Clone, Debug, Default, PartialEq, Eq, PartialOrd, Ord, Hash)]
 #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
 pub struct AccessRequestBase {
@@ -44,7 +44,7 @@ epee_object! {
 }
 
 //---------------------------------------------------------------------------------------------------- Responses
-#[doc = monero_definition_link!(cc73fe71162d564ffda8e549b79a350bca53c454, "rpc/core_rpc_server_commands_defs.h", 101..=112)]
+#[doc = monero_definition_link!("cc73fe71162d564ffda8e549b79a350bca53c454", "rpc/core_rpc_server_commands_defs.h", 101..=112)]
 /// The most common base for responses.
 #[derive(Clone, Debug, Default, PartialEq, Eq, PartialOrd, Ord, Hash)]
 #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
@@ -98,7 +98,7 @@ epee_object! {
     untrusted: bool,
 }
 
-#[doc = monero_definition_link!(cc73fe71162d564ffda8e549b79a350bca53c454, "rpc/core_rpc_server_commands_defs.h", 124..=136)]
+#[doc = monero_definition_link!("cc73fe71162d564ffda8e549b79a350bca53c454", "rpc/core_rpc_server_commands_defs.h", 124..=136)]
 /// A base for RPC response types that support RPC payment.
 #[derive(Clone, Debug, Default, PartialEq, Eq, PartialOrd, Ord, Hash)]
 #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
diff --git a/rpc/types/src/bin.rs b/rpc/types/src/bin.rs
index d3ff68f0..295bee70 100644
--- a/rpc/types/src/bin.rs
+++ b/rpc/types/src/bin.rs
@@ -11,12 +11,15 @@ use serde::{Deserialize, Serialize};
 #[cfg(feature = "epee")]
 use cuprate_epee_encoding::container_as_blob::ContainerAsBlob;
 
-use cuprate_types::{BlockCompleteEntry, PoolInfo};
+use cuprate_types::{
+    rpc::{BlockOutputIndices, PoolInfo},
+    BlockCompleteEntry,
+};
 
 use crate::{
     base::AccessResponseBase,
     macros::define_request_and_response,
-    misc::{BlockOutputIndices, GetOutputsOut, OutKeyBin},
+    misc::{GetOutputsOut, OutKeyBin},
     rpc_call::RpcCallValue,
 };
 
diff --git a/rpc/types/src/constants.rs b/rpc/types/src/constants.rs
index 8c6120ba..a6a68c32 100644
--- a/rpc/types/src/constants.rs
+++ b/rpc/types/src/constants.rs
@@ -24,28 +24,28 @@ use crate::macros::monero_definition_link;
 // Note that these are _distinct_ from the ones in ZMQ:
 // <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/message.cpp#L40-L44>.
 
-#[doc = monero_definition_link!(cc73fe71162d564ffda8e549b79a350bca53c454, "/rpc/core_rpc_server_commands_defs.h", 78)]
+#[doc = monero_definition_link!("cc73fe71162d564ffda8e549b79a350bca53c454", "/rpc/core_rpc_server_commands_defs.h", 78)]
 pub const CORE_RPC_STATUS_OK: &str = "OK";
 
-#[doc = monero_definition_link!(cc73fe71162d564ffda8e549b79a350bca53c454, "/rpc/core_rpc_server_commands_defs.h", 79)]
+#[doc = monero_definition_link!("cc73fe71162d564ffda8e549b79a350bca53c454", "/rpc/core_rpc_server_commands_defs.h", 79)]
 pub const CORE_RPC_STATUS_BUSY: &str = "BUSY";
 
-#[doc = monero_definition_link!(cc73fe71162d564ffda8e549b79a350bca53c454, "/rpc/core_rpc_server_commands_defs.h", 80)]
+#[doc = monero_definition_link!("cc73fe71162d564ffda8e549b79a350bca53c454", "/rpc/core_rpc_server_commands_defs.h", 80)]
 pub const CORE_RPC_STATUS_NOT_MINING: &str = "NOT MINING";
 
-#[doc = monero_definition_link!(cc73fe71162d564ffda8e549b79a350bca53c454, "/rpc/core_rpc_server_commands_defs.h", 81)]
+#[doc = monero_definition_link!("cc73fe71162d564ffda8e549b79a350bca53c454", "/rpc/core_rpc_server_commands_defs.h", 81)]
 pub const CORE_RPC_STATUS_PAYMENT_REQUIRED: &str = "PAYMENT REQUIRED";
 
 //---------------------------------------------------------------------------------------------------- Versions
-#[doc = monero_definition_link!(cc73fe71162d564ffda8e549b79a350bca53c454, "/rpc/core_rpc_server_commands_defs.h", 90)]
+#[doc = monero_definition_link!("cc73fe71162d564ffda8e549b79a350bca53c454", "/rpc/core_rpc_server_commands_defs.h", 90)]
 /// RPC major version.
 pub const CORE_RPC_VERSION_MAJOR: u32 = 3;
 
-#[doc = monero_definition_link!(cc73fe71162d564ffda8e549b79a350bca53c454, "/rpc/core_rpc_server_commands_defs.h", 91)]
+#[doc = monero_definition_link!("cc73fe71162d564ffda8e549b79a350bca53c454", "/rpc/core_rpc_server_commands_defs.h", 91)]
 /// RPC miror version.
 pub const CORE_RPC_VERSION_MINOR: u32 = 14;
 
-#[doc = monero_definition_link!(cc73fe71162d564ffda8e549b79a350bca53c454, "/rpc/core_rpc_server_commands_defs.h", 92..=93)]
+#[doc = monero_definition_link!("cc73fe71162d564ffda8e549b79a350bca53c454", "/rpc/core_rpc_server_commands_defs.h", 92..=93)]
 /// RPC version.
 pub const CORE_RPC_VERSION: u32 = (CORE_RPC_VERSION_MAJOR << 16) | CORE_RPC_VERSION_MINOR;
 
diff --git a/rpc/types/src/from.rs b/rpc/types/src/from.rs
index cc86876b..6d8ceec5 100644
--- a/rpc/types/src/from.rs
+++ b/rpc/types/src/from.rs
@@ -1,380 +1,230 @@
 //! [`From`] implementations from other crate's types into [`crate`] types.
+//!
+//! Only non-crate types are imported, all crate types use `crate::`.
 
 #![allow(unused_variables, unreachable_code, reason = "TODO")]
 
-use cuprate_types::rpc::{
-    AuxPow, BlockHeader, BlockOutputIndices, ChainInfo, ConnectionInfo, GetBan,
-    GetMinerDataTxBacklogEntry, GetOutputsOut, HardforkEntry, HistogramEntry, OutKey, OutKeyBin,
-    OutputDistributionData, Peer, PublicNode, SetBan, Span, SpentKeyImageInfo, SyncInfoPeer,
-    TxBacklogEntry, TxInfo, TxOutputIndices, TxpoolHisto, TxpoolStats,
+use std::{
+    net::{Ipv4Addr, SocketAddr, SocketAddrV4},
+    time::Duration,
 };
 
+use cuprate_helper::map::combine_low_high_bits_to_u128;
+use cuprate_p2p_core::{
+    types::{BanState, ConnectionId, ConnectionInfo, SetBan, Span},
+    ClearNet, NetZoneAddress, NetworkZone,
+};
+use cuprate_types::{
+    hex::Hex,
+    rpc::{
+        AuxPow, BlockHeader, BlockOutputIndices, ChainInfo, GetBan, GetMinerDataTxBacklogEntry,
+        GetOutputsOut, HardforkEntry, HistogramEntry, OutKey, OutKeyBin, OutputDistributionData,
+        Peer, PublicNode, SpentKeyImageInfo, TxBacklogEntry, TxInfo, TxOutputIndices, TxpoolHisto,
+        TxpoolStats,
+    },
+};
+
+/// <https://architecture.cuprate.org/oddities/le-ipv4.html>
+const fn ipv4_from_u32(ip: u32) -> Ipv4Addr {
+    let [a, b, c, d] = ip.to_le_bytes();
+    Ipv4Addr::new(a, b, c, d)
+}
+
+/// Format two [`u64`]'s as a [`u128`] as a hexadecimal string prefixed with `0x`.
+fn hex_prefix_u128(low: u64, high: u64) -> String {
+    format!("{:#x}", combine_low_high_bits_to_u128(low, high))
+}
+
 impl From<BlockHeader> for crate::misc::BlockHeader {
     fn from(x: BlockHeader) -> Self {
-        todo!();
-
-        // Self {
-        // 	block_size: u64,
-        // 	block_weight: u64,
-        // 	cumulative_difficulty_top64: u64,
-        // 	cumulative_difficulty: u64,
-        // 	depth: u64,
-        // 	difficulty_top64: u64,
-        // 	difficulty: u64,
-        // 	hash: String,
-        // 	height: u64,
-        // 	long_term_weight: u64,
-        // 	major_version: u8,
-        // 	miner_tx_hash: String,
-        // 	minor_version: u8,
-        // 	nonce: u32,
-        // 	num_txes: u64,
-        // 	orphan_status: bool,
-        // 	pow_hash: String,
-        // 	prev_hash: String,
-        // 	reward: u64,
-        // 	timestamp: u64,
-        // 	wide_cumulative_difficulty: String,
-        // 	wide_difficulty: String,
-        // }
+        Self {
+            block_size: x.block_weight,
+            block_weight: x.block_weight,
+            cumulative_difficulty_top64: x.cumulative_difficulty_top64,
+            cumulative_difficulty: x.cumulative_difficulty,
+            depth: x.depth,
+            difficulty_top64: x.difficulty_top64,
+            difficulty: x.difficulty,
+            hash: Hex(x.hash),
+            height: x.height,
+            long_term_weight: x.long_term_weight,
+            major_version: x.major_version,
+            miner_tx_hash: Hex(x.miner_tx_hash),
+            minor_version: x.minor_version,
+            nonce: x.nonce,
+            num_txes: x.num_txes,
+            orphan_status: x.orphan_status,
+            pow_hash: Hex(x.pow_hash),
+            prev_hash: Hex(x.prev_hash),
+            reward: x.reward,
+            timestamp: x.timestamp,
+            // FIXME: if we made a type that automatically did `hex_prefix_u128`,
+            //  we wouldn't need `crate::misc::BlockHeader`.
+            wide_cumulative_difficulty: hex_prefix_u128(
+                x.cumulative_difficulty,
+                x.cumulative_difficulty_top64,
+            ),
+            wide_difficulty: hex_prefix_u128(x.difficulty, x.difficulty_top64),
+        }
     }
 }
 
-impl From<ConnectionInfo> for crate::misc::ConnectionInfo {
-    fn from(x: ConnectionInfo) -> Self {
-        todo!();
+impl<A: NetZoneAddress> From<ConnectionInfo<A>> for crate::misc::ConnectionInfo {
+    fn from(x: ConnectionInfo<A>) -> Self {
+        let (ip, port) = match x.socket_addr {
+            Some(socket) => (socket.ip().to_string(), socket.port().to_string()),
+            None => (String::new(), String::new()),
+        };
 
-        // Self {
-        // 	address: String,
-        // 	address_type: AddressType,
-        // 	avg_download: u64,
-        // 	avg_upload: u64,
-        // 	connection_id: String,
-        // 	current_download: u64,
-        // 	current_upload: u64,
-        // 	height: u64,
-        // 	host: String,
-        // 	incoming: bool,
-        // 	ip: String,
-        // 	live_time: u64,
-        // 	localhost: bool,
-        // 	local_ip: bool,
-        // 	peer_id: String,
-        // 	port: String,
-        // 	pruning_seed: u32,
-        // 	recv_count: u64,
-        // 	recv_idle_time: u64,
-        // 	rpc_credits_per_hash: u32,
-        // 	rpc_port: u16,
-        // 	send_count: u64,
-        // 	send_idle_time: u64,
-        // 	// Exists in the original definition, but isn't
-        // 	// used or (de)serialized for RPC purposes.
-        // 	// ssl: bool,
-        // 	state: ConnectionState,
-        // 	support_flags: u32,
-        // }
+        Self {
+            address: x.address.to_string(),
+            address_type: x.address_type,
+            avg_download: x.avg_download,
+            avg_upload: x.avg_upload,
+            connection_id: String::from(ConnectionId::DEFAULT_STR),
+            current_download: x.current_download,
+            current_upload: x.current_upload,
+            height: x.height,
+            host: x.host,
+            incoming: x.incoming,
+            ip,
+            live_time: x.live_time,
+            localhost: x.localhost,
+            local_ip: x.local_ip,
+            peer_id: hex::encode(x.peer_id.to_ne_bytes()),
+            port,
+            pruning_seed: x.pruning_seed.compress(),
+            recv_count: x.recv_count,
+            recv_idle_time: x.recv_idle_time,
+            rpc_credits_per_hash: x.rpc_credits_per_hash,
+            rpc_port: x.rpc_port,
+            send_count: x.send_count,
+            send_idle_time: x.send_idle_time,
+            state: x.state,
+            support_flags: x.support_flags,
+        }
     }
 }
 
-impl From<SetBan> for crate::misc::SetBan {
-    fn from(x: SetBan) -> Self {
-        todo!();
+// TODO: support non-clearnet addresses.
+impl From<crate::misc::SetBan> for SetBan<SocketAddr> {
+    fn from(x: crate::misc::SetBan) -> Self {
+        let address = SocketAddr::V4(SocketAddrV4::new(ipv4_from_u32(x.ip), 0));
 
-        // Self {
-        // 	#[cfg_attr(feature = "serde", serde(default = "default_string"))]
-        // 	host: String,
-        // 	#[cfg_attr(feature = "serde", serde(default = "default_zero"))]
-        // 	ip: u32,
-        // 	ban: bool,
-        // 	seconds: u32,
-        // }
-    }
-}
-
-impl From<GetBan> for crate::misc::GetBan {
-    fn from(x: GetBan) -> Self {
-        todo!();
-
-        // Self {
-        // 	host: String,
-        // 	ip: u32,
-        // 	seconds: u32,
-        // }
+        let ban = if x.ban {
+            Some(Duration::from_secs(x.seconds.into()))
+        } else {
+            None
+        };
+
+        Self { address, ban }
     }
 }
 
+// TODO: do we need this type?
 impl From<HistogramEntry> for crate::misc::HistogramEntry {
     fn from(x: HistogramEntry) -> Self {
-        todo!();
-
-        // Self {
-        // 	amount: u64,
-        // 	total_instances: u64,
-        // 	unlocked_instances: u64,
-        // 	recent_instances: u64,
-        // }
+        Self {
+            amount: x.amount,
+            total_instances: x.total_instances,
+            unlocked_instances: x.unlocked_instances,
+            recent_instances: x.recent_instances,
+        }
     }
 }
 
-impl From<HardforkEntry> for crate::misc::HardforkEntry {
-    fn from(x: HardforkEntry) -> Self {
-        todo!();
-
-        // Self {
-        // 	height: u64,
-        // 	hf_version: u8,
-        // }
-    }
-}
+// impl From<HardforkEntry> for crate::misc::HardforkEntry {
+//     fn from(x: HardforkEntry) -> Self {
+//         Self {
+//             height: x.height,
+//             hf_version: x.hf_version,
+//         }
+//     }
+// }
 
 impl From<ChainInfo> for crate::misc::ChainInfo {
     fn from(x: ChainInfo) -> Self {
-        todo!();
-
-        // Self {
-        // 	block_hash: [u8; 32],
-        // 	block_hashes: Vec<[u8; 32]>,
-        // 	difficulty_top64: u64,
-        // 	difficulty_low64: u64,
-        // 	height: u64,
-        // 	length: u64,
-        // 	main_chain_parent_block: [u8; 32],
-        // }
+        Self {
+            block_hash: Hex(x.block_hash),
+            block_hashes: x.block_hashes.into_iter().map(hex::encode).collect(),
+            difficulty_top64: x.difficulty_top64,
+            difficulty: x.difficulty,
+            height: x.height,
+            length: x.length,
+            main_chain_parent_block: Hex(x.main_chain_parent_block),
+            wide_difficulty: hex_prefix_u128(x.difficulty, x.difficulty_top64),
+        }
     }
 }
 
-impl From<SyncInfoPeer> for crate::misc::SyncInfoPeer {
-    fn from(x: SyncInfoPeer) -> Self {
-        todo!();
-
-        // Self {
-        // 	info: ConnectionInfo,
-        // }
+// TODO: support non-clearnet addresses.
+impl From<Span<SocketAddr>> for crate::misc::Span {
+    fn from(x: Span<SocketAddr>) -> Self {
+        Self {
+            connection_id: String::from(ConnectionId::DEFAULT_STR),
+            nblocks: x.nblocks,
+            rate: x.rate,
+            remote_address: x.remote_address.to_string(),
+            size: x.size,
+            speed: x.speed,
+            start_block_height: x.start_block_height,
+        }
     }
 }
 
-impl From<Span> for crate::misc::Span {
-    fn from(x: Span) -> Self {
-        todo!();
+// impl From<OutputDistributionData> for crate::misc::OutputDistributionData {
+//     fn from(x: OutputDistributionData) -> Self {
+//         todo!();
 
-        // Self {
-        // 	connection_id: String,
-        // 	nblocks: u64,
-        // 	rate: u32,
-        // 	remote_address: String,
-        // 	size: u64,
-        // 	speed: u32,
-        // 	start_block_height: u64,
-        // }
-    }
-}
+//         // Self {
+//         // 	distribution: Vec<u64>,
+//         // 	start_height: u64,
+//         // 	base: u64,
+//         // }
+//     }
+// }
 
-impl From<TxBacklogEntry> for crate::misc::TxBacklogEntry {
-    fn from(x: TxBacklogEntry) -> Self {
-        todo!();
-
-        // Self {
-        // 	weight: u64,
-        // 	fee: u64,
-        // 	time_in_pool: u64,
-        // }
-    }
-}
-
-impl From<OutputDistributionData> for crate::misc::OutputDistributionData {
-    fn from(x: OutputDistributionData) -> Self {
-        todo!();
-
-        // Self {
-        // 	distribution: Vec<u64>,
-        // 	start_height: u64,
-        // 	base: u64,
-        // }
-    }
-}
-
-impl From<GetMinerDataTxBacklogEntry> for crate::misc::GetMinerDataTxBacklogEntry {
-    fn from(x: GetMinerDataTxBacklogEntry) -> Self {
-        todo!();
-
-        // Self {
-        // 	id: String,
-        // 	weight: u64,
-        // 	fee: u64,
-        // }
+impl From<TxInfo> for crate::misc::TxInfo {
+    fn from(x: TxInfo) -> Self {
+        Self {
+            blob_size: x.blob_size,
+            do_not_relay: x.do_not_relay,
+            double_spend_seen: x.double_spend_seen,
+            fee: x.fee,
+            id_hash: Hex(x.id_hash),
+            kept_by_block: x.kept_by_block,
+            last_failed_height: x.last_failed_height,
+            last_failed_id_hash: Hex(x.last_failed_id_hash),
+            last_relayed_time: x.last_relayed_time,
+            max_used_block_height: x.max_used_block_height,
+            max_used_block_id_hash: Hex(x.max_used_block_id_hash),
+            receive_time: x.receive_time,
+            relayed: x.relayed,
+            tx_blob: hex::encode(x.tx_blob),
+            tx_json: x.tx_json,
+            weight: x.weight,
+        }
     }
 }
 
 impl From<AuxPow> for crate::misc::AuxPow {
     fn from(x: AuxPow) -> Self {
-        todo!();
-
-        // Self {
-        // 	id: [u8; 32],
-        // 	hash: [u8; 32],
-        // }
+        Self {
+            id: Hex(x.id),
+            hash: Hex(x.hash),
+        }
     }
 }
 
-impl From<TxOutputIndices> for crate::misc::TxOutputIndices {
-    fn from(x: TxOutputIndices) -> Self {
-        todo!();
+#[cfg(test)]
+mod tests {
+    use super::*;
 
-        // Self {
-        // 	indices: Vec<u64>,
-        // }
-    }
-}
-
-impl From<BlockOutputIndices> for crate::misc::BlockOutputIndices {
-    fn from(x: BlockOutputIndices) -> Self {
-        todo!();
-
-        // Self {
-        // 	indices: Vec<TxOutputIndices>,
-        // }
-    }
-}
-
-impl From<GetOutputsOut> for crate::misc::GetOutputsOut {
-    fn from(x: GetOutputsOut) -> Self {
-        todo!();
-
-        // Self {
-        // 	amount: u64,
-        // 	index: u64,
-        // }
-    }
-}
-
-impl From<OutKeyBin> for crate::misc::OutKeyBin {
-    fn from(x: OutKeyBin) -> Self {
-        todo!();
-
-        // Self {
-        // 	key: [u8; 32],
-        // 	mask: [u8; 32],
-        // 	unlocked: bool,
-        // 	height: u64,
-        // 	txid: [u8; 32],
-        // }
-    }
-}
-
-impl From<Peer> for crate::misc::Peer {
-    fn from(x: Peer) -> Self {
-        todo!();
-
-        // Self {
-        // 	id: u64,
-        // 	host: String,
-        // 	ip: u32,
-        // 	port: u16,
-        // 	#[cfg_attr(feature = "serde", serde(default = "default_zero"))]
-        // 	rpc_port: u16 = default_zero::<u16>(),
-        // 	#[cfg_attr(feature = "serde", serde(default = "default_zero"))]
-        // 	rpc_credits_per_hash: u32 = default_zero::<u32>(),
-        // 	last_seen: u64,
-        // 	#[cfg_attr(feature = "serde", serde(default = "default_zero"))]
-        // 	pruning_seed: u32 = default_zero::<u32>(),
-        // }
-    }
-}
-
-impl From<PublicNode> for crate::misc::PublicNode {
-    fn from(x: PublicNode) -> Self {
-        todo!();
-
-        // Self {
-        // 	host: String,
-        // 	last_seen: u64,
-        // 	rpc_port: u16,
-        // 	rpc_credits_per_hash: u32,
-        // }
-    }
-}
-
-impl From<TxInfo> for crate::misc::TxInfo {
-    fn from(x: TxInfo) -> Self {
-        todo!();
-
-        // Self {
-        // 	blob_size: u64,
-        // 	do_not_relay: bool,
-        // 	double_spend_seen: bool,
-        // 	fee: u64,
-        // 	id_hash: String,
-        // 	kept_by_block: bool,
-        // 	last_failed_height: u64,
-        // 	last_failed_id_hash: String,
-        // 	last_relayed_time: u64,
-        // 	max_used_block_height: u64,
-        // 	max_used_block_id_hash: String,
-        // 	receive_time: u64,
-        // 	relayed: bool,
-        // 	tx_blob: String,
-        // 	tx_json: String, // TODO: this should be another struct
-        // 	#[cfg_attr(feature = "serde", serde(default = "default_zero"))]
-        // 	weight: u64 = default_zero::<u64>(),
-        // }
-    }
-}
-
-impl From<SpentKeyImageInfo> for crate::misc::SpentKeyImageInfo {
-    fn from(x: SpentKeyImageInfo) -> Self {
-        todo!();
-
-        // Self {
-        // 	id_hash: String,
-        // 	txs_hashes: Vec<String>,
-        // }
-    }
-}
-
-impl From<TxpoolHisto> for crate::misc::TxpoolHisto {
-    fn from(x: TxpoolHisto) -> Self {
-        todo!();
-
-        // Self {
-        // 	txs: u32,
-        // 	bytes: u64,
-        // }
-    }
-}
-
-impl From<TxpoolStats> for crate::misc::TxpoolStats {
-    fn from(x: TxpoolStats) -> Self {
-        todo!();
-
-        // Self {
-        // 	bytes_max: u32,
-        // 	bytes_med: u32,
-        // 	bytes_min: u32,
-        // 	bytes_total: u64,
-        // 	fee_total: u64,
-        // 	histo_98pc: u64,
-        // 	histo: Vec<TxpoolHisto>,
-        // 	num_10m: u32,
-        // 	num_double_spends: u32,
-        // 	num_failing: u32,
-        // 	num_not_relayed: u32,
-        // 	oldest: u64,
-        // 	txs_total: u32,
-        // }
-    }
-}
-
-impl From<OutKey> for crate::misc::OutKey {
-    fn from(x: OutKey) -> Self {
-        todo!();
-
-        // Self {
-        // 	key: String,
-        // 	mask: String,
-        // 	unlocked: bool,
-        // 	height: u64,
-        // 	txid: String,
-        // }
+    #[test]
+    fn hex() {
+        assert_eq!(hex_prefix_u128(0, 0), "0x0");
+        assert_eq!(hex_prefix_u128(0, u64::MAX), "0x0");
+        assert_eq!(hex_prefix_u128(u64::MAX, 0), "0x0");
+        assert_eq!(hex_prefix_u128(u64::MAX, u64::MAX), "0x0");
     }
 }
diff --git a/rpc/types/src/json.rs b/rpc/types/src/json.rs
index a454cab4..8f687268 100644
--- a/rpc/types/src/json.rs
+++ b/rpc/types/src/json.rs
@@ -6,13 +6,14 @@
 #[cfg(feature = "serde")]
 use serde::{Deserialize, Serialize};
 
+use cuprate_types::rpc::{GetMinerDataTxBacklogEntry, HardforkEntry, TxBacklogEntry};
+
 use crate::{
     base::{AccessResponseBase, ResponseBase},
     macros::define_request_and_response,
     misc::{
-        AuxPow, BlockHeader, ChainInfo, ConnectionInfo, Distribution, GetBan,
-        GetMinerDataTxBacklogEntry, HardforkEntry, HistogramEntry, SetBan, Span, Status,
-        SyncInfoPeer, TxBacklogEntry,
+        AuxPow, BlockHeader, ChainInfo, ConnectionInfo, Distribution, GetBan, HistogramEntry,
+        SetBan, Span, Status, SyncInfoPeer,
     },
     rpc_call::RpcCallValue,
 };
diff --git a/rpc/types/src/lib.rs b/rpc/types/src/lib.rs
index 4d3f5ac6..353ca001 100644
--- a/rpc/types/src/lib.rs
+++ b/rpc/types/src/lib.rs
@@ -9,6 +9,7 @@ mod constants;
 #[cfg(any(feature = "serde", feature = "epee"))]
 mod defaults;
 mod free;
+#[cfg(feature = "from")]
 mod from;
 mod macros;
 mod rpc_call;
diff --git a/rpc/types/src/macros.rs b/rpc/types/src/macros.rs
index db1b5d8d..aad4197e 100644
--- a/rpc/types/src/macros.rs
+++ b/rpc/types/src/macros.rs
@@ -408,13 +408,13 @@ pub(crate) use define_request_and_response_doc;
 /// Output a string link to `monerod` source code.
 macro_rules! monero_definition_link {
     (
-        $commit:ident, // Git commit hash
+        $commit:literal, // Git commit hash
         $file_path:literal, // File path within `monerod`'s `src/`, e.g. `rpc/core_rpc_server_commands_defs.h`
         $start:literal$(..=$end:literal)? // File lines, e.g. `0..=123` or `0`
     ) => {
         concat!(
             "[Definition](https://github.com/monero-project/monero/blob/",
-            stringify!($commit),
+            $commit,
             "/src/",
             $file_path,
             "#L",
diff --git a/rpc/types/src/misc/distribution.rs b/rpc/types/src/misc/distribution.rs
index e920d129..ce00de0b 100644
--- a/rpc/types/src/misc/distribution.rs
+++ b/rpc/types/src/misc/distribution.rs
@@ -16,7 +16,7 @@ use cuprate_epee_encoding::{
 ///
 /// Used for [`Distribution::CompressedBinary::distribution`].
 #[doc = crate::macros::monero_definition_link!(
-    cc73fe71162d564ffda8e549b79a350bca53c454,
+    "cc73fe71162d564ffda8e549b79a350bca53c454",
     "rpc/core_rpc_server_commands_defs.h",
     45..=55
 )]
@@ -29,7 +29,7 @@ fn compress_integer_array(_: &[u64]) -> Vec<u8> {
 ///
 /// Used for [`Distribution::CompressedBinary::distribution`].
 #[doc = crate::macros::monero_definition_link!(
-    cc73fe71162d564ffda8e549b79a350bca53c454,
+    "cc73fe71162d564ffda8e549b79a350bca53c454",
     "rpc/core_rpc_server_commands_defs.h",
     57..=72
 )]
@@ -40,7 +40,7 @@ fn decompress_integer_array(_: &[u8]) -> Vec<u64> {
 
 //---------------------------------------------------------------------------------------------------- Distribution
 #[doc = crate::macros::monero_definition_link!(
-    cc73fe71162d564ffda8e549b79a350bca53c454,
+    "cc73fe71162d564ffda8e549b79a350bca53c454",
     "rpc/core_rpc_server_commands_defs.h",
     2468..=2508
 )]
diff --git a/rpc/types/src/misc/key_image_spent_status.rs b/rpc/types/src/misc/key_image_spent_status.rs
index 4b2eb535..44717de5 100644
--- a/rpc/types/src/misc/key_image_spent_status.rs
+++ b/rpc/types/src/misc/key_image_spent_status.rs
@@ -13,7 +13,7 @@ use cuprate_epee_encoding::{
 
 //---------------------------------------------------------------------------------------------------- KeyImageSpentStatus
 #[doc = crate::macros::monero_definition_link!(
-    cc73fe71162d564ffda8e549b79a350bca53c454,
+    "cc73fe71162d564ffda8e549b79a350bca53c454",
     "rpc/core_rpc_server_commands_defs.h",
     456..=460
 )]
diff --git a/rpc/types/src/misc/mod.rs b/rpc/types/src/misc/mod.rs
index 77343567..0d616210 100644
--- a/rpc/types/src/misc/mod.rs
+++ b/rpc/types/src/misc/mod.rs
@@ -27,8 +27,6 @@ pub use requested_info::RequestedInfo;
 pub use status::Status;
 pub use tx_entry::TxEntry;
 pub use types::{
-    AuxPow, BlockHeader, BlockOutputIndices, ChainInfo, ConnectionInfo, GetBan,
-    GetMinerDataTxBacklogEntry, GetOutputsOut, HardforkEntry, HistogramEntry, OutKey, OutKeyBin,
-    OutputDistributionData, Peer, PublicNode, SetBan, Span, SpentKeyImageInfo, SyncInfoPeer,
-    TxBacklogEntry, TxInfo, TxOutputIndices, TxpoolHisto, TxpoolStats,
+    AuxPow, BlockHeader, ChainInfo, ConnectionInfo, GetBan, GetOutputsOut, HistogramEntry,
+    OutKeyBin, SetBan, Span, SpentKeyImageInfo, SyncInfoPeer, TxInfo,
 };
diff --git a/rpc/types/src/misc/requested_info.rs b/rpc/types/src/misc/requested_info.rs
index e594ced6..faf8fb94 100644
--- a/rpc/types/src/misc/requested_info.rs
+++ b/rpc/types/src/misc/requested_info.rs
@@ -13,7 +13,7 @@ use cuprate_epee_encoding::{
 
 //---------------------------------------------------------------------------------------------------- RequestedInfo
 #[doc = crate::macros::monero_definition_link!(
-    cc73fe71162d564ffda8e549b79a350bca53c454,
+    "cc73fe71162d564ffda8e549b79a350bca53c454",
     "rpc/core_rpc_server_commands_defs.h",
     178..=183
 )]
diff --git a/rpc/types/src/misc/tx_entry.rs b/rpc/types/src/misc/tx_entry.rs
index 59dd4604..0c0a9669 100644
--- a/rpc/types/src/misc/tx_entry.rs
+++ b/rpc/types/src/misc/tx_entry.rs
@@ -16,7 +16,7 @@ use crate::serde::{serde_false, serde_true};
 
 //---------------------------------------------------------------------------------------------------- TxEntry
 #[doc = crate::macros::monero_definition_link!(
-    cc73fe71162d564ffda8e549b79a350bca53c454,
+    "cc73fe71162d564ffda8e549b79a350bca53c454",
     "rpc/core_rpc_server_commands_defs.h",
     389..=428
 )]
diff --git a/rpc/types/src/misc/types.rs b/rpc/types/src/misc/types.rs
index d4057264..49bd8517 100644
--- a/rpc/types/src/misc/types.rs
+++ b/rpc/types/src/misc/types.rs
@@ -5,6 +5,8 @@
 //! the [`crate::misc::ConnectionInfo`] struct defined here.
 
 //---------------------------------------------------------------------------------------------------- Import
+use cuprate_types::{hex::Hex, HardFork};
+
 #[cfg(any(feature = "epee", feature = "serde"))]
 use crate::defaults::default_zero;
 
@@ -60,7 +62,7 @@ macro_rules! define_struct_and_impl_epee {
 //---------------------------------------------------------------------------------------------------- Type Definitions
 define_struct_and_impl_epee! {
     #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
+        "cc73fe71162d564ffda8e549b79a350bca53c454",
         "rpc/core_rpc_server_commands_defs.h",
         1163..=1212
     )]
@@ -79,17 +81,17 @@ define_struct_and_impl_epee! {
         depth: u64,
         difficulty_top64: u64,
         difficulty: u64,
-        hash: String,
+        hash: Hex<32>,
         height: u64,
         long_term_weight: u64,
-        major_version: u8,
-        miner_tx_hash: String,
+        major_version: HardFork,
+        miner_tx_hash: Hex<32>,
         minor_version: u8,
         nonce: u32,
         num_txes: u64,
         orphan_status: bool,
-        pow_hash: String,
-        prev_hash: String,
+        pow_hash: Hex<32>,
+        prev_hash: Hex<32>,
         reward: u64,
         timestamp: u64,
         wide_cumulative_difficulty: String,
@@ -99,7 +101,7 @@ define_struct_and_impl_epee! {
 
 define_struct_and_impl_epee! {
     #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
+        "cc73fe71162d564ffda8e549b79a350bca53c454",
         "cryptonote_protocol/cryptonote_protocol_defs.h",
         47..=116
     )]
@@ -138,7 +140,7 @@ define_struct_and_impl_epee! {
 
 define_struct_and_impl_epee! {
     #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
+        "cc73fe71162d564ffda8e549b79a350bca53c454",
         "rpc/core_rpc_server_commands_defs.h",
         2034..=2047
     )]
@@ -155,7 +157,7 @@ define_struct_and_impl_epee! {
 
 define_struct_and_impl_epee! {
     #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
+        "cc73fe71162d564ffda8e549b79a350bca53c454",
         "rpc/core_rpc_server_commands_defs.h",
         1999..=2010
     )]
@@ -169,7 +171,7 @@ define_struct_and_impl_epee! {
 
 define_struct_and_impl_epee! {
     #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
+        "cc73fe71162d564ffda8e549b79a350bca53c454",
         "rpc/core_rpc_server_commands_defs.h",
         2139..=2156
     )]
@@ -185,40 +187,26 @@ define_struct_and_impl_epee! {
 
 define_struct_and_impl_epee! {
     #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
-        "rpc/core_rpc_server_commands_defs.h",
-        2180..=2191
-    )]
-    #[derive(Copy)]
-    /// Used in [`crate::json::GetVersionResponse`].
-    HardforkEntry {
-        height: u64,
-        hf_version: u8,
-    }
-}
-
-define_struct_and_impl_epee! {
-    #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
+        "cc73fe71162d564ffda8e549b79a350bca53c454",
         "rpc/core_rpc_server_commands_defs.h",
         2289..=2310
     )]
     /// Used in [`crate::json::GetAlternateChainsResponse`].
     ChainInfo {
-        block_hash: String,
-        block_hashes: Vec<String>,
+        block_hash: Hex<32>,
+        block_hashes: Vec<String>, // TODO: Vec<Hex<32>> when it has epee
         difficulty: u64,
         difficulty_top64: u64,
         height: u64,
         length: u64,
-        main_chain_parent_block: String,
+        main_chain_parent_block: Hex<32>,
         wide_difficulty: String,
     }
 }
 
 define_struct_and_impl_epee! {
     #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
+        "cc73fe71162d564ffda8e549b79a350bca53c454",
         "rpc/core_rpc_server_commands_defs.h",
         2393..=2400
     )]
@@ -230,7 +218,7 @@ define_struct_and_impl_epee! {
 
 define_struct_and_impl_epee! {
     #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
+        "cc73fe71162d564ffda8e549b79a350bca53c454",
         "rpc/core_rpc_server_commands_defs.h",
         2402..=2421
     )]
@@ -248,89 +236,7 @@ define_struct_and_impl_epee! {
 
 define_struct_and_impl_epee! {
     #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
-        "rpc/core_rpc_server_commands_defs.h",
-        1637..=1642
-    )]
-    #[derive(Copy)]
-    /// Used in [`crate::json::GetTransactionPoolBacklogResponse`].
-    TxBacklogEntry {
-        weight: u64,
-        fee: u64,
-        time_in_pool: u64,
-    }
-}
-
-define_struct_and_impl_epee! {
-    #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
-        "rpc/rpc_handler.h",
-        45..=50
-    )]
-    /// Used in [`crate::json::GetOutputDistributionResponse`].
-    OutputDistributionData {
-        distribution: Vec<u64>,
-        start_height: u64,
-        base: u64,
-    }
-}
-
-define_struct_and_impl_epee! {
-    #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
-        "rpc/core_rpc_server_commands_defs.h",
-        1016..=1027
-    )]
-    /// Used in [`crate::json::GetMinerDataResponse`].
-    ///
-    /// Note that this is different than [`crate::misc::TxBacklogEntry`].
-    GetMinerDataTxBacklogEntry {
-        id: String,
-        weight: u64,
-        fee: u64,
-    }
-}
-
-define_struct_and_impl_epee! {
-    #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
-        "rpc/core_rpc_server_commands_defs.h",
-        1070..=1079
-    )]
-    /// Used in [`crate::json::AddAuxPowRequest`].
-    AuxPow {
-        id: String,
-        hash: String,
-    }
-}
-
-define_struct_and_impl_epee! {
-    #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
-        "rpc/core_rpc_server_commands_defs.h",
-        192..=199
-    )]
-    /// Used in [`crate::bin::GetBlocksResponse`].
-    TxOutputIndices {
-        indices: Vec<u64>,
-    }
-}
-
-define_struct_and_impl_epee! {
-    #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
-        "rpc/core_rpc_server_commands_defs.h",
-        201..=208
-    )]
-    /// Used in [`crate::bin::GetBlocksResponse`].
-    BlockOutputIndices {
-        indices: Vec<TxOutputIndices>,
-    }
-}
-
-define_struct_and_impl_epee! {
-    #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
+        "cc73fe71162d564ffda8e549b79a350bca53c454",
         "rpc/core_rpc_server_commands_defs.h",
         512..=521
     )]
@@ -347,7 +253,7 @@ define_struct_and_impl_epee! {
 
 define_struct_and_impl_epee! {
     #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
+        "cc73fe71162d564ffda8e549b79a350bca53c454",
         "rpc/core_rpc_server_commands_defs.h",
         538..=553
     )]
@@ -364,47 +270,7 @@ define_struct_and_impl_epee! {
 
 define_struct_and_impl_epee! {
     #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
-        "rpc/core_rpc_server_commands_defs.h",
-        1335..=1367
-    )]
-    /// Used in [`crate::other::GetPeerListResponse`].
-    Peer {
-        id: u64,
-        host: String,
-        ip: u32,
-        port: u16,
-        #[cfg_attr(feature = "serde", serde(default = "default_zero"))]
-        rpc_port: u16 = default_zero::<u16>(),
-        #[cfg_attr(feature = "serde", serde(default = "default_zero"))]
-        rpc_credits_per_hash: u32 = default_zero::<u32>(),
-        last_seen: u64,
-        #[cfg_attr(feature = "serde", serde(default = "default_zero"))]
-        pruning_seed: u32 = default_zero::<u32>(),
-    }
-}
-
-define_struct_and_impl_epee! {
-    #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
-        "rpc/core_rpc_server_commands_defs.h",
-        1398..=1417
-    )]
-    ///
-    /// Used in:
-    /// - [`crate::other::GetPeerListResponse`]
-    /// - [`crate::other::GetPublicNodesResponse`]
-    PublicNode {
-        host: String,
-        last_seen: u64,
-        rpc_port: u16,
-        rpc_credits_per_hash: u32,
-    }
-}
-
-define_struct_and_impl_epee! {
-    #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
+        "cc73fe71162d564ffda8e549b79a350bca53c454",
         "rpc/core_rpc_server_commands_defs.h",
         1519..=1556
     )]
@@ -414,17 +280,17 @@ define_struct_and_impl_epee! {
         do_not_relay: bool,
         double_spend_seen: bool,
         fee: u64,
-        id_hash: String,
+        id_hash: Hex<32>,
         kept_by_block: bool,
         last_failed_height: u64,
-        last_failed_id_hash: String,
+        last_failed_id_hash: Hex<32>,
         last_relayed_time: u64,
         max_used_block_height: u64,
-        max_used_block_id_hash: String,
+        max_used_block_id_hash: Hex<32>,
         receive_time: u64,
         relayed: bool,
         tx_blob: String,
-        tx_json: String, // TODO: this should be another struct
+        tx_json: cuprate_types::json::tx::Transaction,
         #[cfg_attr(feature = "serde", serde(default = "default_zero"))]
         weight: u64 = default_zero::<u64>(),
     }
@@ -432,68 +298,26 @@ define_struct_and_impl_epee! {
 
 define_struct_and_impl_epee! {
     #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
+        "cc73fe71162d564ffda8e549b79a350bca53c454",
         "rpc/core_rpc_server_commands_defs.h",
         1558..=1567
     )]
     /// Used in [`crate::other::GetTransactionPoolResponse`].
     SpentKeyImageInfo {
-        id_hash: String,
-        txs_hashes: Vec<String>,
+        id_hash: Hex<32>,
+        txs_hashes: Vec<String>, // TODO: Vec<Hex<32>> when it has epee
     }
 }
 
 define_struct_and_impl_epee! {
     #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
+        "cc73fe71162d564ffda8e549b79a350bca53c454",
         "rpc/core_rpc_server_commands_defs.h",
-        1666..=1675
+        1070..=1079
     )]
-    #[derive(Copy)]
-    /// Used in [`crate::other::GetTransactionPoolStatsResponse`].
-    TxpoolHisto {
-        txs: u32,
-        bytes: u64,
-    }
-}
-
-define_struct_and_impl_epee! {
-    #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
-        "rpc/core_rpc_server_commands_defs.h",
-        1677..=1710
-    )]
-    /// Used in [`crate::other::GetTransactionPoolStatsResponse`].
-    TxpoolStats {
-        bytes_max: u32,
-        bytes_med: u32,
-        bytes_min: u32,
-        bytes_total: u64,
-        fee_total: u64,
-        histo_98pc: u64,
-        histo: Vec<TxpoolHisto>,
-        num_10m: u32,
-        num_double_spends: u32,
-        num_failing: u32,
-        num_not_relayed: u32,
-        oldest: u64,
-        txs_total: u32,
-    }
-}
-
-define_struct_and_impl_epee! {
-    #[doc = monero_definition_link!(
-        cc73fe71162d564ffda8e549b79a350bca53c454,
-        "rpc/core_rpc_server_commands_defs.h",
-        582..=597
-    )]
-    /// Used in [`crate::other::GetOutsResponse`].
-    OutKey {
-        key: String,
-        mask: String,
-        unlocked: bool,
-        height: u64,
-        txid: String,
+    AuxPow {
+        id: Hex<32>,
+        hash: Hex<32>,
     }
 }
 
diff --git a/rpc/types/src/other.rs b/rpc/types/src/other.rs
index d5cbe82b..97132f1d 100644
--- a/rpc/types/src/other.rs
+++ b/rpc/types/src/other.rs
@@ -6,13 +6,12 @@
 #[cfg(feature = "serde")]
 use serde::{Deserialize, Serialize};
 
+use cuprate_types::rpc::{OutKey, Peer, PublicNode, TxpoolStats};
+
 use crate::{
     base::{AccessResponseBase, ResponseBase},
     macros::define_request_and_response,
-    misc::{
-        GetOutputsOut, OutKey, Peer, PublicNode, SpentKeyImageInfo, Status, TxEntry, TxInfo,
-        TxpoolStats,
-    },
+    misc::{GetOutputsOut, SpentKeyImageInfo, Status, TxEntry, TxInfo},
     RpcCallValue,
 };
 
diff --git a/storage/txpool/Cargo.toml b/storage/txpool/Cargo.toml
index 0fb43b24..63d55578 100644
--- a/storage/txpool/Cargo.toml
+++ b/storage/txpool/Cargo.toml
@@ -20,7 +20,7 @@ serde       = ["dep:serde", "cuprate-database/serde", "cuprate-database-service/
 [dependencies]
 cuprate-database         = { workspace = true, features = ["heed"] }
 cuprate-database-service = { workspace = true }
-cuprate-types            = { workspace = true }
+cuprate-types            = { workspace = true, features = ["rpc"] }
 cuprate-helper           = { workspace = true, default-features = false, features = ["constants"] }
 
 monero-serai             = { workspace = true, features = ["std"] }
diff --git a/storage/txpool/src/service/interface.rs b/storage/txpool/src/service/interface.rs
index f2fb144d..d78894dc 100644
--- a/storage/txpool/src/service/interface.rs
+++ b/storage/txpool/src/service/interface.rs
@@ -7,7 +7,7 @@ use std::{
     sync::Arc,
 };
 
-use cuprate_types::{PoolInfo, TransactionVerificationData};
+use cuprate_types::{rpc::PoolInfo, TransactionVerificationData};
 
 use crate::{
     tx::TxEntry,
diff --git a/types/Cargo.toml b/types/Cargo.toml
index b7473198..f58524d2 100644
--- a/types/Cargo.toml
+++ b/types/Cargo.toml
@@ -9,15 +9,16 @@ repository  = "https://github.com/Cuprate/cuprate/tree/main/types"
 keywords    = ["cuprate", "types"]
 
 [features]
-default    = ["blockchain", "epee", "serde", "json", "hex"]
-blockchain = []
+default    = ["blockchain", "epee", "serde", "json", "hex", "rpc"]
+blockchain = ["rpc"]
 epee       = ["dep:cuprate-epee-encoding"]
 serde      = ["dep:serde", "hex"]
 proptest   = ["dep:proptest",  "dep:proptest-derive"]
 json       = ["hex", "dep:cuprate-helper"]
 # We sadly have no choice but to enable serde here as otherwise we will get warnings from the `hex` dep being unused.
-# This isn't too bad as `HexBytes` only makes sense with serde anyway.
+# This isn't too bad as `Hex` only makes sense with serde anyway.
 hex        = ["serde", "dep:hex"]
+rpc        = ["hex"]
 
 [dependencies]
 cuprate-epee-encoding = { workspace = true, optional = true, features = ["std"] }
@@ -25,6 +26,7 @@ cuprate-helper        = { workspace = true, optional = true, features = ["cast"]
 cuprate-fixed-bytes   = { workspace = true, features = ["std", "serde"] }
 
 bytes            = { workspace = true }
+cfg-if           = { workspace = true }
 curve25519-dalek = { workspace = true }
 monero-serai     = { workspace = true }
 hex              = { workspace = true, features = ["serde", "alloc"], optional = true }
diff --git a/types/src/hard_fork.rs b/types/src/hard_fork.rs
index d16032f5..95ffec16 100644
--- a/types/src/hard_fork.rs
+++ b/types/src/hard_fork.rs
@@ -7,6 +7,13 @@ use strum::{
 
 use monero_serai::block::BlockHeader;
 
+#[cfg(feature = "epee")]
+use cuprate_epee_encoding::{
+    error,
+    macros::bytes::{Buf, BufMut},
+    EpeeValue, Marker,
+};
+
 /// Target block time for hf 1.
 ///
 /// ref: <https://monero-book.cuprate.org/consensus_rules/blocks/difficulty.html#target-seconds>
@@ -51,6 +58,7 @@ pub enum HardForkError {
     VariantArray,
 )]
 #[cfg_attr(any(feature = "proptest"), derive(proptest_derive::Arbitrary))]
+#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
 #[repr(u8)]
 pub enum HardFork {
     #[default]
@@ -194,3 +202,19 @@ impl HardFork {
         matches!(self, Self::LATEST)
     }
 }
+
+#[cfg(feature = "epee")]
+impl EpeeValue for HardFork {
+    const MARKER: Marker = u8::MARKER;
+
+    fn read<B: Buf>(r: &mut B, marker: &Marker) -> error::Result<Self> {
+        let u = u8::read(r, marker)?;
+        Self::from_repr(u).ok_or(error::Error::Format("unknown hardfork"))
+    }
+
+    fn write<B: BufMut>(self, w: &mut B) -> error::Result<()> {
+        let u = self.as_u8();
+        u8::write(u, w)?;
+        Ok(())
+    }
+}
diff --git a/types/src/hex.rs b/types/src/hex.rs
index de4fc816..801d8180 100644
--- a/types/src/hex.rs
+++ b/types/src/hex.rs
@@ -18,12 +18,12 @@ use serde::{Deserialize, Serialize};
 #[cfg_attr(feature = "serde", derive(Serialize))]
 #[cfg_attr(feature = "serde", serde(transparent))]
 #[repr(transparent)]
-pub struct HexBytes<const N: usize>(
+pub struct Hex<const N: usize>(
     #[cfg_attr(feature = "serde", serde(with = "hex::serde"))] pub [u8; N],
 );
 
 #[cfg(feature = "serde")]
-impl<'de, const N: usize> Deserialize<'de> for HexBytes<N>
+impl<'de, const N: usize> Deserialize<'de> for Hex<N>
 where
     [u8; N]: hex::FromHex,
     <[u8; N] as hex::FromHex>::Error: std::fmt::Display,
@@ -37,7 +37,7 @@ where
 }
 
 #[cfg(feature = "epee")]
-impl<const N: usize> EpeeValue for HexBytes<N> {
+impl<const N: usize> EpeeValue for Hex<N> {
     const MARKER: Marker = <[u8; N] as EpeeValue>::MARKER;
 
     fn read<B: bytes::Buf>(r: &mut B, marker: &Marker) -> error::Result<Self> {
@@ -50,7 +50,7 @@ impl<const N: usize> EpeeValue for HexBytes<N> {
 }
 
 // Default is not implemented for arrays >32, so we must do it manually.
-impl<const N: usize> Default for HexBytes<N> {
+impl<const N: usize> Default for Hex<N> {
     fn default() -> Self {
         Self([0; N])
     }
@@ -63,13 +63,13 @@ mod test {
     #[test]
     fn hex_bytes_32() {
         let hash = [1; 32];
-        let hex_bytes = HexBytes::<32>(hash);
+        let hex_bytes = Hex::<32>(hash);
         let expected_json = r#""0101010101010101010101010101010101010101010101010101010101010101""#;
 
         let to_string = serde_json::to_string(&hex_bytes).unwrap();
         assert_eq!(to_string, expected_json);
 
-        let from_str = serde_json::from_str::<HexBytes<32>>(expected_json).unwrap();
+        let from_str = serde_json::from_str::<Hex<32>>(expected_json).unwrap();
         assert_eq!(hex_bytes, from_str);
     }
 }
diff --git a/types/src/json/block.rs b/types/src/json/block.rs
index 88f134d5..0ac59494 100644
--- a/types/src/json/block.rs
+++ b/types/src/json/block.rs
@@ -8,7 +8,7 @@ use monero_serai::{block, transaction};
 use cuprate_helper::cast::usize_to_u64;
 
 use crate::{
-    hex::HexBytes,
+    hex::Hex,
     json::output::{Output, TaggedKey, Target},
 };
 
@@ -22,10 +22,10 @@ pub struct Block {
     pub major_version: u8,
     pub minor_version: u8,
     pub timestamp: u64,
-    pub prev_id: HexBytes<32>,
+    pub prev_id: Hex<32>,
     pub nonce: u32,
     pub miner_tx: MinerTransaction,
-    pub tx_hashes: Vec<HexBytes<32>>,
+    pub tx_hashes: Vec<Hex<32>>,
 }
 
 impl From<block::Block> for Block {
@@ -34,13 +34,13 @@ impl From<block::Block> for Block {
             unreachable!("input is a miner tx, this should never fail");
         };
 
-        let tx_hashes = b.transactions.into_iter().map(HexBytes::<32>).collect();
+        let tx_hashes = b.transactions.into_iter().map(Hex::<32>).collect();
 
         Self {
             major_version: b.header.hardfork_version,
             minor_version: b.header.hardfork_signal,
             timestamp: b.header.timestamp,
-            prev_id: HexBytes::<32>(b.header.previous),
+            prev_id: Hex::<32>(b.header.previous),
             nonce: b.header.nonce,
             miner_tx,
             tx_hashes,
@@ -101,14 +101,14 @@ impl TryFrom<transaction::Transaction> for MinerTransaction {
                     let target = match o.view_tag {
                         Some(view_tag) => {
                             let tagged_key = TaggedKey {
-                                key: HexBytes::<32>(o.key.0),
-                                view_tag: HexBytes::<1>([view_tag]),
+                                key: Hex::<32>(o.key.0),
+                                view_tag: Hex::<1>([view_tag]),
                             };
 
                             Target::TaggedKey { tagged_key }
                         }
                         None => Target::Key {
-                            key: HexBytes::<32>(o.key.0),
+                            key: Hex::<32>(o.key.0),
                         },
                     };
 
@@ -222,7 +222,7 @@ mod test {
             major_version: 1,
             minor_version: 0,
             timestamp: 1415690591,
-            prev_id: HexBytes::<32>(hex!(
+            prev_id: Hex::<32>(hex!(
                 "e97a0ab6307de9b9f9a9872263ef3e957976fb227eb9422c6854e989e5d5d34c"
             )),
             nonce: 2147484616,
@@ -237,25 +237,25 @@ mod test {
                       Output {
                         amount: 47019296802,
                         target: Target::Key {
-                          key: HexBytes::<32>(hex!("3c1dcbf5b485987ecef4596bb700e32cbc7bd05964e3888ffc05f8a46bf5fc33")),
+                          key: Hex::<32>(hex!("3c1dcbf5b485987ecef4596bb700e32cbc7bd05964e3888ffc05f8a46bf5fc33")),
                         }
                       },
                       Output {
                         amount: 200000000000,
                         target: Target::Key {
-                          key: HexBytes::<32>(hex!("5810afc7a1b01a1c913eb6aab15d4a851cbc4a8cf0adf90bb80ac1a7ca9928aa")),
+                          key: Hex::<32>(hex!("5810afc7a1b01a1c913eb6aab15d4a851cbc4a8cf0adf90bb80ac1a7ca9928aa")),
                         }
                       },
                       Output {
                         amount: 3000000000000,
                         target: Target::Key {
-                          key: HexBytes::<32>(hex!("520f49c5f2ce8456dc1a565f35ed3a5ccfff3a1210b340870a57d2749a81a2df")),
+                          key: Hex::<32>(hex!("520f49c5f2ce8456dc1a565f35ed3a5ccfff3a1210b340870a57d2749a81a2df")),
                         }
                       },
                       Output {
                         amount: 10000000000000,
                         target: Target::Key {
-                          key: HexBytes::<32>(hex!("44d7705e62c76c2e349a474df6724aa1d9932092002b03a94f9c19d9d12b9427")),
+                          key: Hex::<32>(hex!("44d7705e62c76c2e349a474df6724aa1d9932092002b03a94f9c19d9d12b9427")),
                         }
                       }
                     ],
@@ -281,7 +281,7 @@ mod test {
             major_version: 16,
             minor_version: 16,
             timestamp: 1727293028,
-            prev_id: HexBytes::<32>(hex!(
+            prev_id: Hex::<32>(hex!(
                 "41b56c273d69def3294e56179de71c61808042d54c1e085078d21dbe99e81b6f"
             )),
             nonce: 311,
@@ -296,10 +296,10 @@ mod test {
                         amount: 601012280000,
                         target: Target::TaggedKey {
                             tagged_key: TaggedKey {
-                                key: HexBytes::<32>(hex!(
+                                key: Hex::<32>(hex!(
                                 "8c0b16c6df02b9944b49f375d96a958a0fc5431c048879bb5bf25f64a1163b9e"
                             )),
-                                view_tag: HexBytes::<1>(hex!("88")),
+                                view_tag: Hex::<1>(hex!("88")),
                             },
                         },
                     }],
@@ -312,43 +312,43 @@ mod test {
                 rct_signatures: MinerTransactionRctSignatures { r#type: 0 },
             },
             tx_hashes: vec![
-                HexBytes::<32>(hex!(
+                Hex::<32>(hex!(
                     "eab76986a0cbcae690d8499f0f616f783fd2c89c6f611417f18011950dbdab2e"
                 )),
-                HexBytes::<32>(hex!(
+                Hex::<32>(hex!(
                     "57b19aa8c2cdbb6836cf13dd1e321a67860965c12e4418f3c30f58c8899a851e"
                 )),
-                HexBytes::<32>(hex!(
+                Hex::<32>(hex!(
                     "5340185432ab6b74fb21379f7e8d8f0e37f0882b2a7121fd7c08736f079e2edc"
                 )),
-                HexBytes::<32>(hex!(
+                Hex::<32>(hex!(
                     "01dc6d31db56d68116f5294c1b4f80b33b048b5cdfefcd904f23e6c0de3daff5"
                 )),
-                HexBytes::<32>(hex!(
+                Hex::<32>(hex!(
                     "c9fb6a2730678203948fef2a49fa155b63f35a3649f3d32ed405a6806f3bbd56"
                 )),
-                HexBytes::<32>(hex!(
+                Hex::<32>(hex!(
                     "af965cdd2a2315baf1d4a3d242f44fe07b1fd606d5f4853c9ff546ca6c12a5af"
                 )),
-                HexBytes::<32>(hex!(
+                Hex::<32>(hex!(
                     "97bc9e047d25fae8c14ce6ec882224e7b722f5e79b62a2602a6bacebdac8547b"
                 )),
-                HexBytes::<32>(hex!(
+                Hex::<32>(hex!(
                     "28c46992eaf10dc0cceb313c30572d023432b7bd26e85e679bc8fe419533a7bf"
                 )),
-                HexBytes::<32>(hex!(
+                Hex::<32>(hex!(
                     "c32e3acde2ff2885c9cc87253b40d6827d167dfcc3022c72f27084fd98788062"
                 )),
-                HexBytes::<32>(hex!(
+                Hex::<32>(hex!(
                     "19e66a47f075c7cccde8a7b52803119e089e33e3a4847cace0bd1d17b0d22bab"
                 )),
-                HexBytes::<32>(hex!(
+                Hex::<32>(hex!(
                     "8e8ac560e77a1ee72e82a5eb6887adbe5979a10cd29cb2c2a3720ce87db43a70"
                 )),
-                HexBytes::<32>(hex!(
+                Hex::<32>(hex!(
                     "b7ff5141524b5cca24de6780a5dbfdf71e7de1e062fd85f557fb3b43b8e285dc"
                 )),
-                HexBytes::<32>(hex!(
+                Hex::<32>(hex!(
                     "f09df0f113763ef9b9a2752ac293b478102f7cab03ef803a3d9db7585aea8912"
                 )),
             ],
diff --git a/types/src/json/output.rs b/types/src/json/output.rs
index 182618cd..a1b8605d 100644
--- a/types/src/json/output.rs
+++ b/types/src/json/output.rs
@@ -7,10 +7,10 @@
 #[cfg(feature = "serde")]
 use serde::{Deserialize, Serialize};
 
-use crate::hex::HexBytes;
+use crate::hex::Hex;
 
 /// JSON representation of an output.
-#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
+#[derive(Clone, Default, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
 #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
 pub struct Output {
     pub amount: u64,
@@ -22,7 +22,7 @@ pub struct Output {
 #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
 #[cfg_attr(feature = "serde", serde(untagged))]
 pub enum Target {
-    Key { key: HexBytes<32> },
+    Key { key: Hex<32> },
     TaggedKey { tagged_key: TaggedKey },
 }
 
@@ -38,6 +38,6 @@ impl Default for Target {
 #[derive(Clone, Default, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
 #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
 pub struct TaggedKey {
-    pub key: HexBytes<32>,
-    pub view_tag: HexBytes<1>,
+    pub key: Hex<32>,
+    pub view_tag: Hex<1>,
 }
diff --git a/types/src/json/tx.rs b/types/src/json/tx.rs
index a18dc89a..ff557a18 100644
--- a/types/src/json/tx.rs
+++ b/types/src/json/tx.rs
@@ -8,12 +8,19 @@
 #[cfg(feature = "serde")]
 use serde::{Deserialize, Serialize};
 
+#[cfg(feature = "epee")]
+use cuprate_epee_encoding::{
+    error,
+    macros::bytes::{Buf, BufMut},
+    EpeeObject, EpeeObjectBuilder,
+};
+
 use cuprate_helper::cast::usize_to_u64;
 
 use monero_serai::{ringct, transaction};
 
 use crate::{
-    hex::HexBytes,
+    hex::Hex,
     json::output::{Output, TaggedKey, Target},
 };
 
@@ -30,7 +37,7 @@ pub enum Transaction {
         /// This field is [flattened](https://serde.rs/field-attrs.html#flatten).
         #[cfg_attr(feature = "serde", serde(flatten))]
         prefix: TransactionPrefix,
-        signatures: Vec<HexBytes<64>>,
+        signatures: Vec<Hex<64>>,
     },
     V2 {
         /// This field is [flattened](https://serde.rs/field-attrs.html#flatten).
@@ -43,8 +50,41 @@ pub enum Transaction {
     },
 }
 
+#[cfg(feature = "epee")]
+impl EpeeObjectBuilder<Transaction> for () {
+    fn add_field<B: Buf>(&mut self, _: &str, _: &mut B) -> error::Result<bool> {
+        unreachable!()
+    }
+
+    fn finish(self) -> error::Result<Transaction> {
+        unreachable!()
+    }
+}
+
+#[cfg(feature = "epee")]
+impl EpeeObject for Transaction {
+    type Builder = ();
+
+    fn number_of_fields(&self) -> u64 {
+        unreachable!()
+    }
+
+    fn write_fields<B: BufMut>(self, _: &mut B) -> error::Result<()> {
+        unreachable!()
+    }
+}
+
+impl Default for Transaction {
+    fn default() -> Self {
+        Self::V1 {
+            prefix: Default::default(),
+            signatures: Default::default(),
+        }
+    }
+}
+
 /// [`Transaction::V1::prefix`] & [`Transaction::V2::prefix`].
-#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
+#[derive(Default, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
 #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
 pub struct TransactionPrefix {
     pub version: u8,
@@ -71,7 +111,7 @@ impl From<transaction::Transaction> for Transaction {
                         let key = Key {
                             amount: amount.unwrap_or(0),
                             key_offsets,
-                            k_image: HexBytes::<32>(key_image.compress().0),
+                            k_image: Hex::<32>(key_image.compress().0),
                         };
 
                         Some(Input { key })
@@ -92,14 +132,14 @@ impl From<transaction::Transaction> for Transaction {
                     let target = match o.view_tag {
                         Some(view_tag) => {
                             let tagged_key = TaggedKey {
-                                key: HexBytes::<32>(o.key.0),
-                                view_tag: HexBytes::<1>([view_tag]),
+                                key: Hex::<32>(o.key.0),
+                                view_tag: Hex::<1>([view_tag]),
                             };
 
                             Target::TaggedKey { tagged_key }
                         }
                         None => Target::Key {
-                            key: HexBytes::<32>(o.key.0),
+                            key: Hex::<32>(o.key.0),
                         },
                     };
 
@@ -131,7 +171,7 @@ impl From<transaction::Transaction> for Transaction {
                     .map(|sig| {
                         // TODO: `RingSignature` needs to expose the
                         // inner `Signature` struct as a byte array.
-                        let sig_to_64_bytes = |sig| -> HexBytes<64> { todo!() };
+                        let sig_to_64_bytes = |sig| -> Hex<64> { todo!() };
                         sig_to_64_bytes(sig)
                     })
                     .collect(),
@@ -169,7 +209,7 @@ impl From<transaction::Transaction> for Transaction {
                     .base
                     .commitments
                     .into_iter()
-                    .map(|point| HexBytes::<32>(point.compress().0))
+                    .map(|point| Hex::<32>(point.compress().0))
                     .collect();
 
                 let rct_signatures = RctSignatures::NonCoinbase {
@@ -200,13 +240,21 @@ pub enum RctSignatures {
         r#type: u8,
         txnFee: u64,
         ecdhInfo: Vec<EcdhInfo>,
-        outPk: Vec<HexBytes<32>>,
+        outPk: Vec<Hex<32>>,
     },
     Coinbase {
         r#type: u8,
     },
 }
 
+impl Default for RctSignatures {
+    fn default() -> Self {
+        Self::Coinbase {
+            r#type: Default::default(),
+        }
+    }
+}
+
 /// [`Transaction::V2::rctsig_prunable`].
 #[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
 #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
@@ -224,7 +272,7 @@ pub enum RctSigPrunable {
         nbp: u64,
         bp: Vec<Bulletproof>,
         MGs: Vec<Mg>,
-        pseudoOuts: Vec<HexBytes<32>>,
+        pseudoOuts: Vec<Hex<32>>,
     },
 
     /// - [`ringct::RctPrunable::Clsag`] with [`ringct::bulletproofs::Bulletproof::Original`]
@@ -232,7 +280,7 @@ pub enum RctSigPrunable {
         nbp: u64,
         bp: Vec<Bulletproof>,
         CLSAGs: Vec<Clsag>,
-        pseudoOuts: Vec<HexBytes<32>>,
+        pseudoOuts: Vec<Hex<32>>,
     },
 
     /// - [`ringct::RctPrunable::Clsag`] with [`ringct::bulletproofs::Bulletproof::Plus`]
@@ -240,10 +288,19 @@ pub enum RctSigPrunable {
         nbp: u64,
         bpp: Vec<BulletproofPlus>,
         CLSAGs: Vec<Clsag>,
-        pseudoOuts: Vec<HexBytes<32>>,
+        pseudoOuts: Vec<Hex<32>>,
     },
 }
 
+impl Default for RctSigPrunable {
+    fn default() -> Self {
+        Self::MlsagBorromean {
+            rangeSigs: Default::default(),
+            MGs: Default::default(),
+        }
+    }
+}
+
 #[expect(unused_variables, reason = "TODO: finish impl")]
 impl From<ringct::RctPrunable> for RctSigPrunable {
     fn from(r: ringct::RctPrunable) -> Self {
@@ -282,7 +339,7 @@ impl From<ringct::RctPrunable> for RctSigPrunable {
 }
 
 /// [`RctSigPrunable::MlsagBorromean::rangeSigs`]
-#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
+#[derive(Default, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
 #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
 pub struct RangeSignature {
     // These fields are hex but way too big to be
@@ -293,53 +350,53 @@ pub struct RangeSignature {
 
 /// - [`RctSigPrunable::MlsagBorromean::MGs`]
 /// - [`RctSigPrunable::MlsagBulletproofs::MGs`]
-#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
+#[derive(Default, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
 #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
 pub struct Mg {
-    pub ss: Vec<[HexBytes<32>; 2]>,
-    pub cc: HexBytes<32>,
+    pub ss: Vec<[Hex<32>; 2]>,
+    pub cc: Hex<32>,
 }
 
 /// - [`RctSigPrunable::MlsagBulletproofs::bp`]
 /// - [`RctSigPrunable::ClsagBulletproofs::bp`]
-#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
+#[derive(Default, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
 #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
 pub struct Bulletproof {
-    pub A: HexBytes<32>,
-    pub S: HexBytes<32>,
-    pub T1: HexBytes<32>,
-    pub T2: HexBytes<32>,
-    pub taux: HexBytes<32>,
-    pub mu: HexBytes<32>,
-    pub L: Vec<HexBytes<32>>,
-    pub R: Vec<HexBytes<32>>,
-    pub a: HexBytes<32>,
-    pub b: HexBytes<32>,
-    pub t: HexBytes<32>,
+    pub A: Hex<32>,
+    pub S: Hex<32>,
+    pub T1: Hex<32>,
+    pub T2: Hex<32>,
+    pub taux: Hex<32>,
+    pub mu: Hex<32>,
+    pub L: Vec<Hex<32>>,
+    pub R: Vec<Hex<32>>,
+    pub a: Hex<32>,
+    pub b: Hex<32>,
+    pub t: Hex<32>,
 }
 
 /// - [`RctSigPrunable::ClsagBulletproofsPlus::bpp`]
-#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
+#[derive(Default, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
 #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
 pub struct BulletproofPlus {
-    pub A: HexBytes<32>,
-    pub A1: HexBytes<32>,
-    pub B: HexBytes<32>,
-    pub r1: HexBytes<32>,
-    pub s1: HexBytes<32>,
-    pub d1: HexBytes<32>,
-    pub L: Vec<HexBytes<32>>,
-    pub R: Vec<HexBytes<32>>,
+    pub A: Hex<32>,
+    pub A1: Hex<32>,
+    pub B: Hex<32>,
+    pub r1: Hex<32>,
+    pub s1: Hex<32>,
+    pub d1: Hex<32>,
+    pub L: Vec<Hex<32>>,
+    pub R: Vec<Hex<32>>,
 }
 
 /// - [`RctSigPrunable::ClsagBulletproofs`]
 /// - [`RctSigPrunable::ClsagBulletproofsPlus`]
-#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
+#[derive(Default, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
 #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
 pub struct Clsag {
-    pub s: Vec<HexBytes<32>>,
-    pub c1: HexBytes<32>,
-    pub D: HexBytes<32>,
+    pub s: Vec<Hex<32>>,
+    pub c1: Hex<32>,
+    pub D: Hex<32>,
 }
 
 /// [`RctSignatures::NonCoinbase::ecdhInfo`].
@@ -348,43 +405,47 @@ pub struct Clsag {
 #[cfg_attr(feature = "serde", serde(untagged))]
 #[expect(variant_size_differences)]
 pub enum EcdhInfo {
-    Original {
-        mask: HexBytes<32>,
-        amount: HexBytes<32>,
-    },
-    Compact {
-        amount: HexBytes<8>,
-    },
+    Original { mask: Hex<32>, amount: Hex<32> },
+    Compact { amount: Hex<8> },
+}
+
+impl Default for EcdhInfo {
+    fn default() -> Self {
+        Self::Original {
+            mask: Default::default(),
+            amount: Default::default(),
+        }
+    }
 }
 
 impl From<ringct::EncryptedAmount> for EcdhInfo {
     fn from(ea: ringct::EncryptedAmount) -> Self {
         match ea {
             ringct::EncryptedAmount::Original { amount, mask } => Self::Original {
-                amount: HexBytes::<32>(amount),
-                mask: HexBytes::<32>(mask),
+                amount: Hex::<32>(amount),
+                mask: Hex::<32>(mask),
             },
             ringct::EncryptedAmount::Compact { amount } => Self::Compact {
-                amount: HexBytes::<8>(amount),
+                amount: Hex::<8>(amount),
             },
         }
     }
 }
 
 /// [`TransactionPrefix::vin`].
-#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
+#[derive(Default, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
 #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
 pub struct Input {
     pub key: Key,
 }
 
 /// [`Input::key`].
-#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
+#[derive(Default, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
 #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
 pub struct Key {
     pub amount: u64,
     pub key_offsets: Vec<u64>,
-    pub k_image: HexBytes<32>,
+    pub k_image: Hex<32>,
 }
 
 #[cfg(test)]
@@ -415,7 +476,7 @@ mod test {
                         key: Key {
                             amount: 2865950000,
                             key_offsets: vec![0],
-                            k_image: HexBytes::<32>(hex!(
+                            k_image: Hex::<32>(hex!(
                                 "f1b0eeff62493ea78b2b7e843c278d6d5a7b09adf0cbc83560380d1fe397d6f3"
                             )),
                         },
@@ -424,7 +485,7 @@ mod test {
                         key: Key {
                             amount: 6000000000000,
                             key_offsets: vec![75146],
-                            k_image: HexBytes::<32>(hex!(
+                            k_image: Hex::<32>(hex!(
                                 "3d289ab83c06e0948a460e836699a33fe9c300b2448c0f2de0e3b40c13d9bd78"
                             )),
                         },
@@ -433,7 +494,7 @@ mod test {
                         key: Key {
                             amount: 3000000000000,
                             key_offsets: vec![49742],
-                            k_image: HexBytes::<32>(hex!(
+                            k_image: Hex::<32>(hex!(
                                 "52a32e6ecadcce76c11262eda8f7265c098b3da1f6e27ae8c9656636faf51ae4"
                             )),
                         },
@@ -443,7 +504,7 @@ mod test {
                     Output {
                         amount: 29220020000,
                         target: Target::Key {
-                            key: HexBytes::<32>(hex!(
+                            key: Hex::<32>(hex!(
                                 "f9da453f7cd5248e109de3216208eb9ec8617b0739450405de582f09b7e3fc47"
                             )),
                         },
@@ -451,7 +512,7 @@ mod test {
                     Output {
                         amount: 400000000000,
                         target: Target::Key {
-                            key: HexBytes::<32>(hex!(
+                            key: Hex::<32>(hex!(
                                 "c31ce6d52fae900ffab9f30b036bbdea0b9442b589cbe24c2e071ddb8291da14"
                             )),
                         },
@@ -459,7 +520,7 @@ mod test {
                     Output {
                         amount: 400000000000,
                         target: Target::Key {
-                            key: HexBytes::<32>(hex!(
+                            key: Hex::<32>(hex!(
                                 "bd570e3805c0198c92f9a24d8f12e9dbe88570196efd176b7f186ade904803f4"
                             )),
                         },
@@ -467,7 +528,7 @@ mod test {
                     Output {
                         amount: 1000000000000,
                         target: Target::Key {
-                            key: HexBytes::<32>(hex!(
+                            key: Hex::<32>(hex!(
                                 "84d1ba528dfc2e2ff29b3840fc3ae1c87ae5f750e582b78c4161a6bdb6a4717a"
                             )),
                         },
@@ -475,7 +536,7 @@ mod test {
                     Output {
                         amount: 7000000000000,
                         target: Target::Key {
-                            key: HexBytes::<32>(hex!(
+                            key: Hex::<32>(hex!(
                                 "993fd478527fd3e790fd3f5a0d9a3a39bebe72598cc81cb9936e08dea7e5fb0f"
                             )),
                         },
@@ -489,9 +550,9 @@ mod test {
                 ],
             },
             signatures: vec![
-              HexBytes::<64>(hex!("318755c67c5d3379b0958a047f5439cf43dd251f64b6314c84b2edbf240d950abbeaad13233700e6b6c59bea178c6fbaa246b8fd84b5caf94d1affd520e6770b")),
-              HexBytes::<64>(hex!("a47e6a65e907e49442828db46475ecdf27f3c472f24688423ac97f0efbd8b90b164ed52c070f7a2a95b95398814b19c0befd14a4aab5520963daf3482604df01")),
-              HexBytes::<64>(hex!("fa6981c969c2a1b9d330a8901d2ef7def7f3ade8d9fba444e18e7e349e286a035ae1729a76e01bbbb3ccd010502af6c77049e3167cf108be69706a8674b0c508"))
+              Hex::<64>(hex!("318755c67c5d3379b0958a047f5439cf43dd251f64b6314c84b2edbf240d950abbeaad13233700e6b6c59bea178c6fbaa246b8fd84b5caf94d1affd520e6770b")),
+              Hex::<64>(hex!("a47e6a65e907e49442828db46475ecdf27f3c472f24688423ac97f0efbd8b90b164ed52c070f7a2a95b95398814b19c0befd14a4aab5520963daf3482604df01")),
+              Hex::<64>(hex!("fa6981c969c2a1b9d330a8901d2ef7def7f3ade8d9fba444e18e7e349e286a035ae1729a76e01bbbb3ccd010502af6c77049e3167cf108be69706a8674b0c508"))
             ],
         };
 
@@ -512,7 +573,7 @@ mod test {
                         key_offsets: vec![
                             8608351, 301575, 15985, 56460, 28593, 9238, 1709, 170, 369, 1874, 681,
                         ],
-                        k_image: HexBytes::<32>(hex!(
+                        k_image: Hex::<32>(hex!(
                             "86e1cc68d3970757c4a265a7c28c3a39fe230851f2d8a14c5916a6aa60dbc892"
                         )),
                     },
@@ -521,7 +582,7 @@ mod test {
                     Output {
                         amount: 0,
                         target: Target::Key {
-                            key: HexBytes::<32>(hex!(
+                            key: Hex::<32>(hex!(
                                 "f21fd68e011df2e544a3d33221172baf921a121c85d1a2190c42e81d5dd1830e"
                             )),
                         },
@@ -529,7 +590,7 @@ mod test {
                     Output {
                         amount: 0,
                         target: Target::Key {
-                            key: HexBytes::<32>(hex!(
+                            key: Hex::<32>(hex!(
                                 "64a3e54d80a729f69ae04f85db06dd26a96f3b05674f6927337a755a9cdaefeb"
                             )),
                         },
@@ -537,7 +598,7 @@ mod test {
                     Output {
                         amount: 0,
                         target: Target::Key {
-                            key: HexBytes::<32>(hex!(
+                            key: Hex::<32>(hex!(
                                 "ad2ccf74d2c99946af10cedc922a87c30a4b1c0d7a13143e71d31cd788b0c171"
                             )),
                         },
@@ -545,7 +606,7 @@ mod test {
                     Output {
                         amount: 0,
                         target: Target::Key {
-                            key: HexBytes::<32>(hex!(
+                            key: Hex::<32>(hex!(
                                 "e03d9b552a50734487ed0da40ba977f718c91a782fe85899debfd2c56ea3e551"
                             )),
                         },
@@ -553,7 +614,7 @@ mod test {
                     Output {
                         amount: 0,
                         target: Target::Key {
-                            key: HexBytes::<32>(hex!(
+                            key: Hex::<32>(hex!(
                                 "b312d502c1b71a10d9483fb816e17d27d0508b5b74c462e14dca52395a14a155"
                             )),
                         },
@@ -579,60 +640,60 @@ mod test {
                 txnFee: 86000000,
                 ecdhInfo: vec![
                     EcdhInfo::Original {
-                        mask: HexBytes::<32>(hex!(
+                        mask: Hex::<32>(hex!(
                             "95f1dcd5076d92d9592f1ad5d2e60e8b353c0048da1833db3d11634a9deff50f"
                         )),
-                        amount: HexBytes::<32>(hex!(
+                        amount: Hex::<32>(hex!(
                             "9386f5401e2577e66dea290aae981a85f75ab81d21cd8060b6a2070c0c3d4209"
                         )),
                     },
                     EcdhInfo::Original {
-                        mask: HexBytes::<32>(hex!(
+                        mask: Hex::<32>(hex!(
                             "9a3015d73ee53f40c4a194c725aa5cea4822b99442ddb94223a52e365e02f70b"
                         )),
-                        amount: HexBytes::<32>(hex!(
+                        amount: Hex::<32>(hex!(
                             "40b471293514f4399782abfe2968f5bb297a77b16b58261df7cffc60b68a5b04"
                         )),
                     },
                     EcdhInfo::Original {
-                        mask: HexBytes::<32>(hex!(
+                        mask: Hex::<32>(hex!(
                             "64b2b70d2e61fd4ac5c6d92f61d85dda1daf948853cc303a3a39baeeece41e08"
                         )),
-                        amount: HexBytes::<32>(hex!(
+                        amount: Hex::<32>(hex!(
                             "b388bdce5bd31493dae245af4dbfc8486d959ef28af4ad1c1338f43dd3bd5a01"
                         )),
                     },
                     EcdhInfo::Original {
-                        mask: HexBytes::<32>(hex!(
+                        mask: Hex::<32>(hex!(
                             "e8d8b9380c446cace527ea1864d69f524b2c6b8eaf08f0f6c36621e73de49d0a"
                         )),
-                        amount: HexBytes::<32>(hex!(
+                        amount: Hex::<32>(hex!(
                             "c74b47b823b7e5f2744e9643e4490f236eb9de006acd7bb8a32cca2f56223b06"
                         )),
                     },
                     EcdhInfo::Original {
-                        mask: HexBytes::<32>(hex!(
+                        mask: Hex::<32>(hex!(
                             "1ec895cc03e6831311a3ab6f86745312feec53de5aef1e1f204a984f082bff0c"
                         )),
-                        amount: HexBytes::<32>(hex!(
+                        amount: Hex::<32>(hex!(
                             "d16c02a92488cd7d5fdf3c461ff8f4f7e75a18644e810ddd55a153e79464af0a"
                         )),
                     },
                 ],
                 outPk: vec![
-                    HexBytes::<32>(hex!(
+                    Hex::<32>(hex!(
                         "ff1a463fcb285d747df43612cc3bc925d4d27bebb08537b177a0dba960f90131"
                     )),
-                    HexBytes::<32>(hex!(
+                    Hex::<32>(hex!(
                         "6b62f6ed7338cbf9b2639620400690676fa9d43aca93da4a9dc56d665a72b506"
                     )),
-                    HexBytes::<32>(hex!(
+                    Hex::<32>(hex!(
                         "9363af049e5b0530fd77f884e84838efcabebf5fff57e2f00b49148c6415eafc"
                     )),
-                    HexBytes::<32>(hex!(
+                    Hex::<32>(hex!(
                         "2fc11a581752a6465d59217e6a5841170de3ba96e27d2744ad280b5242efa9e7"
                     )),
-                    HexBytes::<32>(hex!(
+                    Hex::<32>(hex!(
                         "56b6c2ca082d95600584ca429e6723816d4496cbf6f586cf1cfe2e0319224451"
                     )),
                 ],
@@ -640,188 +701,188 @@ mod test {
             rctsig_prunable: Some(RctSigPrunable::MlsagBulletproofs {
                 nbp: 1,
                 bp: vec![Bulletproof {
-                    A: HexBytes::<32>(hex!(
+                    A: Hex::<32>(hex!(
                         "4e3433b32bd6d349774eac4ad467e698125d9e0402d216609ff0f4cfc216c50c"
                     )),
-                    S: HexBytes::<32>(hex!(
+                    S: Hex::<32>(hex!(
                         "7f6d8c127e4138c6153954836b127694786b890a138bae684eb951fb0fbf9be4"
                     )),
-                    T1: HexBytes::<32>(hex!(
+                    T1: Hex::<32>(hex!(
                         "40ee0b2925d7555c17dd38bb69b80e1cfc05aa8b9dc2bd088c1361321a09d4f4"
                     )),
-                    T2: HexBytes::<32>(hex!(
+                    T2: Hex::<32>(hex!(
                         "1488d918c2acdd6ff9e8d5bf82a08599733b9084cdfb0f891c9254742f2ea258"
                     )),
-                    taux: HexBytes::<32>(hex!(
+                    taux: Hex::<32>(hex!(
                         "9b26002cff6e74e3da8ce59cadea4c8a0d93b9d4d94e6764031c21ecbac5f600"
                     )),
-                    mu: HexBytes::<32>(hex!(
+                    mu: Hex::<32>(hex!(
                         "a414b36b00a290c62a443282295f50f381a44197af5db74f518a1b77dd8c120a"
                     )),
                     L: vec![
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "d4c3360932332dd3cc407d857c6e759d7c29d10deede96a0649bba89fbdb0e04"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "33d7311748c6ee1fa92311513a3f32acf0bbcbd1c507e4378db19f108914f6c1"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "aeedddc3feaa374880a388a992e38027d97c8e0e3728fd536fb2f0a560f5f481"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "662e94760e3d51cf89a39db06c8f95e08b923ed97e883e9144d15f21e1639011"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "c07d35cb78309eec01052227df1967c0e0d553f6ca5d592f34bbeebcecdc78a8"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "9954f3a6c818fd5aed6fd7c94fdaf4f49d2159c47e31b953c3e44e11aa4c9943"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "a22d2b47f1a051daece177803252b976c33ac5e2a8c487afd89d61f3a08180f0"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "3ce357034185a6f540d00b2ab8229e64d2d6cad27a2b141d6f6e202307d959ae"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "5906da535fbd816292692880fe4630e9ed1dd2dc94495a4f7db080e18fd4a8e0"
                         )),
                     ],
                     R: vec![
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "0b40204226678fee886140e7c20e809165a58e1355101a2c5bdf7c797811ac21"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "94a1da201d9e85ad6ac564fe2e6a1fa62873d78e33a5931fd143ed165b360eba"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "fc458a6c42264f6c8890a386b7a68543a952ecc2b6239138b548c25d6bfa6c68"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "052da59d062001df5d95d3117deecb9b3175ed59a44aba9b92f84add748c1698"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "5aa7cf7545d4859a62903b29500449813a231a0c25cdb133a4780a9b0a411cd0"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "5366ad21b6b33b8f43aecfda087f0aee9cfdc2836e59f7721856058685965b39"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "960c4764aea3c0dff74c88728514da160bd79712cd50a948bd8b52d9569e69b1"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "6db5c54be77c08460e4581ee7709c0179108b46a55c3858e0897bd4f12e3e913"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "ffb4d75cab91763dc3e556fce046413382c84abe24615ada0605a43f8de88309"
                         )),
                     ],
-                    a: HexBytes::<32>(hex!(
+                    a: Hex::<32>(hex!(
                         "43bf84ef0f596d1d76990c5202261f0963dade1affc1eee92a0508f5ce8d2900"
                     )),
-                    b: HexBytes::<32>(hex!(
+                    b: Hex::<32>(hex!(
                         "747be0d98f642649d2925a459238ed13f65bd6f12019683d4ede505394341604"
                     )),
-                    t: HexBytes::<32>(hex!(
+                    t: Hex::<32>(hex!(
                         "8592adba69d884c48e52135909a9738eafae80e590ae245b1a9ca65eea3a8b0f"
                     )),
                 }],
                 MGs: vec![Mg {
                     ss: vec![
                         [
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "8a8838d965aa1bb49448c12ea1aabb680b393f5bf02e3b73874aa545cde6dc04"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "e16bf1d0c4c2639af6bed0c0205181b2a03bc5cdc22207906aac710acdd5170e"
                             )),
                         ],
                         [
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "208d25cad34bcc9c49a5516102990814c75e0bbe2335b601880d9c6ce4fb400a"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "279a89826548b8b15ea342d892ca6f8bf9e6a5a14077a57edaa4fd676b0b9f0f"
                             )),
                         ],
                         [
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "9edbd1d2082bad9dd9ca98baf82b4d70014dee720c758ed0944a9fb82ae55206"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "3314001eeec40a2e0ca83f48af1ade8b4139418da49e2c6d95aa3a1d4427de07"
                             )),
                         ],
                         [
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "1837f42c1a4bd0747ed86c1e99bfe058031858c47ff4f066cfcdaf107499bf0f"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "963bd0ed98a01be7c847b393ad0c2c25c3052148d67126c12b25ec2239373005"
                             )),
                         ],
                         [
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "e41e7dd0430ccbc17f717db7fa1720241ab4de24249c607b9f882143d266ff0e"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "95c4a4ec2756ec57caacb64f17a7e5306103f030dfb12dd53b42c72e68b6e60b"
                             )),
                         ],
                         [
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "8ecfab987a8697c58f4b183620b2fa0e11972fa666b71c138e067621ab5d1703"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "2e070ae83ab7f01f91766c2fd6de425dc0f18ae4e34fdcb3ac18db4dfec77a0c"
                             )),
                         ],
                         [
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "187cd1a318666e9f7a9f2f9d4eaf7c662c6162c5bc2be94219992f261f46b90b"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "97ca174ff4bcf1e5d139bf0ad85577b9c6247f9e4782cd69100e683bf2e3f80b"
                             )),
                         ],
                         [
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "28eb6f60cfa35b52cbf74b7e68ce795ebfa0d3db6f00e69677fc98aef963bf05"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "6662186aa949465b7b2174d6da077ab8ffdddb710bdab42386e7d8ae20f1890d"
                             )),
                         ],
                         [
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "577c9cf99480b0633121737756bcc7f4887fc7fdf3a9344c84578886e60d1404"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "2d241b48e63acc39c8c899f7c009fcbc09025ea1211930a338e193d17aed890a"
                             )),
                         ],
                         [
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "7a3f489532743f117999a1b375789cd0863541cae0b8633e8cd4c7dedc740305"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "500c1033ca2b4b47c39e70a1c563553571e0e25a2e1fa984cb5ba08546bc4907"
                             )),
                         ],
                         [
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "82efb453a98454e07e8f4b367ee0db2f957e6222e720a69354fdf910fe5fe803"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "1c3204cf63c8ba3ebd817d603a4e5cadfa6a9af5999648eabff7605b5de8b306"
                             )),
                         ],
                     ],
-                    cc: HexBytes::<32>(hex!(
+                    cc: Hex::<32>(hex!(
                         "8b579f973b9395a175fb2fc1df7d66511166c606903a3c082b63fa831e833b00"
                     )),
                 }],
-                pseudoOuts: vec![HexBytes::<32>(hex!(
+                pseudoOuts: vec![Hex::<32>(hex!(
                     "bd6260cafa1afbe44d24cf7c42ac9e2b451424472eb1334b3c042e82196be0d7"
                 ))],
             }),
@@ -845,7 +906,7 @@ mod test {
                             21656060, 186727, 69935, 9151, 6868, 5611, 37323, 11548, 1080, 2867,
                             1193,
                         ],
-                        k_image: HexBytes::<32>(hex!(
+                        k_image: Hex::<32>(hex!(
                             "2969fedfe8eff9fe1aa29c73ea55e8a9080c25dc565d2703e4d2776991a158bd"
                         )),
                     },
@@ -854,7 +915,7 @@ mod test {
                     Output {
                         amount: 0,
                         target: Target::Key {
-                            key: HexBytes::<32>(hex!(
+                            key: Hex::<32>(hex!(
                                 "4a46669165c842dcc4529cb0ca7e34b47073a96d5b29862c9f052a6113ac4db6"
                             )),
                         },
@@ -862,7 +923,7 @@ mod test {
                     Output {
                         amount: 0,
                         target: Target::Key {
-                            key: HexBytes::<32>(hex!(
+                            key: Hex::<32>(hex!(
                                 "264b1dcf7eebde1f4eb9ec87eca25dd963d7281ab5efaa5cfa994a4265fd9b4c"
                             )),
                         },
@@ -879,17 +940,17 @@ mod test {
                 txnFee: 13210000,
                 ecdhInfo: vec![
                     EcdhInfo::Compact {
-                        amount: HexBytes::<8>(hex!("5db75ce558a47531")),
+                        amount: Hex::<8>(hex!("5db75ce558a47531")),
                     },
                     EcdhInfo::Compact {
-                        amount: HexBytes::<8>(hex!("0499d909aafd0109")),
+                        amount: Hex::<8>(hex!("0499d909aafd0109")),
                     },
                 ],
                 outPk: vec![
-                    HexBytes::<32>(hex!(
+                    Hex::<32>(hex!(
                         "70cbcd5105fcb33f29c8f58b7515f98cfdfcbc425239f65eac3804fbee069995"
                     )),
-                    HexBytes::<32>(hex!(
+                    Hex::<32>(hex!(
                         "0aba72c6895d733b7cf59d2cf9c4cd7c82dedf23f9424148d63f138291e6b142"
                     )),
                 ],
@@ -897,124 +958,124 @@ mod test {
             rctsig_prunable: Some(RctSigPrunable::ClsagBulletproofs {
                 nbp: 1,
                 bp: vec![Bulletproof {
-                    A: HexBytes::<32>(hex!(
+                    A: Hex::<32>(hex!(
                         "86765eb65aac879a755822a69a54dbf69d2d3495439eff917dc01667b72d30f8"
                     )),
-                    S: HexBytes::<32>(hex!(
+                    S: Hex::<32>(hex!(
                         "1a1e62a9ca8142cafdd8a8b74517d17f2e883d3495b7722e27750fa3fed44d84"
                     )),
-                    T1: HexBytes::<32>(hex!(
+                    T1: Hex::<32>(hex!(
                         "a6513e0191d0561c16f06dda675e9d21a6f7a074dbf1af498530711a4c0a3b8e"
                     )),
-                    T2: HexBytes::<32>(hex!(
+                    T2: Hex::<32>(hex!(
                         "47a1197d264c8becf36fe2e45bebbe9ff86ab7c141dd99db218ba691a412190b"
                     )),
-                    taux: HexBytes::<32>(hex!(
+                    taux: Hex::<32>(hex!(
                         "cc5aa963d74e48c673f5079b0968060db5c408d8ef50ca8cba9fc58f5e11ff06"
                     )),
-                    mu: HexBytes::<32>(hex!(
+                    mu: Hex::<32>(hex!(
                         "869813119eb1c88103d3b396bb1ee604df3c2ecfd7fab9a70da41f9cb95b2309"
                     )),
                     L: vec![
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "34d1b4db37ad7d522d273c134a80d08eb6a22c1e009d3ab7db950090d35accdf"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "e7b41adc55ec0887b1a982f25c11d50a6191aa0e3de7f92ba944b0967b7b0cd5"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "343b5ad8c7abe7753ddba2fadb3cef36de91a2757167c102c4bb95c3e6778028"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "c132bb4bab3e60b86637ce2a3a563ecf92635b4a972083adacf6ede475467eb6"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "3303f34042776e60631352f687a4508b6e0e96ba58e05da825649c0b342527a8"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "c927d1a85fab1d83e1d3312e4f136e58f13853e529e3d2738d69e7885713a402"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "8a440a513f9e71d1a1a6357954b9a90123da3cfde7ed50b9cb389f6963090e49"
                         )),
                     ],
                     R: vec![
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "60cec37d53635e0f7cfddf7ab7bd4fc092ac69444aa8ebe1029cdac3505e028d"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "4b4c26bae4ee65f66246f45a83d8f2b4aca580d3ec53bfb62ed0d33e3e80ea60"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "f1e6aa90b3ae9e72ce487c1728f73a550b5dc41d971a85a90785b922760b0dcd"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "66e773ab75baa86936bd6653102be3518470f98b1357abb3251da54f273b0e40"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "792e4c055a4483088698a828e6b35447a4f890ad590d9e37709e53b7a8d63d0e"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "f6a43739cc3895d297c42179c9cacc31715f675b332a269f7fdf7c3c645f47c3"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "483a9954d40d1a9ce9082a7e10b8c06fd6e5e925d87dea0d04c4b05c6e74eda7"
                         )),
                     ],
-                    a: HexBytes::<32>(hex!(
+                    a: Hex::<32>(hex!(
                         "65b1099198e6b20e5d810147bb0f9b4de297da33fb8ffbde3721a600b91ab504"
                     )),
-                    b: HexBytes::<32>(hex!(
+                    b: Hex::<32>(hex!(
                         "40280b8a652159007d7e36d2a3d4872ae3b7e25617f486a8eeca993d1146c002"
                     )),
-                    t: HexBytes::<32>(hex!(
+                    t: Hex::<32>(hex!(
                         "aa7d0c7b795de8736e1881fe4b9457cca1e370352c9a2f791d8902292d67de0d"
                     )),
                 }],
                 CLSAGs: vec![Clsag {
                     s: vec![
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "27c6ca7f8cbdb7d8e6a1e0d3cc0805e48a809b827ccb70a9b297b7e9fd506f04"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "25212da093e8a866fe693e31022f8f37547cb38643f0a8373ad20032c0d0970a"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "c41751c335a147960f4daf5d4f18544eab8661e4509e1def78e3c2a08800ab0e"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "7a82c4e2e693ad5cf288b369ed647847e2b3ada1faab0727331aebce7e026507"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "690685c5ecab57799fed9067c88c172c466f1ca2ce6768900af0d7d46d474f0a"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "1891173b4f269dbeb1e13eecd8deecf3ee9bb864476b85a5639257cf6e9f8402"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "737980e8606d2da628368934c5c05fd2b6c2d43a2b56c5c6c2163b70c0836b06"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "274a23f3b8baabb020c4e5315174d12049409cae36af0016a0993cdf97957809"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "de2f2b04ac951975fda136268e60126a6ca53e7cd6cbbff0c9515256d5a1c50f"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "d5747b07bc733144c8ef9574213731a30d1239596467e25b6aac4427647b1d0c"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "5fd4c201cfd87e8fb155c1975e02c06c8de1ab49c84c7948e429798a90d52101"
                         )),
                     ],
-                    c1: HexBytes::<32>(hex!(
+                    c1: Hex::<32>(hex!(
                         "0e118c43701bf377e13d9693f6783963d1e6e2a7bff9d75640eb9e1684c26205"
                     )),
-                    D: HexBytes::<32>(hex!(
+                    D: Hex::<32>(hex!(
                         "deb55a8e4de5b9c84b8d94d63988ce04048497f91bdd3e3878a3f9e7c313e01c"
                     )),
                 }],
-                pseudoOuts: vec![HexBytes::<32>(hex!(
+                pseudoOuts: vec![Hex::<32>(hex!(
                     "48604572eb550295c16f5fe4282131ed4fc5de297611f813b12e752b6b67865f"
                 ))],
             }),
@@ -1039,7 +1100,7 @@ mod test {
                                 56619444, 517411, 383964, 1514827, 38358, 263974, 91303, 3018,
                                 14681, 34540, 7767, 8131, 20234, 16575, 18300, 3587,
                             ],
-                            k_image: HexBytes::<32>(hex!(
+                            k_image: Hex::<32>(hex!(
                                 "ec1636db12f12cffa66e8e3286d8216ad7900128c996ffcc96196856daf10585"
                             )),
                         },
@@ -1051,7 +1112,7 @@ mod test {
                                 49738606, 2766321, 6291275, 92656, 166783, 91733, 286477, 1130,
                                 5724, 9633, 44284, 24605, 8133, 20600, 9906, 2115,
                             ],
-                            k_image: HexBytes::<32>(hex!(
+                            k_image: Hex::<32>(hex!(
                                 "953c1d93684671eb658284061b6f7724f37c68c3bc24732fb81a09f7056426d0"
                             )),
                         },
@@ -1063,7 +1124,7 @@ mod test {
                                 2971790, 44215494, 8487702, 3226387, 861, 158991, 281736, 74021,
                                 24277, 10705, 51824, 25824, 4951, 1235, 7824, 15715,
                             ],
-                            k_image: HexBytes::<32>(hex!(
+                            k_image: Hex::<32>(hex!(
                                 "41a34e8637c3974c9a0444f9c45b361775cc178e4d7d8e07e7d4afdc8e591675"
                             )),
                         },
@@ -1075,7 +1136,7 @@ mod test {
                                 57701146, 641169, 170653, 321459, 625073, 40514, 6448, 5687, 13246,
                                 14743, 7359, 1788, 1054, 1061, 4460, 4059,
                             ],
-                            k_image: HexBytes::<32>(hex!(
+                            k_image: Hex::<32>(hex!(
                                 "2d57a890ff948dd7f0ba17940b6b76db2c87163322f0bd5aca29462f9224c777"
                             )),
                         },
@@ -1086,10 +1147,10 @@ mod test {
                         amount: 0,
                         target: Target::TaggedKey {
                             tagged_key: TaggedKey {
-                                key: HexBytes::<32>(hex!(
+                                key: Hex::<32>(hex!(
                                 "570482299e724f78b8441d700aa63388a842c7f5dbcbe5fa859c2c0abad96b30"
                             )),
-                                view_tag: HexBytes::<1>(hex!("9f")),
+                                view_tag: Hex::<1>(hex!("9f")),
                             },
                         },
                     },
@@ -1097,10 +1158,10 @@ mod test {
                         amount: 0,
                         target: Target::TaggedKey {
                             tagged_key: TaggedKey {
-                                key: HexBytes::<32>(hex!(
+                                key: Hex::<32>(hex!(
                                 "50c1a24ef57aeba07beecd8ddbf294e2501d6fa90ad9712829c00b7293eead96"
                             )),
-                                view_tag: HexBytes::<1>(hex!("06")),
+                                view_tag: Hex::<1>(hex!("06")),
                             },
                         },
                     },
@@ -1116,17 +1177,17 @@ mod test {
                 txnFee: 71860000,
                 ecdhInfo: vec![
                     EcdhInfo::Compact {
-                        amount: HexBytes::<8>(hex!("b0af37c16a8f08a0")),
+                        amount: Hex::<8>(hex!("b0af37c16a8f08a0")),
                     },
                     EcdhInfo::Compact {
-                        amount: HexBytes::<8>(hex!("4cc0843dec9af6b4")),
+                        amount: Hex::<8>(hex!("4cc0843dec9af6b4")),
                     },
                 ],
                 outPk: vec![
-                    HexBytes::<32>(hex!(
+                    Hex::<32>(hex!(
                         "3c51d83c816a0cb8585641a165e866e0215302af9b498db762db27141e673e15"
                     )),
-                    HexBytes::<32>(hex!(
+                    Hex::<32>(hex!(
                         "96eba06bfd2781e65e9a1b1506abfd9ae29dc60fcd29007cd6ad94a8abbf1ecc"
                     )),
                 ],
@@ -1134,67 +1195,67 @@ mod test {
             rctsig_prunable: Some(RctSigPrunable::ClsagBulletproofsPlus {
                 nbp: 1,
                 bpp: vec![BulletproofPlus {
-                    A: HexBytes::<32>(hex!(
+                    A: Hex::<32>(hex!(
                         "28197d8ac07948082b50274fb8d5bea0f81561d02c88981e0d9b5ffd6e5ee169"
                     )),
-                    A1: HexBytes::<32>(hex!(
+                    A1: Hex::<32>(hex!(
                         "efe6eda671d68a894e1b8aff4a1992f85c4269e17196916cfcdf8519cc94d35e"
                     )),
-                    B: HexBytes::<32>(hex!(
+                    B: Hex::<32>(hex!(
                         "7e374ac72276298148217d99568c3d4e09f2442864b5be228cd2d01328abe2d2"
                     )),
-                    r1: HexBytes::<32>(hex!(
+                    r1: Hex::<32>(hex!(
                         "a2e06c25825774e5a130944c6c3eaa3c8afea2ca7d2c09e024615ff700be240a"
                     )),
-                    s1: HexBytes::<32>(hex!(
+                    s1: Hex::<32>(hex!(
                         "6ee7e6624941d1e9ea18024f39a9a694ac798fb69084e10bf982d6a58d416c0a"
                     )),
-                    d1: HexBytes::<32>(hex!(
+                    d1: Hex::<32>(hex!(
                         "d30bea1ffb8e79d0fe37d60c55f6e654d1ca388b102b29a6b28c48c2c617b70f"
                     )),
                     L: vec![
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "cf6e067c87b9161c424620e83645f13284e64c803b9d7af729d0550d475d2199"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "159a03db0d038f6691816d9c31b52a325ad13941222ce1791a0285ca0cf0169d"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "f0276445ea2ec07957fa58675c89aec4dab57d163290e95845dccd484c3e1790"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "40c19df50385f55b4d53fc101c8eef7d411b76c8b94eadbf464d1401d171ea0a"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "6b9a8da4219da8f3e944351825eaf66e99ea954ed0e3b4eed0782379f8fd5509"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "567d12ccd952444055c9a595024f1229a8e0d3ad816f6fd28a448f021603bcc1"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "44616a4203c430653b12e5a2504e79ea390719a1d6a9557eeb55067ba7efc9d3"
                         )),
                     ],
                     R: vec![
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "a7dd6caebda761e8c2ca07e65f9f5b5868777bdc9a4af810d55c691ee62922aa"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "e8db14727596359e8b2e52bd55ceea81e102028d979f79d464d8afe3fd183de3"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "0f808f768cec8fe9f5e41d5925eb5c4955a2c16f650ba26e8cf7be2246b4e559"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "4931dd8eb664e60d86ff259b0e8af24329aefd550170683c324bf8e68ca97169"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "ce05c6ddb73f36dcd5d94cd6a92220c5c42df15f649d4029c9046fb8a8bf4003"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "ae2d51efb12a81062c7a6c9d2c4cdb4b6d7561f76e6f8aa554d98717716b8dda"
                         )),
-                        HexBytes::<32>(hex!(
+                        Hex::<32>(hex!(
                             "ab4a29f9efa41472ae9dfb13d80c929d904a2fbc72a9d2bce063b19baf3bbdbe"
                         )),
                     ],
@@ -1202,248 +1263,248 @@ mod test {
                 CLSAGs: vec![
                     Clsag {
                         s: vec![
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "fa3c832924a4716bac410b9708ac11ed35d9cb01f3e0c1d3958e77791f9ce905"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "6b4dfe306de3f55c5507d802347f4c94ae55e0db4f3bf25e1af3ba1ecd993e0d"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "71c7c612a3dd9d123609df658aaff494787b5cabb5624d5c5d519120f29f5407"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "d72c30a667f22dbc5bbc8479a4e70094bff1980eb962f3f5ce43954da9a5b009"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "869470794715faa72ec2cbbb78743448f9dc5bb6383ac2030484adbb760e7a09"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "6247f181b491a4da82cadbca6272b58365e9160030ed92a1ac5641f9d4163b06"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "9269814384a16ff2bd297fbce5a614ed67529551ba0c21a26abdaff55c96870a"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "b10aeaac7f08f1782a2eb4094864f26fcb6c43559b7610ccd7809b90b1c4f003"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "f38ce2ac13fcdee7be79d0bd98bc17f3df4b1c266a45e1fede7582b12e3a3c0d"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "1b9f3aee12c9fd4e5aae9cf64bd65f0ad20dbc779f472db0bd338229638a6401"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "a04b7e6791b7ea10af2a8b0ff2dbfe63fb6036beed0bd09e9319d4728e33130b"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "a0cd570e0cb80e0fc111468add13b0fc0d8eb4df6942ce3caafedb6c9eee0f07"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "14b38cbfb7012d1c96a25ea5dcb9bfdfb1a92ffe727dd7a1cb332a9bd630d10f"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "5f9be3bc2f667e41baaad111e34ac14eefa493b565c4be4ab6eeab286903870b"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "549bc3275bafd26ab4b89ba14b43976dd317d8d344e37ccbd5a20351a084e005"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "a93847d26171a9194cfa5a94d7f40576b2e808b4bde927e3398bb0a6e9ad0f0e"
                             )),
                         ],
-                        c1: HexBytes::<32>(hex!(
+                        c1: Hex::<32>(hex!(
                             "794f4e50841235043b39fbcb5b50babf5c4b98339fec9538c2538644ac104f01"
                         )),
-                        D: HexBytes::<32>(hex!(
+                        D: Hex::<32>(hex!(
                             "6d50f7b691c0bc174aa11d9953b3452b0f249aa4e7edd560ff1e5772f592a618"
                         )),
                     },
                     Clsag {
                         s: vec![
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "e8140f6e69981917d78656f0b1572ff748771f3106f6134cca77ae83bc2ff201"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "7970c1856b630f213e52c825c507f331145c55104611a908c91998dcc76dd40f"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "8b6899f8eef5bb4c0c830fbb53e34b6089215e0c18b174648fe482675eb0740e"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "8ff4173d836bddc7fd430b0e2cd7d377f9a81025ebdee6030c19114b7964dc05"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "8f14171c429fbf9bd4aa5fe67d180e99a6092f8a7e27a97e6fd85c02613a0209"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "9208e8cc2fd66d6c154202c42bde24f14917b79ccc1b2f31d54880fa14c51202"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "11da8c69a612d2090b375efb61f9be10a16d6ac3d95e8777cb4d3b0cce028509"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "f0b097956d07aaf27a4d19463b63bed427b4945321f203be856a1c45e058ed0e"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "0ad2af34567c40ea4166cd49c368a9ac3bac132c2507f444657de8152465ff0c"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "ded4f3f699c692d01999b858cb752bb6691418393543fa0b1805115847be8f04"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "6ef1fa94a6448488fdc4fdc629813940f78706f9045f48b8d69ce717510b7b0e"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "fbc95294de167bb8a431ff2eacec66637a49927eb15bb443f0ec7c909e301a06"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "03eec8ccae4fd9942376e3df671ed3de9743b03331ee518a69e0f8fb09644e0e"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "861c4a794793dd3eaedd1770263124530035378121bde995b27cbf50bfeb0d08"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "043d02997ff017b110590482dba8a69d2a97092ef7640b8cba5d4271ffc67e04"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "23f12cabd4d7d69a1c6c6cb960b82a427a0ad2df276786312e2b1c60cb17de06"
                             )),
                         ],
-                        c1: HexBytes::<32>(hex!(
+                        c1: Hex::<32>(hex!(
                             "c0f8e42ef1b220d60fa76532b84dd5def896a25b62eec08691ca438c6abcc40d"
                         )),
-                        D: HexBytes::<32>(hex!(
+                        D: Hex::<32>(hex!(
                             "9d0844d4ac7c5988e336514ba17841a3bd1aefd5fa024b692ccd6ef6e9364e34"
                         )),
                     },
                     Clsag {
                         s: vec![
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "bf3a319fd83070d2c97049e1e2d4636f498a5c0547e5e0144f9eb58247f9a50d"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "70b626b51f5e934fad8f6df0db79c3d2af88b6a93e3fcf872d64e89d1909b10b"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "71b200df8b8c5132ba533f1f18924114d451d2b9cca454ea36b7e4b559962307"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "99cc6995a942ad4e9f993d980a077113d46da70f003539190c5bb9ffb4f6310f"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "4dac904bc896e0f8690353924bc98f0baf2d3a2e39da272fd34444664eede404"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "158c1087ae06422bd71a0b59ff7e8f2caa6bbc651b4d0e105551bf91a51f2002"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "e4d119f8c6d39a02b06aca1627078c37b962463d733a4b25d3b6410bdaad6f0f"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "16d5e70dc9bd9f8e9d8d74d75db0bf3a144952d7eaab3abc78ce7c66cb958d06"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "3a0ee94b516a8596bd718ffd87efb76e10b61904033fd0225543680064c5120e"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "354d44ea658710784c4b3389d4048399302e4d7bfa676ea3de53feba2012e30b"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "ce00bbc38aa3e018f1231972232a076f42d38e6d75dececee6561c6336c4be00"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "85094c21f620b87e976f42b742449a048eb303597b1ef362c1a44f76f8d9fa08"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "8e88e960c771bdd2b3df0e0fddbc0cd0a692807d8432c54d6b6ad2114007d10f"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "976274603af385a4079a970a5ddba77a01ac7411e9b2303e76207b288830a107"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "a7f760605b4dffb5b76943e8097b11fb4f2db2fea6354cffc2b96c21aef7a300"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "7e378e64b7a3ece77d88d966e386e939f56976109ad395b4712cf916f50b4c01"
                             )),
                         ],
-                        c1: HexBytes::<32>(hex!(
+                        c1: Hex::<32>(hex!(
                             "edecc915049e5ead7e5fe36dd70c558ace09f4d3a0c6216be148a51e3a72e302"
                         )),
-                        D: HexBytes::<32>(hex!(
+                        D: Hex::<32>(hex!(
                             "197665d3b405f42a2053f9e946483435e75d6c4e801427bfeb66cc58c72e2670"
                         )),
                     },
                     Clsag {
                         s: vec![
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "20c7f0d492ecf79f1d29305f4e8387238a5927fe676674fe479c129431841607"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "b9b98379560d7e22a09fcc72db5b1d05870ffdbded5cf560fcaf5303033f7d04"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "8fc79c2b767ea73f7f552f48d0603b5ee369cdd9535ca06f03fd11e16f08ea0b"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "7e2bdb348f8a719ffed9d995a35d83ae93a63abe1090fae68a3d23ae47c64402"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "aa0f6221cc1454b4dbf84b7f8c6e7b89a1c2a3d0f56a2d6302106e47b6b1b50d"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "08a9283d8b34426eb7b7547fa8fb1573430b99f1c119f2ff9612e82acee98e03"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "250d2ac44e26782f293eca3deb70fc5c52cb942166b1efb2f78ec32640e02d06"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "1bc1bcc3de357a4652c03815e59e14cb13668946366746dca3dad2f4c44c9000"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "9f8b446e373e3e19871f22b9bc95017d4411e555477afb34114b428c8296470a"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "e49d0313e969fb8c4e451388309280a96b8e3216fa1e28ab2efab49f38e86f07"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "0cee07c99293507ad558838f2fa07af1c4ddc86886658c6207c1f25f343afb06"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "39bd17be3aaaeda4fb8aa8dafcf5748581f7bb8b92b0dfe3add14a8481570003"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "0048e1ca905806551cd210c40356cc80935a98f63163a087ea89585915e8770d"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "3c46eea5308dbdff7376d89378998376cb722d08604d6ecb2b3cb795f91dc607"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "7d13be56b2e858d2fca81b3a6b0312943d33e501b4e09814818edb96fb28aa0c"
                             )),
-                            HexBytes::<32>(hex!(
+                            Hex::<32>(hex!(
                                 "313a2021350abd25bd79c22ea33fe071367da2e208913d788d50101c90f0e702"
                             )),
                         ],
-                        c1: HexBytes::<32>(hex!(
+                        c1: Hex::<32>(hex!(
                             "9d96220cd0d49340e06b915f7204cd1f68c4c2069389bf4c011b4fa6c24c0d02"
                         )),
-                        D: HexBytes::<32>(hex!(
+                        D: Hex::<32>(hex!(
                             "91d00727ba3655729ce88981e803967946403e970f0a6749625f59d4e6d7ebc9"
                         )),
                     },
                 ],
                 pseudoOuts: vec![
-                    HexBytes::<32>(hex!(
+                    Hex::<32>(hex!(
                         "a6785a3aca529db1da40944bb1826519d7caaa31f4549e6854cb97e5234d3e8e"
                     )),
-                    HexBytes::<32>(hex!(
+                    Hex::<32>(hex!(
                         "f5cda4db5f83f1c1edea0b66461d1848daf01054c24a690e1438add59dc4f206"
                     )),
-                    HexBytes::<32>(hex!(
+                    Hex::<32>(hex!(
                         "dff30968b66355b9c7890db508692e9620c999e0025ca9395fa53732e6432606"
                     )),
-                    HexBytes::<32>(hex!(
+                    Hex::<32>(hex!(
                         "6b78d37b63714ebe1d09981766c61a07bf0bfbc9fc7f7a8998396aa99d43e0cc"
                     )),
                 ],
diff --git a/types/src/lib.rs b/types/src/lib.rs
index 2eed99f3..a0ffdb64 100644
--- a/types/src/lib.rs
+++ b/types/src/lib.rs
@@ -13,19 +13,13 @@ mod address_type;
 mod block_complete_entry;
 mod connection_state;
 mod hard_fork;
-mod pool_info;
-mod pool_info_extent;
 mod transaction_verification_data;
 mod types;
 
-pub mod rpc;
-
 pub use address_type::AddressType;
 pub use block_complete_entry::{BlockCompleteEntry, PrunedTxBlobEntry, TransactionBlobs};
 pub use connection_state::ConnectionState;
 pub use hard_fork::{HardFork, HardForkError};
-pub use pool_info::PoolInfo;
-pub use pool_info_extent::PoolInfoExtent;
 pub use transaction_verification_data::{
     CachedVerificationState, TransactionVerificationData, TxVersion,
 };
@@ -44,4 +38,10 @@ pub mod json;
 #[cfg(feature = "hex")]
 pub mod hex;
 
+cfg_if::cfg_if! {
+    if #[cfg(feature = "rpc")] {
+        pub mod rpc;
+    }
+}
+
 //---------------------------------------------------------------------------------------------------- Private
diff --git a/types/src/rpc/mod.rs b/types/src/rpc/mod.rs
new file mode 100644
index 00000000..74f31b87
--- /dev/null
+++ b/types/src/rpc/mod.rs
@@ -0,0 +1,24 @@
+//! Various types (in)directly used in RPC.
+//!
+//! These types map very closely to types within `cuprate-rpc-types`,
+//! however they use more canonical types when appropriate, for example,
+//! instead of `hash: String`, this module's types would use something like
+//! `hash: [u8; 32]`.
+//!
+//! - TODO: finish making fields canonical after <https://github.com/Cuprate/cuprate/pull/355>
+//! - TODO: can epee handle `u128`? there are a lot of `(top_64 | low_64)` fields
+
+mod pool_info;
+mod pool_info_extent;
+mod types;
+
+pub use pool_info::PoolInfo;
+pub use pool_info_extent::PoolInfoExtent;
+pub use types::{
+    AddAuxPow, AuxPow, BlockHeader, BlockOutputIndices, ChainInfo, CoinbaseTxSum, ConnectionInfo,
+    FeeEstimate, GetBan, GetMinerDataTxBacklogEntry, GetOutputsOut, HardForkInfo, HardforkEntry,
+    HistogramEntry, MinerData, MinerDataTxBacklogEntry, OutKey, OutKeyBin, OutputDistributionData,
+    OutputHistogramEntry, OutputHistogramInput, Peer, PoolInfoFull, PoolInfoIncremental,
+    PoolTxInfo, PublicNode, SetBan, Span, SpentKeyImageInfo, SyncInfoPeer, TxBacklogEntry, TxInfo,
+    TxOutputIndices, TxpoolHisto, TxpoolStats,
+};
diff --git a/types/src/pool_info.rs b/types/src/rpc/pool_info.rs
similarity index 99%
rename from types/src/pool_info.rs
rename to types/src/rpc/pool_info.rs
index 6d7909ef..759b0f00 100644
--- a/types/src/pool_info.rs
+++ b/types/src/rpc/pool_info.rs
@@ -2,7 +2,7 @@
 use serde::{Deserialize, Serialize};
 
 #[cfg(feature = "epee")]
-use crate::pool_info_extent::PoolInfoExtent;
+use crate::rpc::PoolInfoExtent;
 #[cfg(feature = "epee")]
 use cuprate_epee_encoding::{
     error,
diff --git a/types/src/pool_info_extent.rs b/types/src/rpc/pool_info_extent.rs
similarity index 100%
rename from types/src/pool_info_extent.rs
rename to types/src/rpc/pool_info_extent.rs
diff --git a/types/src/rpc.rs b/types/src/rpc/types.rs
similarity index 92%
rename from types/src/rpc.rs
rename to types/src/rpc/types.rs
index 43cc37c0..a9ac06fc 100644
--- a/types/src/rpc.rs
+++ b/types/src/rpc/types.rs
@@ -1,16 +1,8 @@
 //! Various types (in)directly used in RPC.
-//!
-//! These types map very closely to types within `cuprate-rpc-types`,
-//! however they use more canonical types when appropriate, for example,
-//! instead of `hash: String`, this module's types would use something like
-//! `hash: [u8; 32]`.
-//!
-//! - TODO: finish making fields canonical after <https://github.com/Cuprate/cuprate/pull/355>
-//! - TODO: can epee handle `u128`? there are a lot of `(top_64 | low_64)` fields
 
 use cuprate_fixed_bytes::ByteArrayVec;
 
-use crate::{AddressType, ConnectionState};
+use crate::{hex::Hex, AddressType, ConnectionState, HardFork};
 
 const fn default_string() -> String {
     String::new()
@@ -96,28 +88,25 @@ define_struct_and_impl_epee! {
         1163..=1212
     )]
     BlockHeader {
-        block_size: u64,
         block_weight: u64,
         cumulative_difficulty_top64: u64,
         cumulative_difficulty: u64,
         depth: u64,
         difficulty_top64: u64,
         difficulty: u64,
-        hash: String,
+        hash: [u8; 32],
         height: u64,
         long_term_weight: u64,
-        major_version: u8,
-        miner_tx_hash: String,
+        major_version: HardFork,
+        miner_tx_hash: [u8; 32],
         minor_version: u8,
         nonce: u32,
         num_txes: u64,
         orphan_status: bool,
-        pow_hash: String,
-        prev_hash: String,
+        pow_hash: [u8; 32],
+        prev_hash: [u8; 32],
         reward: u64,
         timestamp: u64,
-        wide_cumulative_difficulty: String,
-        wide_difficulty: String,
     }
 
     #[doc = monero_definition_link!(
@@ -202,7 +191,7 @@ define_struct_and_impl_epee! {
     #[derive(Copy)]
     HardforkEntry {
         height: u64,
-        hf_version: u8,
+        hf_version: HardFork,
     }
 
     #[doc = monero_definition_link!(
@@ -214,7 +203,7 @@ define_struct_and_impl_epee! {
         block_hash: [u8; 32],
         block_hashes: Vec<[u8; 32]>,
         difficulty_top64: u64,
-        difficulty_low64: u64,
+        difficulty: u64,
         height: u64,
         length: u64,
         main_chain_parent_block: [u8; 32],
@@ -371,17 +360,17 @@ define_struct_and_impl_epee! {
         do_not_relay: bool,
         double_spend_seen: bool,
         fee: u64,
-        id_hash: String,
+        id_hash: [u8; 32],
         kept_by_block: bool,
         last_failed_height: u64,
-        last_failed_id_hash: String,
+        last_failed_id_hash: [u8; 32],
         last_relayed_time: u64,
         max_used_block_height: u64,
-        max_used_block_id_hash: String,
+        max_used_block_id_hash: [u8; 32],
         receive_time: u64,
         relayed: bool,
-        tx_blob: String,
-        tx_json: String, // TODO: this should be another struct
+        tx_blob: Vec<u8>,
+        tx_json: crate::json::tx::Transaction,
         #[cfg_attr(feature = "serde", serde(default = "default_zero"))]
         weight: u64 = default_zero::<u64>(),
     }
@@ -434,11 +423,11 @@ define_struct_and_impl_epee! {
         582..=597
     )]
     OutKey {
-        key: String,
-        mask: String,
+        key: Hex<32>,
+        mask: Hex<32>,
         unlocked: bool,
         height: u64,
-        txid: String,
+        txid: Hex<32>,
     }
 
     #[doc = monero_definition_link!(
@@ -473,9 +462,9 @@ define_struct_and_impl_epee! {
     )]
     CoinbaseTxSum {
         emission_amount_top64: u64,
-        emission_amount_low64: u64,
+        emission_amount: u64,
         fee_amount_top64: u64,
-        fee_amount_low64: u64,
+        fee_amount: u64,
     }
 
     #[doc = monero_definition_link!(
@@ -489,7 +478,7 @@ define_struct_and_impl_epee! {
         prev_id: [u8; 32],
         seed_hash: [u8; 32],
         difficulty_top64: u64,
-        difficulty_low64: u64,
+        difficulty: u64,
         median_weight: u64,
         already_generated_coins: u64,
         tx_backlog: Vec<MinerDataTxBacklogEntry>,
diff --git a/zmq/types/src/json_message_types.rs b/zmq/types/src/json_message_types.rs
index 2699600f..0adbd947 100644
--- a/zmq/types/src/json_message_types.rs
+++ b/zmq/types/src/json_message_types.rs
@@ -5,9 +5,11 @@
 //! * `json-full-chain_main` (`Vec<ChainMain>`)
 //! * `json-minimal-chain_main` (`ChainMainMin`)
 //! * `json-full-miner_data` (`MinerData`)
-use cuprate_types::hex::HexBytes;
+
 use serde::{Deserialize, Serialize};
 
+use cuprate_types::hex::Hex;
+
 /// ZMQ `json-full-txpool_add` packets contain an array of `TxPoolAdd`.
 ///
 /// Each `TxPoolAdd` object represents a new transaction in the mempool that was
@@ -42,7 +44,7 @@ pub struct TxPoolAdd {
 #[derive(Debug, Default, Clone, Serialize, Deserialize)]
 pub struct TxPoolAddMin {
     /// transaction ID
-    pub id: HexBytes<32>,
+    pub id: Hex<32>,
     /// size of the full transaction blob
     pub blob_size: u64,
     /// metric used to calculate transaction fee
@@ -63,13 +65,13 @@ pub struct ChainMain {
     /// epoch time, decided by the miner, at which the block was mined
     pub timestamp: u64,
     /// block id of the previous block
-    pub prev_id: HexBytes<32>,
+    pub prev_id: Hex<32>,
     /// cryptographic random one-time number used in mining a Monero block
     pub nonce: u32,
     /// coinbase transaction information
     pub miner_tx: MinerTx,
     /// non-coinbase transaction IDs in the block (can be empty)
-    pub tx_hashes: Vec<HexBytes<32>>,
+    pub tx_hashes: Vec<Hex<32>>,
 }
 
 /// ZMQ `json-minimal-chain_main` subscriber messages contain a single
@@ -80,10 +82,10 @@ pub struct ChainMainMin {
     /// height of the block
     pub first_height: u64,
     /// block id of the previous block
-    pub first_prev_id: HexBytes<32>,
+    pub first_prev_id: Hex<32>,
     /// block ID of the current block is the 0th entry; additional block IDs
     /// will only be included if this is the topmost block of a re-org.
-    pub ids: Vec<HexBytes<32>>,
+    pub ids: Vec<Hex<32>>,
 }
 
 /// ZMQ `json-full-miner_data` subscriber messages contain a single
@@ -96,9 +98,9 @@ pub struct MinerData {
     /// height on which to mine
     pub height: u64,
     /// block id of the most recent block on which to mine the next block
-    pub prev_id: HexBytes<32>,
+    pub prev_id: Hex<32>,
     /// hash of block to use as seed for Random-X proof-of-work
-    pub seed_hash: HexBytes<32>,
+    pub seed_hash: Hex<32>,
     /// least-significant 64 bits of the 128-bit network difficulty
     #[serde(with = "hex_difficulty")]
     pub difficulty: u64,
@@ -124,7 +126,7 @@ pub struct ToKey {
     /// integer offsets for ring members
     pub key_offsets: Vec<u64>,
     /// key image for the given input
-    pub key_image: HexBytes<32>,
+    pub key_image: Hex<32>,
 }
 
 /// Holds the block height of the coinbase transaction.
@@ -156,9 +158,9 @@ pub struct Output {
 #[derive(Debug, Default, Clone, Copy, Serialize, Deserialize)]
 pub struct ToTaggedKey {
     /// public key used to indicate the destination of a transaction output
-    pub key: HexBytes<32>,
+    pub key: Hex<32>,
     /// 1st byte of a shared secret used to reduce wallet synchronization time
-    pub view_tag: HexBytes<1>,
+    pub view_tag: Hex<1>,
 }
 
 /// Ring CT information used inside `TxPoolAdd`
@@ -169,7 +171,7 @@ pub struct PoolRingCt {
     /// encrypted amount values of the transaction outputs
     pub encrypted: Vec<Encrypted>,
     /// Ring CT commitments, 1 per transaction input
-    pub commitments: Vec<HexBytes<32>>,
+    pub commitments: Vec<Hex<32>>,
     /// mining fee in piconeros
     pub fee: u64,
     /// data to validate the transaction that can be pruned from older blocks
@@ -189,9 +191,9 @@ struct MinerRingCt {
 pub struct Encrypted {
     /// obsolete field, but present as zeros in JSON; this does not represent
     /// the newer deterministically derived mask
-    mask: HexBytes<32>,
+    mask: Hex<32>,
     /// encrypted amount of the transaction output
-    pub amount: HexBytes<32>,
+    pub amount: Hex<32>,
 }
 
 /// Data needed to validate a transaction that can optionally be pruned from
@@ -210,22 +212,22 @@ pub struct Prunable {
     pub clsags: Vec<Clsag>,
     /// Ring CT pseudo output commitments; 1 per transaction input (*not*
     /// output)
-    pub pseudo_outs: Vec<HexBytes<32>>,
+    pub pseudo_outs: Vec<Hex<32>>,
 }
 
 /// Bulletproofs+ data used to validate the legitimacy of a Ring CT transaction.
 #[derive(Debug, Default, Clone, Serialize, Deserialize)]
 #[expect(non_snake_case)]
 pub struct BulletproofPlus {
-    pub V: Vec<HexBytes<32>>,
-    pub A: HexBytes<32>,
-    pub A1: HexBytes<32>,
-    pub B: HexBytes<32>,
-    pub r1: HexBytes<32>,
-    pub s1: HexBytes<32>,
-    pub d1: HexBytes<32>,
-    pub L: Vec<HexBytes<32>>,
-    pub R: Vec<HexBytes<32>>,
+    pub V: Vec<Hex<32>>,
+    pub A: Hex<32>,
+    pub A1: Hex<32>,
+    pub B: Hex<32>,
+    pub r1: Hex<32>,
+    pub s1: Hex<32>,
+    pub d1: Hex<32>,
+    pub L: Vec<Hex<32>>,
+    pub R: Vec<Hex<32>>,
 }
 
 /// Placeholder element type so obsolete fields can be deserialized
@@ -237,9 +239,9 @@ struct Obsolete;
 #[expect(non_snake_case)]
 #[derive(Debug, Default, Clone, Serialize, Deserialize)]
 pub struct Clsag {
-    pub s: Vec<HexBytes<32>>,
-    pub c1: HexBytes<32>,
-    pub D: HexBytes<32>,
+    pub s: Vec<Hex<32>>,
+    pub c1: Hex<32>,
+    pub D: Hex<32>,
 }
 
 /// Part of the new block information in `ChainMain`
@@ -269,7 +271,7 @@ pub struct MinerTx {
 #[derive(Debug, Default, Clone, Serialize, Deserialize)]
 pub struct TxBacklog {
     /// transaction ID
-    pub id: HexBytes<32>,
+    pub id: Hex<32>,
     /// metric used to calculate transaction fee
     pub weight: u64,
     /// mining fee in piconeros