diff --git a/src/storage/src/model_ext.rs b/src/storage/src/model_ext.rs index 7a336aae74..d3c24d1a62 100644 --- a/src/storage/src/model_ext.rs +++ b/src/storage/src/model_ext.rs @@ -310,6 +310,61 @@ pub struct WriteObjectRequest { pub params: Option, } +#[cfg(google_cloud_unstable_storage_bidi)] +/// Represents the parameters of a request to open a new object for exclusive appends. +/// +/// This type might be used in mocks of the `Storage` client. +#[derive(Debug, PartialEq)] +#[non_exhaustive] +pub struct OpenAppendableObjectRequest { + /// The object attributes and pre-conditions for the open operation. + pub spec: Box, + /// Additional request parameters. + pub params: Option, +} + +#[cfg(google_cloud_unstable_storage_bidi)] +/// Represents the parameters of a request to reopen an existing object for appends. +/// +/// This type might be used in mocks of the `Storage` client. +#[derive(Debug, PartialEq)] +#[non_exhaustive] +pub struct ReopenAppendableObjectRequest { + /// The bucket containing the target object. + pub bucket: String, + /// The target object name. + pub object: String, + /// The target object generation to append to. + pub generation: i64, + /// If set, return an error if the current metageneration does not match the value. + pub if_metageneration_match: Option, + /// If set, return an error if the current metageneration matches the value. + pub if_metageneration_not_match: Option, + /// A routing token from a previous operation. + pub routing_token: Option, + /// A write handle from a previous operation. + pub write_handle: Option, + /// Additional request parameters. + pub params: Option, +} + +#[cfg(google_cloud_unstable_storage_bidi)] +impl From for crate::google::storage::v2::AppendObjectSpec { + fn from(value: ReopenAppendableObjectRequest) -> Self { + Self { + bucket: value.bucket, + object: value.object, + generation: value.generation, + if_metageneration_match: value.if_metageneration_match, + if_metageneration_not_match: value.if_metageneration_not_match, + routing_token: value.routing_token, + write_handle: value + .write_handle + .map(|h| crate::google::storage::v2::BidiWriteHandle { handle: h }), + } + } +} + #[cfg(test)] pub(crate) mod tests { use super::*; @@ -429,4 +484,44 @@ pub(crate) mod tests { assert_eq!(key_aes_256.to_string(), key_base64); Ok(()) } + + #[cfg(google_cloud_unstable_storage_bidi)] + #[test] + fn test_open_appendable_object_request() { + let req = OpenAppendableObjectRequest { + spec: Box::new(crate::model::WriteObjectSpec::default()), + params: None, + }; + assert_eq!(req.spec.resource, None); + assert_eq!(req.params, None); + } + + #[cfg(google_cloud_unstable_storage_bidi)] + #[test] + fn test_reopen_appendable_object_request_from() { + let req = ReopenAppendableObjectRequest { + bucket: "my-bucket".into(), + object: "my-object".into(), + generation: 42, + if_metageneration_match: Some(1), + if_metageneration_not_match: Some(2), + routing_token: Some("token".into()), + write_handle: Some(bytes::Bytes::from("handle")), + params: None, + }; + + let spec = crate::google::storage::v2::AppendObjectSpec::from(req); + assert_eq!(spec.bucket, "my-bucket"); + assert_eq!(spec.object, "my-object"); + assert_eq!(spec.generation, 42); + assert_eq!(spec.if_metageneration_match, Some(1)); + assert_eq!(spec.if_metageneration_not_match, Some(2)); + assert_eq!(spec.routing_token, Some("token".into())); + assert_eq!( + spec.write_handle, + Some(crate::google::storage::v2::BidiWriteHandle { + handle: bytes::Bytes::from("handle") + }) + ); + } } diff --git a/src/storage/src/storage.rs b/src/storage/src/storage.rs index accfcabf9d..6dbbb5cfc2 100644 --- a/src/storage/src/storage.rs +++ b/src/storage/src/storage.rs @@ -12,6 +12,8 @@ // See the License for the specific language governing permissions and // limitations under the License. +#[cfg(google_cloud_unstable_storage_bidi)] +pub(crate) mod append_object; pub(crate) mod bidi; pub(crate) mod checksum; pub(crate) mod client; diff --git a/src/storage/src/storage/append_object.rs b/src/storage/src/storage/append_object.rs new file mode 100644 index 0000000000..0b69b45ddf --- /dev/null +++ b/src/storage/src/storage/append_object.rs @@ -0,0 +1,15 @@ +// Copyright 2025 Google LLC +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +//! Appendable object uploads (unstable).