Skip to main content

ironflow_ops_gitlab/endpoints/
merge_requests.rs

1//! Merge request routes missing from the `gitlab` crate:
2//! `POST /projects/:id/merge_requests/:iid/discussions/:discussion_id/notes`,
3//! `PUT /projects/:id/merge_requests/:iid/discussions/:discussion_id`,
4//! `GET /projects/:id/merge_requests/:iid/versions[/:version_id]` and
5//! `DELETE /projects/:id/merge_requests/:iid/notes/:note_id`.
6
7use std::borrow::Cow;
8
9use gitlab::api::common::NameOrId;
10use gitlab::api::endpoint_prelude::{BodyError, Endpoint, FormParams, Method};
11
12/// Add a note (reply) to an existing merge request discussion.
13///
14/// Maps to `POST /projects/:id/merge_requests/:merge_request/discussions/:discussion_id/notes`.
15///
16/// # Examples
17///
18/// ```no_run
19/// use ironflow_ops_gitlab::GitLab;
20/// use ironflow_ops_gitlab::endpoints::merge_requests::CreateMergeRequestDiscussionNote;
21/// use gitlab::api::common::NameOrId;
22///
23/// # async fn example() -> Result<(), ironflow_core::error::OperationError> {
24/// let gitlab = GitLab::new("glpat-xxxx", "gitlab.com").await?;
25/// let endpoint = CreateMergeRequestDiscussionNote {
26///     project: NameOrId::from(42),
27///     merge_request: 7,
28///     discussion_id: "abcd1234".to_string(),
29///     body: "Looks good, thanks!".to_string(),
30/// };
31/// let op = gitlab.op(endpoint);
32/// # Ok(())
33/// # }
34/// ```
35///
36/// # Errors
37///
38/// Returns an error if the request fails or the response cannot be deserialized (e.g. the
39/// project, merge request or discussion does not exist).
40pub struct CreateMergeRequestDiscussionNote {
41    /// The project the merge request belongs to.
42    pub project: NameOrId<'static>,
43    /// The internal ID (`iid`) of the merge request.
44    pub merge_request: u64,
45    /// The ID of the discussion thread to reply to.
46    pub discussion_id: String,
47    /// The text of the note.
48    pub body: String,
49}
50
51impl Endpoint for CreateMergeRequestDiscussionNote {
52    fn method(&self) -> Method {
53        Method::POST
54    }
55
56    fn endpoint(&self) -> Cow<'static, str> {
57        format!(
58            "projects/{}/merge_requests/{}/discussions/{}/notes",
59            self.project, self.merge_request, self.discussion_id,
60        )
61        .into()
62    }
63
64    fn body(&self) -> Result<Option<(&'static str, Vec<u8>)>, BodyError> {
65        let mut params = FormParams::default();
66        params.push("body", self.body.as_str());
67        params.into_body()
68    }
69}
70
71/// Resolve or unresolve an existing merge request discussion.
72///
73/// Maps to `PUT /projects/:id/merge_requests/:merge_request/discussions/:discussion_id`.
74///
75/// # Examples
76///
77/// ```no_run
78/// use ironflow_ops_gitlab::GitLab;
79/// use ironflow_ops_gitlab::endpoints::merge_requests::ResolveMergeRequestDiscussion;
80/// use gitlab::api::common::NameOrId;
81///
82/// # async fn example() -> Result<(), ironflow_core::error::OperationError> {
83/// let gitlab = GitLab::new("glpat-xxxx", "gitlab.com").await?;
84/// let endpoint = ResolveMergeRequestDiscussion {
85///     project: NameOrId::from(42),
86///     merge_request: 7,
87///     discussion_id: "abcd1234".to_string(),
88///     resolved: true,
89/// };
90/// let op = gitlab.op(endpoint);
91/// # Ok(())
92/// # }
93/// ```
94///
95/// # Errors
96///
97/// Returns an error if the request fails or the response cannot be deserialized (e.g. the
98/// project, merge request or discussion does not exist).
99pub struct ResolveMergeRequestDiscussion {
100    /// The project the merge request belongs to.
101    pub project: NameOrId<'static>,
102    /// The internal ID (`iid`) of the merge request.
103    pub merge_request: u64,
104    /// The ID of the discussion thread to resolve or unresolve.
105    pub discussion_id: String,
106    /// Whether the discussion should be marked resolved.
107    pub resolved: bool,
108}
109
110impl Endpoint for ResolveMergeRequestDiscussion {
111    fn method(&self) -> Method {
112        Method::PUT
113    }
114
115    fn endpoint(&self) -> Cow<'static, str> {
116        format!(
117            "projects/{}/merge_requests/{}/discussions/{}",
118            self.project, self.merge_request, self.discussion_id,
119        )
120        .into()
121    }
122
123    fn body(&self) -> Result<Option<(&'static str, Vec<u8>)>, BodyError> {
124        let mut params = FormParams::default();
125        params.push("resolved", self.resolved);
126        params.into_body()
127    }
128}
129
130/// List the diff versions of a merge request, newest first.
131///
132/// Maps to `GET /projects/:id/merge_requests/:merge_request/versions`. Each
133/// version carries `head_commit_sha`, `base_commit_sha` and `start_commit_sha`:
134/// one version per push, which tells a rebase from a content change.
135///
136/// # Examples
137///
138/// ```no_run
139/// use ironflow_ops_gitlab::GitLab;
140/// use ironflow_ops_gitlab::endpoints::merge_requests::MergeRequestVersions;
141/// use gitlab::api::common::NameOrId;
142///
143/// # async fn example() -> Result<(), ironflow_core::error::OperationError> {
144/// let gitlab = GitLab::new("glpat-xxxx", "gitlab.com").await?;
145/// let endpoint = MergeRequestVersions {
146///     project: NameOrId::from("group/project"),
147///     merge_request: 7,
148/// };
149/// let op = gitlab.op(endpoint);
150/// # Ok(())
151/// # }
152/// ```
153///
154/// # Errors
155///
156/// Returns an error if the request fails (e.g. the project or merge request
157/// does not exist).
158pub struct MergeRequestVersions {
159    /// The project the merge request belongs to.
160    pub project: NameOrId<'static>,
161    /// The internal ID (`iid`) of the merge request.
162    pub merge_request: u64,
163}
164
165impl Endpoint for MergeRequestVersions {
166    fn method(&self) -> Method {
167        Method::GET
168    }
169
170    fn endpoint(&self) -> Cow<'static, str> {
171        format!(
172            "projects/{}/merge_requests/{}/versions",
173            self.project, self.merge_request,
174        )
175        .into()
176    }
177}
178
179/// Read one diff version of a merge request, with its `diffs`.
180///
181/// Maps to `GET /projects/:id/merge_requests/:merge_request/versions/:version_id`.
182///
183/// # Examples
184///
185/// ```no_run
186/// use ironflow_ops_gitlab::GitLab;
187/// use ironflow_ops_gitlab::endpoints::merge_requests::MergeRequestVersion;
188/// use gitlab::api::common::NameOrId;
189///
190/// # async fn example() -> Result<(), ironflow_core::error::OperationError> {
191/// let gitlab = GitLab::new("glpat-xxxx", "gitlab.com").await?;
192/// let endpoint = MergeRequestVersion {
193///     project: NameOrId::from(42),
194///     merge_request: 7,
195///     version: 3,
196/// };
197/// let op = gitlab.op(endpoint);
198/// # Ok(())
199/// # }
200/// ```
201///
202/// # Errors
203///
204/// Returns an error if the request fails (e.g. the version does not exist).
205pub struct MergeRequestVersion {
206    /// The project the merge request belongs to.
207    pub project: NameOrId<'static>,
208    /// The internal ID (`iid`) of the merge request.
209    pub merge_request: u64,
210    /// The ID of the diff version, from [`MergeRequestVersions`].
211    pub version: u64,
212}
213
214impl Endpoint for MergeRequestVersion {
215    fn method(&self) -> Method {
216        Method::GET
217    }
218
219    fn endpoint(&self) -> Cow<'static, str> {
220        format!(
221            "projects/{}/merge_requests/{}/versions/{}",
222            self.project, self.merge_request, self.version,
223        )
224        .into()
225    }
226}
227
228/// Delete a note of a merge request.
229///
230/// Maps to `DELETE /projects/:id/merge_requests/:merge_request/notes/:note_id`.
231/// GitLab answers `204 No Content`, which [`GitLab::op`](crate::GitLab::op)
232/// returns as `Value::Null`.
233///
234/// # Examples
235///
236/// ```no_run
237/// use ironflow_ops_gitlab::GitLab;
238/// use ironflow_ops_gitlab::endpoints::merge_requests::DeleteMergeRequestNote;
239/// use gitlab::api::common::NameOrId;
240///
241/// # async fn example() -> Result<(), ironflow_core::error::OperationError> {
242/// let gitlab = GitLab::new("glpat-xxxx", "gitlab.com").await?;
243/// let endpoint = DeleteMergeRequestNote {
244///     project: NameOrId::from(42),
245///     merge_request: 7,
246///     note: 1234,
247/// };
248/// let op = gitlab.op(endpoint);
249/// # Ok(())
250/// # }
251/// ```
252///
253/// # Errors
254///
255/// Returns an error if the request fails (e.g. the note does not exist or the
256/// token may not delete it).
257pub struct DeleteMergeRequestNote {
258    /// The project the merge request belongs to.
259    pub project: NameOrId<'static>,
260    /// The internal ID (`iid`) of the merge request.
261    pub merge_request: u64,
262    /// The ID of the note to delete.
263    pub note: u64,
264}
265
266impl Endpoint for DeleteMergeRequestNote {
267    fn method(&self) -> Method {
268        Method::DELETE
269    }
270
271    fn endpoint(&self) -> Cow<'static, str> {
272        format!(
273            "projects/{}/merge_requests/{}/notes/{}",
274            self.project, self.merge_request, self.note,
275        )
276        .into()
277    }
278}