Skip to main content

openstack_sdk_identity/v3/endpoint/
set.rs

1// Licensed under the Apache License, Version 2.0 (the "License");
2// you may not use this file except in compliance with the License.
3// You may obtain a copy of the License at
4//
5//     http://www.apache.org/licenses/LICENSE-2.0
6//
7// Unless required by applicable law or agreed to in writing, software
8// distributed under the License is distributed on an "AS IS" BASIS,
9// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
10// See the License for the specific language governing permissions and
11// limitations under the License.
12//
13// SPDX-License-Identifier: Apache-2.0
14//
15// WARNING: This file is automatically generated from OpenAPI schema using
16// `openstack-codegenerator`.
17
18//! Updates an endpoint.
19//!
20//! Relationship:
21//! `https://docs.openstack.org/api/openstack-identity/3/rel/endpoint`
22//!
23use derive_builder::Builder;
24use http::{HeaderMap, HeaderName, HeaderValue};
25
26use openstack_sdk_core::api::rest_endpoint_prelude::*;
27
28use serde::Deserialize;
29use serde::Serialize;
30use serde_json::Value;
31use std::borrow::Cow;
32use std::collections::BTreeMap;
33
34#[derive(Debug, Deserialize, Clone, Serialize)]
35pub enum Interface {
36    #[serde(rename = "admin")]
37    Admin,
38    #[serde(rename = "internal")]
39    Internal,
40    #[serde(rename = "public")]
41    Public,
42}
43
44/// An `endpoint` object.
45#[derive(Builder, Debug, Deserialize, Clone, Serialize)]
46#[builder(setter(strip_option))]
47pub struct Endpoint<'a> {
48    /// The endpoint description. It is returned only when set on the resource.
49    #[serde(skip_serializing_if = "Option::is_none")]
50    #[builder(default, setter(into))]
51    pub(crate) description: Option<Option<Cow<'a, str>>>,
52
53    /// Indicates whether the endpoint appears in the service catalog: -
54    /// `false`. The endpoint does not appear in the service catalog. - `true`.
55    /// The endpoint appears in the service catalog.
56    #[serde(skip_serializing_if = "Option::is_none")]
57    #[builder(default, setter(into))]
58    pub(crate) enabled: Option<bool>,
59
60    /// The interface type, which describes the visibility of the endpoint.
61    /// Value is: - `public`. Visible by end users on a publicly available
62    /// network interface. - `internal`. Visible by end users on an unmetered
63    /// internal network interface. - `admin`. Visible by administrative users
64    /// on a secure network interface.
65    #[serde(skip_serializing_if = "Option::is_none")]
66    #[builder(default)]
67    pub(crate) interface: Option<Interface>,
68
69    /// (Deprecated) The endpoint name. The field will only be returned in
70    /// responses when set on the resource.
71    ///
72    /// This field is deprecated as it provides no value. Endpoints are better
73    /// described by the combination of service, region and interface they
74    /// describe or by their ID.
75    #[serde(skip_serializing_if = "Option::is_none")]
76    #[builder(default, setter(into))]
77    pub(crate) name: Option<Cow<'a, str>>,
78
79    /// (Deprecated in v3.2) The geographic location of the service endpoint.
80    #[serde(skip_serializing_if = "Option::is_none")]
81    #[builder(default, setter(into))]
82    pub(crate) region: Option<Option<Cow<'a, str>>>,
83
84    /// (Since v3.2) The ID of the region that contains the service endpoint.
85    #[serde(skip_serializing_if = "Option::is_none")]
86    #[builder(default, setter(into))]
87    pub(crate) region_id: Option<Option<Cow<'a, str>>>,
88
89    /// The UUID of the service to which the endpoint belongs.
90    #[serde(skip_serializing_if = "Option::is_none")]
91    #[builder(default, setter(into))]
92    pub(crate) service_id: Option<Cow<'a, str>>,
93
94    /// The endpoint URL.
95    #[serde(skip_serializing_if = "Option::is_none")]
96    #[builder(default, setter(into))]
97    pub(crate) url: Option<Cow<'a, str>>,
98
99    #[builder(setter(name = "_properties"), default, private)]
100    #[serde(flatten)]
101    _properties: BTreeMap<Cow<'a, str>, Value>,
102}
103
104impl<'a> EndpointBuilder<'a> {
105    pub fn properties<I, K, V>(&mut self, iter: I) -> &mut Self
106    where
107        I: Iterator<Item = (K, V)>,
108        K: Into<Cow<'a, str>>,
109        V: Into<Value>,
110    {
111        self._properties
112            .get_or_insert_with(BTreeMap::new)
113            .extend(iter.map(|(k, v)| (k.into(), v.into())));
114        self
115    }
116}
117
118#[derive(Builder, Debug, Clone)]
119#[builder(setter(strip_option))]
120pub struct Request<'a> {
121    /// An `endpoint` object.
122    #[builder(setter(into))]
123    pub(crate) endpoint: Endpoint<'a>,
124
125    /// endpoint_id parameter for /v3/endpoints/{endpoint_id} API
126    #[builder(default, setter(into))]
127    id: Cow<'a, str>,
128
129    #[builder(setter(name = "_headers"), default, private)]
130    _headers: Option<HeaderMap>,
131}
132impl<'a> Request<'a> {
133    /// Create a builder for the endpoint.
134    pub fn builder() -> RequestBuilder<'a> {
135        RequestBuilder::default()
136    }
137}
138
139impl<'a> RequestBuilder<'a> {
140    /// Add a single header to the Endpoint.
141    pub fn header<K, V>(&mut self, header_name: K, header_value: V) -> &mut Self
142    where
143        K: Into<HeaderName>,
144        V: Into<HeaderValue>,
145    {
146        self._headers
147            .get_or_insert(None)
148            .get_or_insert_with(HeaderMap::new)
149            .insert(header_name.into(), header_value.into());
150        self
151    }
152
153    /// Add multiple headers.
154    pub fn headers<I, T>(&mut self, iter: I) -> &mut Self
155    where
156        I: Iterator<Item = T>,
157        T: Into<(Option<HeaderName>, HeaderValue)>,
158    {
159        self._headers
160            .get_or_insert(None)
161            .get_or_insert_with(HeaderMap::new)
162            .extend(iter.map(Into::into));
163        self
164    }
165}
166
167impl RestEndpoint for Request<'_> {
168    fn method(&self) -> http::Method {
169        http::Method::PATCH
170    }
171
172    fn endpoint(&self) -> Cow<'static, str> {
173        format!("endpoints/{id}", id = self.id.as_ref(),).into()
174    }
175
176    fn parameters(&self) -> QueryParams<'_> {
177        QueryParams::default()
178    }
179
180    fn body(&self) -> Result<Option<(&'static str, Vec<u8>)>, BodyError> {
181        let mut params = JsonBodyParams::default();
182
183        params.push("endpoint", serde_json::to_value(&self.endpoint)?);
184
185        params.into_body()
186    }
187
188    fn service_type(&self) -> ServiceType {
189        ServiceType::Identity
190    }
191
192    fn response_key(&self) -> Option<Cow<'static, str>> {
193        Some("endpoint".into())
194    }
195
196    /// Returns headers to be set into the request
197    fn request_headers(&self) -> Option<&HeaderMap> {
198        self._headers.as_ref()
199    }
200
201    /// Returns required API version
202    fn api_version(&self) -> Option<ApiVersion> {
203        Some(ApiVersion::new(3, 0))
204    }
205}
206
207#[cfg(test)]
208mod tests {
209    use super::*;
210    use http::{HeaderName, HeaderValue};
211    use httpmock::MockServer;
212    #[cfg(feature = "sync")]
213    use openstack_sdk_core::api::Query;
214    use openstack_sdk_core::test::client::FakeOpenStackClient;
215    use openstack_sdk_core::types::ServiceType;
216    use serde_json::json;
217
218    #[test]
219    fn test_service_type() {
220        assert_eq!(
221            Request::builder()
222                .endpoint(EndpointBuilder::default().build().unwrap())
223                .build()
224                .unwrap()
225                .service_type(),
226            ServiceType::Identity
227        );
228    }
229
230    #[test]
231    fn test_response_key() {
232        assert_eq!(
233            Request::builder()
234                .endpoint(EndpointBuilder::default().build().unwrap())
235                .build()
236                .unwrap()
237                .response_key()
238                .unwrap(),
239            "endpoint"
240        );
241    }
242
243    #[cfg(feature = "sync")]
244    #[test]
245    fn endpoint() {
246        let server = MockServer::start();
247        let client = FakeOpenStackClient::new(server.base_url());
248        let mock = server.mock(|when, then| {
249            when.method(httpmock::Method::PATCH)
250                .path(format!("/endpoints/{id}", id = "id",));
251
252            then.status(200)
253                .header("content-type", "application/json")
254                .json_body(json!({ "endpoint": {} }));
255        });
256
257        let endpoint = Request::builder()
258            .id("id")
259            .endpoint(EndpointBuilder::default().build().unwrap())
260            .build()
261            .unwrap();
262        let _: serde_json::Value = endpoint.query(&client).unwrap();
263        mock.assert();
264    }
265
266    #[cfg(feature = "sync")]
267    #[test]
268    fn endpoint_headers() {
269        let server = MockServer::start();
270        let client = FakeOpenStackClient::new(server.base_url());
271        let mock = server.mock(|when, then| {
272            when.method(httpmock::Method::PATCH)
273                .path(format!("/endpoints/{id}", id = "id",))
274                .header("foo", "bar")
275                .header("not_foo", "not_bar");
276            then.status(200)
277                .header("content-type", "application/json")
278                .json_body(json!({ "endpoint": {} }));
279        });
280
281        let endpoint = Request::builder()
282            .id("id")
283            .endpoint(EndpointBuilder::default().build().unwrap())
284            .headers(
285                [(
286                    Some(HeaderName::from_static("foo")),
287                    HeaderValue::from_static("bar"),
288                )]
289                .into_iter(),
290            )
291            .header(
292                HeaderName::from_static("not_foo"),
293                HeaderValue::from_static("not_bar"),
294            )
295            .build()
296            .unwrap();
297        let _: serde_json::Value = endpoint.query(&client).unwrap();
298        mock.assert();
299    }
300}