diff --git a/src/db.rs b/src/db.rs index 4df284e..6728edc 100644 --- a/src/db.rs +++ b/src/db.rs @@ -1,14 +1,23 @@ use base64::prelude::*; +use once_cell::sync::Lazy; + use std::collections::HashSet; use std::hash::{Hash, Hasher}; use std::fs; +use std::path::Path; use std::io::{self, Write, BufRead}; use std::fmt; use std::cmp::{PartialEq, Ordering}; +static STORAGE_FOLDER: String = "storage"; +static STORAGE_PATH: Lazy = Lazy::new(|| { + format!("{}/db.mps", STORAGE_FOLDER) +}); + + pub struct Item { pub id: String, pub content: String @@ -89,6 +98,7 @@ pub struct DB { } impl DB { + // TODO: make path as String too pub fn new(path: &str, password: String) -> io::Result { let encoder = Encoder::from(password); // TODO: throw error is password is incorrect @@ -120,6 +130,25 @@ impl DB { Ok(result) } + pub fn init(passphrase: String) -> io::Result<()> { + fs::create_dir(STORAGE_FOLDER)?; + println!("Storage folder created"); + //let mut db = DB::init(&*STORAGE_PATH, pass)?; + + fs::File::create(&*STORAGE_PATH)?; + println!("Storage db created."); + println!("Initialization complete."); + println!(""); + println!("Now it's required to add folder `{}` under git manually.", STORAGE_FOLDER); + println!("Don't worry it's going to be encrypted."); + + } + + pub fn is_inited() -> bool { + let path = Path::new(STORAGE_FOLDER); + return path.exists(); + } + pub fn contains(&self, id: &String) -> bool { let item = Item::from_empty(id.clone()); self.items.contains(&item) diff --git a/src/main.rs b/src/main.rs index b13cd1f..6fd7c5a 100644 --- a/src/main.rs +++ b/src/main.rs @@ -7,20 +7,11 @@ use db::{DB, Item}; use clap::{Parser, Subcommand}; use rpassword; -use once_cell::sync::Lazy; - use std::fs; use std::io::{self, Write}; -use std::path::Path; use std::process; -static STORAGE_FOLDER: &str = "storage"; -static STORAGE_PATH: Lazy = Lazy::new(|| { - format!("{}/db.mps", STORAGE_FOLDER) -}); - - #[derive(Parser)] #[command(name = "mps", version = "0.0.1", about = "MyPasswordStorage: Tool for storing your passwords locally with git synchronization")] struct Cli { @@ -70,56 +61,43 @@ fn get_prompt(question: &str) -> io::Result { } // TODO: change password functionality - fn login() -> io::Result { - println!("Enter passphrase: "); + // TODO: check if inited + print!("Enter passphrase for storage: "); + io::stdout().flush()?; // TODO: check in db // TODO: return error if db is not inited let password = rpassword::read_password()?; if password != "pass" { - return Err(io::Error::new(io::ErrorKind::InvalidData, "Wrong password")); + return Err(io::Error::new(io::ErrorKind::InvalidData, "Wrong passphrase")); } Ok(String::from(password)) } -fn is_inited() -> bool { - let path = Path::new(STORAGE_FOLDER); - return path.exists(); -} - fn init() -> io::Result<()> { - if is_inited() { + if db::DB::is_inited() { return Err(io::Error::new(io::ErrorKind::AlreadyExists, "Reinitialization attempted")); } - print!("Enter passphrase for db: "); + print!("Enter passphrase for storage: "); io::stdout().flush()?; + // TODO: rename to passphrase let password = rpassword::read_password()?; print!("Reenter passphrase: "); io::stdout().flush()?; let password2 = rpassword::read_password()?; if password != password2 { - return Err(io::Error::new(io::ErrorKind::InvalidInput, "Passwords should be equal")); + return Err(io::Error::new(io::ErrorKind::InvalidInput, "Passwords must be equal")); } - fs::create_dir(STORAGE_FOLDER)?; - println!("Storage folder created"); - //let mut db = DB::init(&*STORAGE_PATH, pass)?; - - // TODO: enter password - // TODO: dont create storate if master password hasn't entered + db:::DB::init(password)?; - fs::File::create(&*STORAGE_PATH)?; - println!("Storage db created."); - println!("Initialization complete."); - println!(""); - println!("Now it's required to add folder `{}` under git manually.", STORAGE_FOLDER); - println!("Don't worry it's going to be encrypted."); Ok(()) } fn add(id: &String) -> io::Result<()> { - let mut db = DB::new(&*STORAGE_PATH, String::from(""))?; + // TODO: get login passphrase + let mut db = DB::new(String::from(""))?; if db.contains(id) { // TODO: ask to edit existing in outer function which invoked this one return Err(io::Error::new( @@ -131,12 +109,12 @@ fn add(id: &String) -> io::Result<()> { let content = editor::open_to_edit()?; db.items.insert(Item::from(id.clone(), content)); db.dump()?; - + Ok(()) } fn list() -> io:: Result<()> { - let db = DB::new(&STORAGE_PATH, String::from(""))?; + let db = DB::new(String::from(""))?; let mut vec: Vec<_> = db.items.iter().collect(); vec.sort(); for item in &vec { @@ -158,7 +136,7 @@ fn run_command() -> io::Result<()> { list()?; } None => { - if !is_inited() { + if !db::DB::is_inited() { match get_prompt("Do you want to init your storage?")? { PROMPT::YES => init()?, PROMPT::NO => { @@ -167,7 +145,7 @@ fn run_command() -> io::Result<()> { println!(" git clone {}", STORAGE_FOLDER); println!("to init manually your storage and config") }, - } + } } else { login()?; } @@ -184,5 +162,5 @@ fn main() { process::exit(2); // TODO: better codes for different errors } } - } +