Skip to content

Commit 4e2f466

Browse files
authored
RUST-310 Use serde for ClientOptions tests (#362)
1 parent 5ab3691 commit 4e2f466

File tree

6 files changed

+297
-202
lines changed

6 files changed

+297
-202
lines changed

src/bson_util/mod.rs

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -87,6 +87,20 @@ pub(crate) fn serialize_duration_as_int_millis<S: Serializer>(
8787
}
8888
}
8989

90+
#[cfg(test)]
91+
pub(crate) fn serialize_duration_option_as_int_secs<S: Serializer>(
92+
val: &Option<Duration>,
93+
serializer: S,
94+
) -> std::result::Result<S::Ok, S::Error> {
95+
match val {
96+
Some(duration) if duration.as_secs() > i32::MAX as u64 => {
97+
serializer.serialize_i64(duration.as_secs() as i64)
98+
}
99+
Some(duration) => serializer.serialize_i32(duration.as_secs() as i32),
100+
None => serializer.serialize_none(),
101+
}
102+
}
103+
90104
pub(crate) fn deserialize_duration_from_u64_millis<'de, D>(
91105
deserializer: D,
92106
) -> std::result::Result<Option<Duration>, D::Error>

src/client/auth/mod.rs

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -431,6 +431,31 @@ impl Credential {
431431
.authenticate_stream(conn, self, server_api, http_client)
432432
.await
433433
}
434+
435+
#[cfg(test)]
436+
pub(crate) fn serialize_for_client_options<S>(
437+
credential: &Option<Credential>,
438+
serializer: S,
439+
) -> std::result::Result<S::Ok, S::Error>
440+
where
441+
S: serde::Serializer,
442+
{
443+
use serde::ser::Serialize;
444+
445+
#[derive(serde::Serialize)]
446+
struct CredentialHelper<'a> {
447+
authsource: Option<&'a String>,
448+
authmechanism: Option<&'a str>,
449+
authmechanismproperties: Option<&'a Document>,
450+
}
451+
452+
let state = credential.as_ref().map(|c| CredentialHelper {
453+
authsource: c.source.as_ref(),
454+
authmechanism: c.mechanism.as_ref().map(|s| s.as_str()),
455+
authmechanismproperties: c.mechanism_properties.as_ref(),
456+
});
457+
state.serialize(serializer)
458+
}
434459
}
435460

436461
impl Debug for Credential {

src/client/options/mod.rs

Lines changed: 139 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -138,7 +138,7 @@ impl Hash for StreamAddress {
138138
///
139139
/// Currently this just supports addresses that can be connected to over TCP, but alternative
140140
/// address types may be supported in the future (e.g. Unix Domain Socket paths).
141-
#[derive(Clone, Debug, Eq)]
141+
#[derive(Clone, Debug, Eq, Serialize)]
142142
#[non_exhaustive]
143143
pub enum ServerAddress {
144144
/// A TCP/IP host and port combination.
@@ -556,6 +556,95 @@ impl Default for ClientOptions {
556556
}
557557
}
558558

559+
#[cfg(test)]
560+
impl Serialize for ClientOptions {
561+
fn serialize<S>(&self, serializer: S) -> std::result::Result<S::Ok, S::Error>
562+
where
563+
S: serde::Serializer,
564+
{
565+
#[derive(Serialize)]
566+
struct ClientOptionsHelper<'a> {
567+
appname: &'a Option<String>,
568+
compressors: &'a Option<Vec<String>>,
569+
570+
#[serde(serialize_with = "serialize_duration_as_int_millis")]
571+
connecttimeoutms: &'a Option<Duration>,
572+
573+
#[serde(flatten, serialize_with = "Credential::serialize_for_client_options")]
574+
credential: &'a Option<Credential>,
575+
576+
directconnection: &'a Option<bool>,
577+
578+
#[serde(serialize_with = "serialize_duration_as_int_millis")]
579+
heartbeatfrequencyms: &'a Option<Duration>,
580+
581+
#[serde(serialize_with = "serialize_duration_as_int_millis")]
582+
localthresholdms: &'a Option<Duration>,
583+
584+
#[serde(serialize_with = "serialize_duration_as_int_millis")]
585+
maxidletimems: &'a Option<Duration>,
586+
587+
maxpoolsize: &'a Option<u32>,
588+
589+
minpoolsize: &'a Option<u32>,
590+
591+
#[serde(flatten, serialize_with = "ReadConcern::serialize_for_client_options")]
592+
readconcern: &'a Option<ReadConcern>,
593+
594+
replicaset: &'a Option<String>,
595+
596+
retryreads: &'a Option<bool>,
597+
598+
retrywrites: &'a Option<bool>,
599+
600+
#[serde(
601+
flatten,
602+
serialize_with = "SelectionCriteria::serialize_for_client_options"
603+
)]
604+
selectioncriteria: &'a Option<SelectionCriteria>,
605+
606+
#[serde(serialize_with = "serialize_duration_as_int_millis")]
607+
serverselectiontimeoutms: &'a Option<Duration>,
608+
609+
#[serde(serialize_with = "serialize_duration_as_int_millis")]
610+
sockettimeoutms: &'a Option<Duration>,
611+
612+
#[serde(flatten, serialize_with = "Tls::serialize_for_client_options")]
613+
tls: &'a Option<Tls>,
614+
615+
#[serde(flatten, serialize_with = "WriteConcern::serialize_for_client_options")]
616+
writeconcern: &'a Option<WriteConcern>,
617+
618+
zlibcompressionlevel: &'a Option<i32>,
619+
}
620+
621+
let client_options = ClientOptionsHelper {
622+
appname: &self.app_name,
623+
compressors: &self.compressors,
624+
connecttimeoutms: &self.connect_timeout,
625+
credential: &self.credential,
626+
directconnection: &self.direct_connection,
627+
heartbeatfrequencyms: &self.heartbeat_freq,
628+
localthresholdms: &self.local_threshold,
629+
maxidletimems: &self.max_idle_time,
630+
maxpoolsize: &self.max_pool_size,
631+
minpoolsize: &self.min_pool_size,
632+
readconcern: &self.read_concern,
633+
replicaset: &self.repl_set_name,
634+
retryreads: &self.retry_reads,
635+
retrywrites: &self.retry_writes,
636+
selectioncriteria: &self.selection_criteria,
637+
serverselectiontimeoutms: &self.server_selection_timeout,
638+
sockettimeoutms: &self.socket_timeout,
639+
tls: &self.tls,
640+
writeconcern: &self.write_concern,
641+
zlibcompressionlevel: &self.zlib_compression,
642+
};
643+
644+
client_options.serialize(serializer)
645+
}
646+
}
647+
559648
#[derive(Debug, Default, PartialEq)]
560649
struct ClientOptionsParser {
561650
pub hosts: Vec<ServerAddress>,
@@ -614,6 +703,24 @@ impl From<TlsOptions> for Option<Tls> {
614703
}
615704
}
616705

706+
impl Tls {
707+
#[cfg(test)]
708+
pub(crate) fn serialize_for_client_options<S>(
709+
tls: &Option<Tls>,
710+
serializer: S,
711+
) -> std::result::Result<S::Ok, S::Error>
712+
where
713+
S: serde::Serializer,
714+
{
715+
match tls {
716+
Some(Tls::Enabled(tls_options)) => {
717+
TlsOptions::serialize_for_client_options(tls_options, serializer)
718+
}
719+
_ => serializer.serialize_none(),
720+
}
721+
}
722+
}
723+
617724
/// Specifies the TLS configuration that the [`Client`](../struct.Client.html) should use.
618725
#[derive(Clone, Debug, Default, Deserialize, PartialEq, TypedBuilder)]
619726
#[builder(field_defaults(default, setter(strip_option)))]
@@ -718,6 +825,37 @@ impl TlsOptions {
718825

719826
Ok(config)
720827
}
828+
829+
#[cfg(test)]
830+
pub(crate) fn serialize_for_client_options<S>(
831+
tls_options: &TlsOptions,
832+
serializer: S,
833+
) -> std::result::Result<S::Ok, S::Error>
834+
where
835+
S: serde::Serializer,
836+
{
837+
#[derive(Serialize)]
838+
struct TlsOptionsHelper<'a> {
839+
tls: bool,
840+
tlscafile: Option<&'a str>,
841+
tlscertificatekeyfile: Option<&'a str>,
842+
tlsallowinvalidcertificates: Option<bool>,
843+
}
844+
845+
let state = TlsOptionsHelper {
846+
tls: true,
847+
tlscafile: tls_options
848+
.ca_file_path
849+
.as_ref()
850+
.map(|s| s.to_str().unwrap()),
851+
tlscertificatekeyfile: tls_options
852+
.cert_key_file_path
853+
.as_ref()
854+
.map(|s| s.to_str().unwrap()),
855+
tlsallowinvalidcertificates: tls_options.allow_invalid_certificates,
856+
};
857+
state.serialize(serializer)
858+
}
721859
}
722860

723861
/// Extra information to append to the driver version in the metadata of the handshake with the

0 commit comments

Comments
 (0)