jirust_cli/runners/jira_cmd_runners/issue_cmd_runner.rs
1use jira_v3_openapi::apis::issue_search_api::search_for_issues_using_jql_post;
2use jira_v3_openapi::apis::issues_api::*;
3use jira_v3_openapi::models::user::AccountType;
4use jira_v3_openapi::models::{
5 CreatedIssue, IssueBean, IssueTransition, SearchRequestBean, Transitions, User,
6};
7use jira_v3_openapi::{apis::configuration::Configuration, models::IssueUpdateDetails};
8use serde_json::Value;
9use std::collections::HashMap;
10use std::io::Error;
11
12use crate::args::commands::TransitionArgs;
13use crate::{
14 args::commands::IssueArgs,
15 config::config_file::{AuthData, ConfigFile},
16};
17
18/// Issue command runner
19/// This struct is responsible for running the issue command
20/// It uses the Jira API to perform the operations
21///
22/// # Fields
23///
24/// * `cfg` - Configuration object
25pub struct IssueCmdRunner {
26 /// Configuration object
27 cfg: Configuration,
28}
29
30/// Implementation of IssueCmdRunner
31///
32/// # Methods
33///
34/// * `new` - Creates a new instance of IssueCmdRunner
35/// * `assign_jira_issue` - Assigns a Jira issue to a user
36/// * `create_jira_issue` - Creates a Jira issue
37/// * `delete_jira_issue` - Deletes a Jira issue
38/// * `get_jira_issue` - Gets a Jira issue
39/// * `transition_jira_issue` - Transitions a Jira issue
40/// * `update_jira_issue` - Updates a Jira issue
41/// * `get_issue_available_transitions` - Gets available transitions for a Jira issue
42impl IssueCmdRunner {
43 /// Creates a new instance of IssueCmdRunner
44 ///
45 /// # Arguments
46 ///
47 /// * `cfg_file` - Configuration file
48 ///
49 /// # Returns
50 ///
51 /// * `IssueCmdRunner` - Instance of IssueCmdRunner
52 ///
53 /// # Examples
54 ///
55 /// ```
56 /// use jirust_cli::config::config_file::ConfigFile;
57 /// use jirust_cli::runners::jira_cmd_runners::issue_cmd_runner::IssueCmdRunner;
58 /// use toml::Table;
59 ///
60 /// let cfg_file = ConfigFile::new("dXNlcm5hbWU6YXBpX2tleQ==".to_string(), "jira_url".to_string(), "standard_resolution".to_string(), "standard_resolution_comment".to_string(), Table::new());
61 ///
62 /// let issue_cmd_runner = IssueCmdRunner::new(&cfg_file);
63 /// ```
64 pub fn new(cfg_file: &ConfigFile) -> IssueCmdRunner {
65 let mut config = Configuration::new();
66 let auth_data = AuthData::from_base64(cfg_file.get_auth_key());
67 config.base_path = cfg_file.get_jira_url().to_string();
68 config.basic_auth = Some((auth_data.0, Some(auth_data.1)));
69 IssueCmdRunner { cfg: config }
70 }
71
72 /// Assigns a Jira issue to a user
73 ///
74 /// # Arguments
75 ///
76 /// * `params` - Issue command parameters
77 ///
78 /// # Returns
79 ///
80 /// * `Value` - JSON value
81 ///
82 /// # Examples
83 ///
84 /// ```no_run
85 /// use jirust_cli::runners::jira_cmd_runners::issue_cmd_runner::{IssueCmdRunner, IssueCmdParams};
86 /// use jirust_cli::config::config_file::ConfigFile;
87 /// use toml::Table;
88 ///
89 /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
90 /// # tokio_test::block_on(async {
91 /// let cfg_file = ConfigFile::new("dXNlcm5hbWU6YXBpX2tleQ==".to_string(), "jira_url".to_string(), "standard_resolution".to_string(), "standard_resolution_comment".to_string(), Table::new());
92 /// let issue_cmd_runner = IssueCmdRunner::new(&cfg_file);
93 /// let mut params = IssueCmdParams::new();
94 /// params.assignee = Some("assignee".to_string());
95 ///
96 /// let result = issue_cmd_runner.assign_jira_issue(params).await?;
97 /// # Ok(())
98 /// # })
99 /// # }
100 /// ```
101 pub async fn assign_jira_issue(
102 &self,
103 params: IssueCmdParams,
104 ) -> Result<Value, Box<dyn std::error::Error>> {
105 let user_data = User {
106 account_id: Some(params.assignee.expect("Assignee is required")),
107 account_type: Some(AccountType::Atlassian),
108 ..Default::default()
109 };
110
111 let i_key = if let Some(key) = ¶ms.issue_key {
112 key.as_str()
113 } else {
114 return Err(Box::new(Error::other(
115 "Error assigning issue: Empty issue key".to_string(),
116 )));
117 };
118
119 Ok(assign_issue(&self.cfg, i_key, user_data).await?)
120 }
121
122 /// Creates a Jira issue
123 ///
124 /// # Arguments
125 ///
126 /// * `params` - Issue command parameters
127 ///
128 /// # Returns
129 ///
130 /// * `CreatedIssue` - Created issue
131 ///
132 /// # Examples
133 ///
134 /// ```no_run
135 /// use jirust_cli::runners::jira_cmd_runners::issue_cmd_runner::{IssueCmdRunner, IssueCmdParams};
136 /// use jirust_cli::config::config_file::ConfigFile;
137 /// use toml::Table;
138 ///
139 /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
140 /// # tokio_test::block_on(async {
141 /// let cfg_file = ConfigFile::new("dXNlcm5hbWU6YXBpX2tleQ==".to_string(), "jira_url".to_string(), "standard_resolution".to_string(), "standard_resolution_comment".to_string(), Table::new());
142 /// let issue_cmd_runner = IssueCmdRunner::new(&cfg_file);
143 /// let params = IssueCmdParams::new();
144 ///
145 /// let result = issue_cmd_runner.create_jira_issue(params).await?;
146 /// # Ok(())
147 /// # })
148 /// # }
149 /// ```
150 pub async fn create_jira_issue(
151 &self,
152 params: IssueCmdParams,
153 ) -> Result<CreatedIssue, Box<dyn std::error::Error>> {
154 let mut issue_fields = params.issue_fields.unwrap_or_default();
155 issue_fields.insert(
156 "project".to_string(),
157 serde_json::json!({"key": params.project_key.expect("Project Key is required to create an issue!")}),
158 );
159 let issue_data = IssueUpdateDetails {
160 fields: Some(issue_fields),
161 history_metadata: None,
162 properties: None,
163 transition: None,
164 update: None,
165 };
166 Ok(create_issue(&self.cfg, issue_data, None).await?)
167 }
168
169 /// Deletes a Jira issue
170 ///
171 /// # Arguments
172 ///
173 /// * `params` - Issue command parameters
174 ///
175 /// # Returns
176 ///
177 /// * `()` - Empty tuple
178 ///
179 /// # Examples
180 ///
181 /// ```no_run
182 /// use jirust_cli::runners::jira_cmd_runners::issue_cmd_runner::{IssueCmdRunner, IssueCmdParams};
183 /// use jirust_cli::config::config_file::ConfigFile;
184 /// use toml::Table;
185 ///
186 /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
187 /// # tokio_test::block_on(async {
188 /// let cfg_file = ConfigFile::new("dXNlcm5hbWU6YXBpX2tleQ==".to_string(), "jira_url".to_string(), "standard_resolution".to_string(), "standard_resolution_comment".to_string(), Table::new());
189 /// let issue_cmd_runner = IssueCmdRunner::new(&cfg_file);
190 /// let mut params = IssueCmdParams::new();
191 /// params.issue_key = Some("issue_key".to_string());
192 ///
193 /// let result = issue_cmd_runner.delete_jira_issue(params).await?;
194 /// # Ok(())
195 /// # })
196 /// # }
197 /// ```
198 pub async fn delete_jira_issue(
199 &self,
200 params: IssueCmdParams,
201 ) -> Result<(), Box<dyn std::error::Error>> {
202 let i_key = if let Some(key) = ¶ms.issue_key {
203 key.as_str()
204 } else {
205 return Err(Box::new(Error::other(
206 "Error deleting issue: Empty issue key".to_string(),
207 )));
208 };
209
210 Ok(delete_issue(&self.cfg, i_key, Some("true")).await?)
211 }
212
213 /// Gets a Jira issue
214 ///
215 /// # Arguments
216 ///
217 /// * `params` - Issue command parameters
218 ///
219 /// # Returns
220 ///
221 /// * `IssueBean` - Jira issue
222 ///
223 /// # Examples
224 ///
225 /// ```no_run
226 /// use jirust_cli::runners::jira_cmd_runners::issue_cmd_runner::{IssueCmdRunner, IssueCmdParams};
227 /// use jirust_cli::config::config_file::ConfigFile;
228 /// use toml::Table;
229 ///
230 /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
231 /// # tokio_test::block_on(async {
232 /// let cfg_file = ConfigFile::new("dXNlcm5hbWU6YXBpX2tleQ==".to_string(), "jira_url".to_string(), "standard_resolution".to_string(), "standard_resolution_comment".to_string(), Table::new());
233 /// let issue_cmd_runner = IssueCmdRunner::new(&cfg_file);
234 /// let mut params = IssueCmdParams::new();
235 /// params.issue_key = Some("issue_key".to_string());
236 ///
237 /// let result = issue_cmd_runner.get_jira_issue(params).await?;
238 /// # Ok(())
239 /// # })
240 /// # }
241 /// ```
242 pub async fn get_jira_issue(
243 &self,
244 params: IssueCmdParams,
245 ) -> Result<IssueBean, Box<dyn std::error::Error>> {
246 let i_key = if let Some(key) = ¶ms.issue_key {
247 key.as_str()
248 } else {
249 return Err(Box::new(Error::other(
250 "Error retrieving issue: Empty issue key".to_string(),
251 )));
252 };
253 Ok(get_issue(&self.cfg, i_key, None, None, None, None, None, None).await?)
254 }
255
256 /// This method searches for Jira issues using the provided JQL query parameters.
257 ///
258 /// # Arguments
259 ///
260 /// * `params` - Issue command parameters
261 ///
262 /// # Returns
263 ///
264 /// * `Vec<IssueBean>` - A vector of Jira issue beans
265 ///
266 /// # Examples
267 ///
268 /// ```no_run
269 /// use jirust_cli::runners::jira_cmd_runners::issue_cmd_runner::{IssueCmdRunner, IssueCmdParams};
270 /// use jirust_cli::config::config_file::ConfigFile;
271 /// use toml::Table;
272 ///
273 /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
274 /// # tokio_test::block_on(async {
275 /// let cfg_file = ConfigFile::new("dXNlcm5hbWU6YXBpX2tleQ==".to_string(), "jira_url".to_string(), "standard_resolution".to_string(), "standard_resolution_comment".to_string(), Table::new());
276 /// let issue_cmd_runner = IssueCmdRunner::new(&cfg_file);
277 /// let mut params = IssueCmdParams::new();
278 /// params.query = Some("field=value".to_string());
279 ///
280 /// let result = issue_cmd_runner.search_jira_issues(params).await?;
281 /// # Ok(())
282 /// # })
283 /// # }
284 /// ```
285 pub async fn search_jira_issues(
286 &self,
287 params: IssueCmdParams,
288 ) -> Result<Vec<IssueBean>, Box<dyn std::error::Error>> {
289 let search_params: SearchRequestBean = SearchRequestBean {
290 jql: params.query,
291 ..Default::default()
292 };
293 match search_for_issues_using_jql_post(&self.cfg, search_params).await {
294 Ok(result) => {
295 if let Some(issues) = result.issues {
296 Ok(issues)
297 } else {
298 Ok(vec![])
299 }
300 }
301 Err(e) => Err(Box::new(e)),
302 }
303 }
304
305 /// Transitions a Jira issue
306 ///
307 /// # Arguments
308 ///
309 /// * `params` - Issue command parameters
310 ///
311 /// # Returns
312 ///
313 /// * `Value` - Jira issue transition
314 ///
315 /// # Examples
316 ///
317 /// ```no_run
318 /// use jirust_cli::runners::jira_cmd_runners::issue_cmd_runner::{IssueCmdRunner, IssueCmdParams};
319 /// use jirust_cli::config::config_file::ConfigFile;
320 /// use toml::Table;
321 ///
322 /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
323 /// # tokio_test::block_on(async {
324 /// let cfg_file = ConfigFile::new("dXNlcm5hbWU6YXBpX2tleQ==".to_string(), "jira_url".to_string(), "standard_resolution".to_string(), "standard_resolution_comment".to_string(), Table::new());
325 /// let issue_cmd_runner = IssueCmdRunner::new(&cfg_file);
326 ///
327 /// let mut params = IssueCmdParams::new();
328 /// params.transition = Some("transition_id".to_string());
329 ///
330 /// let result = issue_cmd_runner.transition_jira_issue(params).await?;
331 /// # Ok(())
332 /// # })
333 /// # }
334 /// ```
335 pub async fn transition_jira_issue(
336 &self,
337 params: IssueCmdParams,
338 ) -> Result<Value, Box<dyn std::error::Error>> {
339 let i_key = if let Some(key) = ¶ms.issue_key {
340 key.as_str()
341 } else {
342 return Err(Box::new(Error::other(
343 "Error with issue transition: Empty issue key".to_string(),
344 )));
345 };
346
347 let trans = if let Some(transition) = ¶ms.transition {
348 transition.as_str()
349 } else {
350 return Err(Box::new(Error::other(
351 "Error with issue transition: Empty transition".to_string(),
352 )));
353 };
354
355 let transition = IssueTransition {
356 id: Some(trans.to_string()),
357 ..Default::default()
358 };
359 let issue_data = IssueUpdateDetails {
360 fields: params.issue_fields,
361 history_metadata: None,
362 properties: None,
363 transition: Some(transition),
364 update: None,
365 };
366 Ok(do_transition(&self.cfg, i_key, issue_data).await?)
367 }
368
369 /// Updates a Jira issue
370 ///
371 /// # Arguments
372 ///
373 /// * `params` - Issue command parameters
374 ///
375 /// # Returns
376 ///
377 /// * `Value` - Jira issue update
378 ///
379 /// # Examples
380 ///
381 /// ```no_run
382 /// use jirust_cli::runners::jira_cmd_runners::issue_cmd_runner::{IssueCmdRunner, IssueCmdParams};
383 /// use jirust_cli::config::config_file::ConfigFile;
384 /// use toml::Table;
385 ///
386 /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
387 /// # tokio_test::block_on(async {
388 /// let cfg_file = ConfigFile::new("dXNlcm5hbWU6YXBpX2tleQ==".to_string(), "jira_url".to_string(), "standard_resolution".to_string(), "standard_resolution_comment".to_string(), Table::new());
389 /// let issue_cmd_runner = IssueCmdRunner::new(&cfg_file);
390 /// let params = IssueCmdParams::new();
391 ///
392 /// let result = issue_cmd_runner.update_jira_issue(params).await?;
393 /// # Ok(())
394 /// # })
395 /// # }
396 /// ```
397 pub async fn update_jira_issue(
398 &self,
399 params: IssueCmdParams,
400 ) -> Result<Value, Box<dyn std::error::Error>> {
401 let i_key = if let Some(key) = ¶ms.issue_key {
402 key.as_str()
403 } else {
404 return Err(Box::new(Error::other(
405 "Error updating issue: Empty issue key".to_string(),
406 )));
407 };
408
409 let issue_data = IssueUpdateDetails {
410 fields: params.issue_fields,
411 history_metadata: None,
412 properties: None,
413 transition: None,
414 update: None,
415 };
416 Ok(edit_issue(
417 &self.cfg,
418 i_key,
419 issue_data,
420 None,
421 None,
422 None,
423 Some(true),
424 None,
425 )
426 .await?)
427 }
428
429 /// Gets available transitions for a Jira issue
430 ///
431 /// # Arguments
432 ///
433 /// * `params` - Issue command parameters
434 ///
435 /// # Returns
436 ///
437 /// * `Transitions` - Jira issue transitions
438 ///
439 /// # Examples
440 ///
441 /// ```no_run
442 /// use jirust_cli::runners::jira_cmd_runners::issue_cmd_runner::{IssueCmdRunner, IssueTransitionCmdParams};
443 /// use jirust_cli::config::config_file::ConfigFile;
444 /// use toml::Table;
445 ///
446 /// # fn main() -> Result<(), Box<dyn std::error::Error>> {
447 /// # tokio_test::block_on(async {
448 /// let cfg_file = ConfigFile::new("dXNlcm5hbWU6YXBpX2tleQ==".to_string(), "jira_url".to_string(), "standard_resolution".to_string(), "standard_resolution_comment".to_string(), Table::new());
449 /// let issue_cmd_runner = IssueCmdRunner::new(&cfg_file);
450 /// let mut params = IssueTransitionCmdParams::new();
451 /// params.issue_key = "issue_key".to_string();
452 ///
453 /// let result = issue_cmd_runner.get_issue_available_transitions(params).await?;
454 /// # Ok(())
455 /// # })
456 /// # }
457 /// ```
458 pub async fn get_issue_available_transitions(
459 &self,
460 params: IssueTransitionCmdParams,
461 ) -> Result<Transitions, Box<dyn std::error::Error>> {
462 Ok(get_transitions(
463 &self.cfg,
464 ¶ms.issue_key,
465 None,
466 None,
467 None,
468 Some(false),
469 None,
470 )
471 .await?)
472 }
473}
474
475/// Issue command parameters
476///
477/// # Fields
478///
479/// * `project_key` - Jira project key
480/// * `issue_key` - Jira issue key
481/// * `issue_fields` - Jira issue fields
482/// * `transition` - Jira issue transition
483/// * `assignee` - Jira issue assignee
484/// * `query` - Jira issue query
485pub struct IssueCmdParams {
486 /// Jira project key
487 pub project_key: Option<String>,
488 /// Jira issue key
489 pub issue_key: Option<String>,
490 /// Jira issue fields
491 pub issue_fields: Option<HashMap<String, Value>>,
492 /// Jira issue transition
493 pub transition: Option<String>,
494 /// Jira issue assignee
495 pub assignee: Option<String>,
496 /// Jira issue query
497 pub query: Option<String>,
498}
499
500/// Implementation of IssueCmdParams struct
501///
502/// # Methods
503///
504/// * `new` - Creates a new IssueCmdParams instance
505impl IssueCmdParams {
506 /// Creates a new IssueCmdParams instance
507 ///
508 /// # Returns
509 ///
510 /// * `IssueCmdParams` - Issue command parameters
511 ///
512 /// # Examples
513 ///
514 /// ```
515 /// use jirust_cli::runners::jira_cmd_runners::issue_cmd_runner::IssueCmdParams;
516 ///
517 /// let params = IssueCmdParams::new();
518 /// ```
519 pub fn new() -> IssueCmdParams {
520 IssueCmdParams {
521 project_key: Some("".to_string()),
522 issue_key: None,
523 issue_fields: None,
524 transition: None,
525 assignee: None,
526 query: None,
527 }
528 }
529}
530
531/// Implementation of From trait for IssueCmdParams struct
532/// to convert IssueArgs struct to IssueCmdParams struct
533impl From<&IssueArgs> for IssueCmdParams {
534 /// Converts IssueArgs struct to IssueCmdParams struct
535 /// to create a new IssueCmdParams instance
536 ///
537 /// # Arguments
538 ///
539 /// * `value` - IssueArgs struct
540 ///
541 /// # Returns
542 ///
543 /// * `IssueCmdParams` - Issue command parameters
544 ///
545 /// # Examples
546 ///
547 /// ```
548 /// use jirust_cli::runners::jira_cmd_runners::issue_cmd_runner::IssueCmdParams;
549 /// use jirust_cli::args::commands::{IssueArgs, PaginationArgs, OutputArgs, IssueActionValues};
550 /// use std::collections::HashMap;
551 /// use serde_json::Value;
552 ///
553 /// let issue_args = IssueArgs {
554 /// issue_act: IssueActionValues::Get,
555 /// project_key: Some("project_key".to_string()),
556 /// issue_key: Some("issue_key".to_string()),
557 /// issue_fields: Some(vec![("key".to_string(), r#"{ "key": "value" }"#.to_string())]),
558 /// transition_to: Some("transition_to".to_string()),
559 /// assignee: Some("assignee".to_string()),
560 /// query: None,
561 /// pagination: PaginationArgs { page_size: Some(20), page_offset: None },
562 /// output: OutputArgs { output_format: None, output_type: None },
563 /// };
564 ///
565 /// let params = IssueCmdParams::from(&issue_args);
566 ///
567 /// assert_eq!(params.project_key, Some("project_key".to_string()));
568 /// assert_eq!(params.issue_key.unwrap(), "issue_key".to_string());
569 /// assert_eq!(params.transition.unwrap(), "transition_to".to_string());
570 /// assert_eq!(params.assignee.unwrap(), "assignee".to_string());
571 /// ```
572 fn from(value: &IssueArgs) -> Self {
573 IssueCmdParams {
574 project_key: value.project_key.clone(),
575 issue_key: value.issue_key.clone(),
576 issue_fields: Some(
577 value
578 .issue_fields
579 .clone()
580 .unwrap_or_default()
581 .iter()
582 .map(|elem| {
583 (
584 elem.0.clone(),
585 serde_json::from_str(elem.1.clone().as_str()).unwrap_or(Value::Null),
586 )
587 })
588 .collect::<HashMap<_, _>>(),
589 ),
590 transition: value.transition_to.clone(),
591 assignee: value.assignee.clone(),
592 query: value.query.clone(),
593 }
594 }
595}
596
597/// Issue transition command parameters
598///
599/// # Fields
600///
601/// * `issue_key` - Jira issue key
602pub struct IssueTransitionCmdParams {
603 /// Jira issue key
604 pub issue_key: String,
605}
606
607/// Implementation of IssueTransitionCmdParams struct
608///
609/// # Methods
610///
611/// * `new` - Creates a new IssueTransitionCmdParams instance
612impl IssueTransitionCmdParams {
613 /// Creates a new IssueTransitionCmdParams instance
614 ///
615 /// # Returns
616 ///
617 /// * `IssueTransitionCmdParams` - Issue transition command parameters
618 ///
619 /// # Examples
620 ///
621 /// ```
622 /// use jirust_cli::runners::jira_cmd_runners::issue_cmd_runner::IssueTransitionCmdParams;
623 ///
624 /// let params = IssueTransitionCmdParams::new();
625 /// ```
626 pub fn new() -> IssueTransitionCmdParams {
627 IssueTransitionCmdParams {
628 issue_key: "".to_string(),
629 }
630 }
631}
632
633/// Implementation of From trait for IssueTransitionCmdParams struct
634/// to convert TransitionArgs struct to IssueTransitionCmdParams struct
635impl From<&TransitionArgs> for IssueTransitionCmdParams {
636 /// Converts TransitionArgs struct to IssueTransitionCmdParams struct
637 /// to create a new IssueTransitionCmdParams instance
638 ///
639 /// # Arguments
640 ///
641 /// * `value` - TransitionArgs struct
642 ///
643 /// # Returns
644 ///
645 /// * `IssueTransitionCmdParams` - Issue transition command parameters
646 ///
647 /// # Examples
648 ///
649 /// ```
650 /// use jirust_cli::runners::jira_cmd_runners::issue_cmd_runner::IssueTransitionCmdParams;
651 /// use jirust_cli::args::commands::{TransitionArgs, TransitionActionValues, OutputArgs};
652 ///
653 /// let transition_args = TransitionArgs {
654 /// transition_act: TransitionActionValues::List,
655 /// issue_key: "issue_key".to_string(),
656 /// output: OutputArgs { output_format: None, output_type: None },
657 /// };
658 ///
659 /// let params = IssueTransitionCmdParams::from(&transition_args);
660 ///
661 /// assert_eq!(params.issue_key, "issue_key".to_string());
662 /// ```
663 fn from(value: &TransitionArgs) -> Self {
664 IssueTransitionCmdParams {
665 issue_key: value.issue_key.clone(),
666 }
667 }
668}
669
670/// Default implementation for IssueCmdParams struct
671impl Default for IssueTransitionCmdParams {
672 /// Creates a default IssueTransitionCmdParams instance
673 ///
674 /// # Returns
675 ///
676 /// A IssueTransitionCmdParams instance with default values
677 ///
678 /// # Examples
679 ///
680 /// ```
681 /// use jirust_cli::runners::jira_cmd_runners::issue_cmd_runner::IssueTransitionCmdParams;
682 ///
683 /// let params = IssueTransitionCmdParams::default();
684 ///
685 /// assert_eq!(params.issue_key, "".to_string());
686 /// ```
687 fn default() -> Self {
688 IssueTransitionCmdParams::new()
689 }
690}
691
692/// Default implementation for IssueCmdParams struct
693impl Default for IssueCmdParams {
694 /// Creates a default IssueCmdParams instance
695 ///
696 /// # Returns
697 ///
698 /// A IssueCmdParams instance with default values
699 ///
700 /// # Examples
701 ///
702 /// ```
703 /// use jirust_cli::runners::jira_cmd_runners::issue_cmd_runner::IssueCmdParams;
704 ///
705 /// let params = IssueCmdParams::default();
706 ///
707 /// assert_eq!(params.project_key, Some("".to_string()));
708 /// assert_eq!(params.issue_key, None);
709 /// assert_eq!(params.issue_fields, None);
710 /// assert_eq!(params.transition, None);
711 /// assert_eq!(params.assignee, None);
712 /// ```
713 fn default() -> Self {
714 IssueCmdParams::new()
715 }
716}