11use std:: {
2+ collections:: HashSet ,
23 convert:: TryFrom ,
34 io:: { Read , Write } ,
45} ;
56
7+ use serde:: Serialize ;
8+
69use crate :: {
710 bson:: {
811 oid:: ObjectId ,
@@ -15,7 +18,7 @@ use crate::{
1518 RawDocumentBuf ,
1619 } ,
1720 checked:: Checked ,
18- error:: { ErrorKind , Result } ,
21+ error:: { Error , ErrorKind , Result } ,
1922 runtime:: SyncLittleEndianRead ,
2023} ;
2124
@@ -65,6 +68,13 @@ pub(crate) fn to_raw_bson_array(docs: &[Document]) -> Result<RawBson> {
6568 }
6669 Ok ( RawBson :: Array ( array) )
6770}
71+ pub ( crate ) fn to_raw_bson_array_ser < T : Serialize > ( values : & [ T ] ) -> Result < RawBson > {
72+ let mut array = RawArrayBuf :: new ( ) ;
73+ for value in values {
74+ array. push ( bson:: to_raw_document_buf ( value) ?) ;
75+ }
76+ Ok ( RawBson :: Array ( array) )
77+ }
6878
6979pub ( crate ) fn first_key ( document : & Document ) -> Option < & str > {
7080 document. keys ( ) . next ( ) . map ( String :: as_str)
@@ -162,13 +172,42 @@ pub(crate) fn extend_raw_document_buf(
162172 this : & mut RawDocumentBuf ,
163173 other : RawDocumentBuf ,
164174) -> Result < ( ) > {
175+ let mut keys: HashSet < String > = HashSet :: new ( ) ;
176+ for elem in this. iter_elements ( ) {
177+ keys. insert ( elem?. key ( ) . to_owned ( ) ) ;
178+ }
165179 for result in other. iter ( ) {
166180 let ( k, v) = result?;
181+ if keys. contains ( k) {
182+ return Err ( Error :: internal ( format ! (
183+ "duplicate raw document key {:?}" ,
184+ k
185+ ) ) ) ;
186+ }
167187 this. append ( k, v. to_raw_bson ( ) ) ;
168188 }
169189 Ok ( ( ) )
170190}
171191
192+ pub ( crate ) fn append_ser (
193+ this : & mut RawDocumentBuf ,
194+ key : impl AsRef < str > ,
195+ value : impl Serialize ,
196+ ) -> Result < ( ) > {
197+ #[ derive( Serialize ) ]
198+ struct Helper < T > {
199+ value : T ,
200+ }
201+ let raw_doc = bson:: to_raw_document_buf ( & Helper { value } ) ?;
202+ this. append_ref (
203+ key,
204+ raw_doc
205+ . get ( "value" ) ?
206+ . ok_or_else ( || Error :: internal ( "no value" ) ) ?,
207+ ) ;
208+ Ok ( ( ) )
209+ }
210+
172211/// Returns the _id field of this document, prepending the field to the document if one is not
173212/// already present.
174213pub ( crate ) fn get_or_prepend_id_field ( doc : & mut RawDocumentBuf ) -> Result < Bson > {
0 commit comments