Use collect_seq when serializing Vec<T>
What changed, and why it matters
This commit is a routine code cleanup in the rust-bitcoin library. It replaces several hand-written loops that serialize lists of values with a single standard helper called collect_seq. There is no functional change intended, and nothing in the commit suggests a security fix or vulnerability.
No security action required. Treat as a normal refactoring commit during code review; verify existing serde round-trip tests still pass.
Security signals we found
No strong security signals were identified.
Evidence from the diff
The patch refactors Vec
Changed components
internals/src/array_vec.rsprimitives/src/serde_as_consensus.rsunits/src/amount/serde.rsunits/src/fee_rate/serde.rsInspect captured patch +14 / −50
diff --git a/internals/src/array_vec.rs b/internals/src/array_vec.rs
index 39a2c15a..a49477de 100644
--- a/internals/src/array_vec.rs
+++ b/internals/src/array_vec.rs
@@ -186,13 +186,7 @@ impl<T: Copy + crate::serde::Serialize, const CAP: usize> crate::serde::Serializ
where
S: crate::serde::Serializer,
{
- use crate::serde::ser::SerializeSeq;
-
- let mut seq = serializer.serialize_seq(Some(self.len()))?;
- for elem in self.as_slice() {
- seq.serialize_element(elem)?;
- }
- seq.end()
+ serializer.collect_seq(self.iter())
}
}
diff --git a/primitives/src/serde_as_consensus.rs b/primitives/src/serde_as_consensus.rs
index 177f1837..7d44b662 100644
--- a/primitives/src/serde_as_consensus.rs
+++ b/primitives/src/serde_as_consensus.rs
@@ -209,8 +209,6 @@ pub mod vec {
T: Encode + Decode,
S: Serializer,
{
- use serde::ser::SerializeSeq;
-
struct AsConsensus<'a, T>(&'a T);
impl<T: Encode + Decode> serde::Serialize for AsConsensus<'_, T> {
@@ -219,11 +217,7 @@ pub mod vec {
}
}
- let mut seq = s.serialize_seq(Some(v.len()))?;
- for item in v {
- seq.serialize_element(&AsConsensus(item))?;
- }
- seq.end()
+ s.collect_seq(v.iter().map(|item| AsConsensus(item)))
}
pub fn deserialize<'d, T, D>(d: D) -> Result<Vec<T>, D::Error>
diff --git a/units/src/amount/serde.rs b/units/src/amount/serde.rs
index 0cdf371b..81b9794f 100644
--- a/units/src/amount/serde.rs
+++ b/units/src/amount/serde.rs
@@ -163,7 +163,6 @@ pub mod as_sat {
use core::marker::PhantomData;
use serde::de::{self, SeqAccess};
- use serde::ser::SerializeSeq;
use serde::{Deserialize, Deserializer, Serializer};
use crate::SignedAmount;
@@ -172,12 +171,10 @@ pub mod as_sat {
where
A: Into<SignedAmount> + Copy,
{
- let mut seq = s.serialize_seq(Some(a.len()))?;
- for amount in a {
+ s.collect_seq(a.iter().map(|amount| {
let signed_amount: SignedAmount = (*amount).into();
- seq.serialize_element(&signed_amount.to_sat())?;
- }
- seq.end()
+ signed_amount.to_sat()
+ }))
}
pub fn deserialize<'d, A, D: Deserializer<'d>>(d: D) -> Result<Vec<A>, D::Error>
@@ -333,7 +330,6 @@ pub mod as_btc {
use core::marker::PhantomData;
use serde::de::{self, SeqAccess};
- use serde::ser::SerializeSeq;
use serde::{Deserialize, Deserializer, Serializer};
use crate::amount::{Denomination, SignedAmount};
@@ -342,12 +338,10 @@ pub mod as_btc {
where
A: Into<SignedAmount> + Copy,
{
- let mut seq = s.serialize_seq(Some(a.len()))?;
- for amount in a {
+ s.collect_seq(a.iter().map(|amount| {
let signed_amount: SignedAmount = (*amount).into();
- seq.serialize_element(&signed_amount.to_float_in(Denomination::Bitcoin))?;
- }
- seq.end()
+ signed_amount.to_float_in(Denomination::Bitcoin)
+ }))
}
pub fn deserialize<'d, A, D: Deserializer<'d>>(d: D) -> Result<Vec<A>, D::Error>
@@ -505,7 +499,6 @@ pub mod as_str {
use core::marker::PhantomData;
use serde::de::{self, SeqAccess};
- use serde::ser::SerializeSeq;
use serde::{Deserialize, Deserializer, Serializer};
use crate::amount::{Denomination, SignedAmount};
@@ -514,12 +507,10 @@ pub mod as_str {
where
A: Into<SignedAmount> + Copy,
{
- let mut seq = s.serialize_seq(Some(a.len()))?;
- for amount in a {
+ s.collect_seq(a.iter().map(|amount| {
let signed_amount: SignedAmount = (*amount).into();
- seq.serialize_element(&signed_amount.to_string_in(Denomination::Bitcoin))?;
- }
- seq.end()
+ signed_amount.to_string_in(Denomination::Bitcoin)
+ }))
}
pub fn deserialize<'d, A, D: Deserializer<'d>>(d: D) -> Result<Vec<A>, D::Error>
diff --git a/units/src/fee_rate/serde.rs b/units/src/fee_rate/serde.rs
index 0cdd3bc5..4d66e865 100644
--- a/units/src/fee_rate/serde.rs
+++ b/units/src/fee_rate/serde.rs
@@ -110,17 +110,12 @@ pub mod as_sat_per_kwu_floor {
use core::fmt;
use serde::de::{self, SeqAccess};
- use serde::ser::SerializeSeq;
use serde::{Deserialize, Deserializer, Serializer};
use crate::FeeRate;
pub fn serialize<S: Serializer>(f: &[FeeRate], s: S) -> Result<S::Ok, S::Error> {
- let mut seq = s.serialize_seq(Some(f.len()))?;
- for rate in f {
- seq.serialize_element(&rate.to_sat_per_kwu_floor())?;
- }
- seq.end()
+ s.collect_seq(f.iter().map(|rate| rate.to_sat_per_kwu_floor()))
}
// Errors on overflow.
@@ -243,17 +238,12 @@ pub mod as_sat_per_vb_floor {
use core::fmt;
use serde::de::{self, SeqAccess};
- use serde::ser::SerializeSeq;
use serde::{Deserialize, Deserializer, Serializer};
use crate::FeeRate;
pub fn serialize<S: Serializer>(f: &[FeeRate], s: S) -> Result<S::Ok, S::Error> {
- let mut seq = s.serialize_seq(Some(f.len()))?;
- for rate in f {
- seq.serialize_element(&rate.to_sat_per_vb_floor())?;
- }
- seq.end()
+ s.collect_seq(f.iter().map(|rate| rate.to_sat_per_vb_floor()))
}
// Errors on overflow.
@@ -376,17 +366,12 @@ pub mod as_sat_per_vb_ceil {
use core::fmt;
use serde::de::{self, SeqAccess};
- use serde::ser::SerializeSeq;
use serde::{Deserialize, Deserializer, Serializer};
use crate::FeeRate;
pub fn serialize<S: Serializer>(f: &[FeeRate], s: S) -> Result<S::Ok, S::Error> {
- let mut seq = s.serialize_seq(Some(f.len()))?;
- for rate in f {
- seq.serialize_element(&rate.to_sat_per_vb_ceil())?;
- }
- seq.end()
+ s.collect_seq(f.iter().map(|rate| rate.to_sat_per_vb_ceil()))
}
// Errors on overflow.
Why this scored 15/100
Community notes
Notes can correct, qualify, or add evidence to the AI analysis. Every note shown here has been validated by a human moderator.
The AI analysis stands alone for now. Submit a note if you can add evidence or important context.