1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
use std::io::{ErrorKind, Write};
use std::fs::{self, File};
use chrono::{DateTime, Local};
use crate::utils;
#[derive(Debug)]
pub enum SessionStatus {
Started(DateTime<Local>),
NotStarted,
}
#[derive(Debug)]
pub struct Session<'a> {
started_at: Option<DateTime<Local>>,
ended_at: Option<DateTime<Local>>,
session_dir: &'a str,
session_path: String,
pub status: SessionStatus,
session_name: &'a str,
}
impl Session<'_> {
pub fn new<'a>(session_dir: &'a str, session_name: &'a str) -> Session<'a> {
let session_path = format!("{}/{}", session_dir, session_name);
let status = Session::get_status(&session_path);
let started_at = match status {
SessionStatus::Started(secs) => Some(secs),
SessionStatus::NotStarted => None,
};
Session {
started_at,
ended_at: None,
session_dir,
status,
session_path,
session_name,
}
}
fn get_status(path: &str) -> SessionStatus {
match fs::metadata(&path) {
Ok(metadata) => SessionStatus::Started(utils::get_metadata_created(metadata)),
Err(e) => {
if e.kind() == ErrorKind::NotFound {
SessionStatus::NotStarted
} else {
panic!("error getting session metadata: {}", e);
}
}
}
}
pub fn start(&self) -> DateTime<Local> {
if let SessionStatus::Started(_) = self.status {
panic!("Tried to start a session that is already started.");
}
match File::create(&self.session_path) {
Ok(file) => match file.metadata() {
Ok(metadata) => utils::get_metadata_created(metadata),
Err(e) => panic!("error getting session start time: {}", e),
},
Err(e) => panic!("error creating session file: {}", e),
}
}
pub fn end(&mut self) -> DateTime<Local> {
if let SessionStatus::NotStarted = self.status {
panic!("Tried to end a session that hasn't been started.");
}
if let Err(e) = fs::remove_file(&self.session_path) {
panic!("error removing session file: {}", e);
}
let ended_at = Local::now();
self.ended_at = Some(ended_at.clone());
ended_at
}
pub fn record(&self, log_name: &str) {
let log_file_path = format!("{}/{}", self.session_dir, log_name);
let mut file = utils::create_or_open_file(&log_file_path);
let start = self.started_at.unwrap();
let end = self.ended_at.unwrap();
let start_dt = utils::format_datetime(&start);
let end_dt = utils::format_datetime(&end);
let session_record = format!("{},{}\n", &start_dt, &end_dt);
file.write(&session_record.as_bytes()).unwrap_or_else(|e| {
let session_info = format!("start,end,length\n{}", &session_record);
panic!("Error logging session:\n{}\nerror: {}", &session_info, e);
});
}
}