2 files changed
+93
-30
src/projects/crud/mod.rs
+30
-1
@@ -1,7 +1,7 @@
1
use crate::{constants::BASE_URL, debug};
2
use anyhow::{anyhow, Result};
3
use reqwest::Client;
4
-use serde::Deserialize;
4
+use serde::{Deserialize, Serialize};
5
6
#[derive(Deserialize, Debug)]
7
pub struct Project {
@@ -10,6 +10,11 @@ pub struct Project {
10
pub created_at: String,
11
pub updated_at: String,
12
}
13
+#[derive(Serialize, Debug)]
14
+pub struct ProjectCreate {
15
+ pub name: String,
16
+ pub description: String,
17
+}
18
19
pub async fn get_all() -> Result<Vec<Project>> {
20
// Get current token
@@ -33,6 +38,30 @@ pub async fn get_all() -> Result<Vec<Project>> {
38
}
39
}
40
41
+pub async fn create_project(project: ProjectCreate) -> Result<Project> {
42
+ // Get current token
43
+ let token = get_token().await.unwrap();
44
+
45
+ let response = Client::new()
46
+ .post([BASE_URL, "v1/projects"].join(""))
47
+ .json(&project)
48
+ .header("Authorization", token)
49
+ .send()
50
+ .await?;
51
+
52
+ match response.status() {
53
+ reqwest::StatusCode::CREATED => {
54
+ let project: Project = response.json().await?;
55
+ println!("Project created: {:#?}", project);
56
+ Ok(project)
57
+ }
58
+ _ => {
59
+ debug!("Failed to create a project.", response.status());
60
+ Err(anyhow!("Failed to create a project."))
61
+ }
62
+ }
63
+}
64
+
65
async fn get_token() -> Result<String> {
66
if let Some(mut path) = dirs::home_dir() {
67
path.push(".smb/token");
src/projects/mod.rs
+63
-29
@@ -3,20 +3,17 @@ mod crud;
3
use anyhow::Result;
4
use clap::Subcommand;
5
use console::style;
6
+use dialoguer::{theme::ColorfulTheme, Input};
7
use spinners::Spinner;
8
9
use crate::util::CommandResult;
10
10
-use self::crud::get_all;
11
+use self::crud::{create_project, get_all, ProjectCreate};
12
13
#[derive(Subcommand)]
14
pub enum Commands {
15
#[clap(about = "Add new project.")]
15
- New {
16
- /// Project name
17
- #[clap(short, long, global = true)]
18
- name: Option<String>,
19
- },
16
+ New {},
17
18
#[clap(about = "List all your projects.")]
19
List {},
@@ -37,24 +34,49 @@ pub enum Commands {
34
}
35
36
pub async fn process(commands: Commands) -> Result<CommandResult> {
40
- let spinner = Spinner::new(
41
- spinners::Spinners::SimpleDotsScrolling,
42
- style("Loading...").green().bold().to_string(),
43
- );
37
match commands {
45
- Commands::New { name } => {
46
- let project_name = match name {
47
- Some(name) => name,
48
- None => "tempe-goreng".to_owned(),
49
- };
38
+ Commands::New {} => {
39
+ let project_name = Input::<String>::with_theme(&ColorfulTheme::default())
40
+ .with_prompt("Project name")
41
+ .interact()
42
+ .unwrap();
43
+ let description = Input::<String>::with_theme(&ColorfulTheme::default())
44
+ .with_prompt("Description")
45
+ .interact()
46
+ .unwrap();
47
51
- Ok(CommandResult {
52
- spinner,
53
- symbol: "✅".to_owned(),
54
- msg: format!("Creating a project {project_name}."),
48
+ let spinner = Spinner::new(
49
+ spinners::Spinners::SimpleDotsScrolling,
50
+ style("Creating project...").green().bold().to_string(),
51
+ );
52
+
53
+ match create_project(ProjectCreate {
54
+ name: project_name.clone(),
55
+ description: description.clone(),
56
})
57
+ .await
58
+ {
59
+ Ok(_) => Ok(CommandResult {
60
+ spinner,
61
+ symbol: "✅".to_owned(),
62
+ msg: format!("Creating a project {project_name}."),
63
+ }),
64
+ Err(e) => {
65
+ println!("Error: {:#?}", e);
66
+ Ok(CommandResult {
67
+ spinner,
68
+ symbol: "❌".to_owned(),
69
+ msg: format!("Failed to create a project {project_name}."),
70
+ })
71
+ }
72
+ }
73
}
74
Commands::List {} => {
75
+ let spinner = Spinner::new(
76
+ spinners::Spinners::SimpleDotsScrolling,
77
+ style("Loading...").green().bold().to_string(),
78
+ );
79
+
80
// Get all
81
match get_all().await {
82
Ok(projects) => {
@@ -85,15 +107,27 @@ pub async fn process(commands: Commands) -> Result<CommandResult> {
107
}
108
}
109
}
88
- Commands::Show { name } => Ok(CommandResult {
89
- spinner,
90
- symbol: "✅".to_owned(),
91
- msg: format!("Showing project {name}."),
92
- }),
93
- Commands::Delete { name } => Ok(CommandResult {
94
- spinner,
95
- symbol: "✅".to_owned(),
96
- msg: format!("Deleting project {name}."),
97
- }),
110
+ Commands::Show { name } => {
111
+ let spinner = Spinner::new(
112
+ spinners::Spinners::SimpleDotsScrolling,
113
+ style("Loading...").green().bold().to_string(),
114
+ );
115
+ Ok(CommandResult {
116
+ spinner,
117
+ symbol: "✅".to_owned(),
118
+ msg: format!("Showing project {name}."),
119
+ })
120
+ }
121
+ Commands::Delete { name } => {
122
+ let spinner = Spinner::new(
123
+ spinners::Spinners::SimpleDotsScrolling,
124
+ style("Loading...").green().bold().to_string(),
125
+ );
126
+ Ok(CommandResult {
127
+ spinner,
128
+ symbol: "✅".to_owned(),
129
+ msg: format!("Deleting project {name}."),
130
+ })
131
+ }
132
}
133
}