2026-08-24 11:35:37 +03:00
|
|
|
use crate::core::srs::WordOpenMode;
|
|
|
|
|
use crate::data::Id;
|
2026-08-24 23:10:23 +03:00
|
|
|
use crate::data::entities::HistoryItem;
|
2026-08-24 01:22:00 +03:00
|
|
|
use crate::fs::*;
|
2026-08-24 11:35:37 +03:00
|
|
|
use crate::notification::NotificationData::PermissionDenied;
|
2026-08-25 12:04:07 +03:00
|
|
|
use crate::notification::{MaybeError, NotificationData};
|
2026-08-28 17:44:14 +03:00
|
|
|
use chrono::{DateTime, NaiveDate};
|
2026-07-29 12:57:46 +03:00
|
|
|
use std::fs::{File, OpenOptions};
|
|
|
|
|
use std::io::Write;
|
|
|
|
|
use std::io::{BufRead, BufReader};
|
|
|
|
|
use std::path::PathBuf;
|
2026-08-28 17:44:14 +03:00
|
|
|
use rusqlite::Connection;
|
|
|
|
|
|
|
|
|
|
pub fn get_open_count_of_set(id: Id, connection: &Connection) -> Result<Vec<(NaiveDate, u32)>, NotificationData>{
|
|
|
|
|
todo!()
|
|
|
|
|
}
|
2026-07-29 12:57:46 +03:00
|
|
|
|
2026-08-24 01:22:00 +03:00
|
|
|
pub fn get_history_of_set(id: Id) -> Result<Vec<HistoryItem>, NotificationData> {
|
|
|
|
|
let app_dir = history_dir()?;
|
2026-07-29 12:57:46 +03:00
|
|
|
let head = app_dir.clone().join(format!("set_{}_history.csv", id));
|
|
|
|
|
let mut lines = Vec::new();
|
|
|
|
|
|
2026-08-24 23:48:00 +03:00
|
|
|
append_lines_if_exists(head, &mut lines)?;
|
2026-08-01 23:40:56 +03:00
|
|
|
lines.reverse();
|
2026-08-24 01:22:00 +03:00
|
|
|
Ok(parse_history_items(lines))
|
2026-07-29 12:57:46 +03:00
|
|
|
}
|
|
|
|
|
|
2026-08-24 23:42:58 +03:00
|
|
|
fn append_lines_if_exists(path: PathBuf, lines: &mut Vec<String>) -> MaybeError {
|
2026-07-29 12:57:46 +03:00
|
|
|
if path.exists() {
|
2026-08-24 23:10:23 +03:00
|
|
|
let reader = BufReader::new(File::open(path).map_err(|_| PermissionDenied)?);
|
|
|
|
|
reader
|
|
|
|
|
.lines()
|
|
|
|
|
.map_while(Result::ok)
|
|
|
|
|
.for_each(|i| lines.push(i));
|
2026-07-29 12:57:46 +03:00
|
|
|
}
|
2026-08-24 23:10:23 +03:00
|
|
|
Ok(())
|
2026-07-29 12:57:46 +03:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
fn parse_history_items(strings: Vec<String>) -> Vec<HistoryItem> {
|
|
|
|
|
let mut items = Vec::with_capacity(strings.len());
|
|
|
|
|
for string in strings {
|
|
|
|
|
if let [time, word, mode, before, after] = string.split(';').collect::<Vec<&str>>()[..] {
|
2026-08-19 23:37:59 +03:00
|
|
|
let id = word.parse::<Id>();
|
2026-08-19 23:51:41 +03:00
|
|
|
if id.is_err() {
|
2026-08-19 23:37:59 +03:00
|
|
|
continue;
|
|
|
|
|
}
|
2026-08-24 23:10:23 +03:00
|
|
|
let id = id.unwrap_or_default();
|
2026-08-19 23:37:59 +03:00
|
|
|
if !id.is_valid() {
|
|
|
|
|
continue;
|
|
|
|
|
}
|
2026-07-29 12:57:46 +03:00
|
|
|
items.push(HistoryItem {
|
2026-08-24 23:10:23 +03:00
|
|
|
timestamp: DateTime::from_timestamp(time.parse().unwrap_or_default(), 0)
|
|
|
|
|
.unwrap_or_default(),
|
2026-08-19 23:37:59 +03:00
|
|
|
word_id: id,
|
|
|
|
|
mode: match mode.parse::<u8>().unwrap_or_default() {
|
2026-07-29 12:57:46 +03:00
|
|
|
2 => WordOpenMode::Hard,
|
|
|
|
|
3 => WordOpenMode::Ok,
|
|
|
|
|
4 => WordOpenMode::Easy,
|
|
|
|
|
_ => WordOpenMode::None,
|
|
|
|
|
},
|
2026-08-19 23:37:59 +03:00
|
|
|
before: before.parse().unwrap_or_default(),
|
|
|
|
|
after: after.parse().unwrap_or_default(),
|
2026-07-29 12:57:46 +03:00
|
|
|
});
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
items
|
|
|
|
|
}
|
|
|
|
|
|
2026-08-24 23:42:58 +03:00
|
|
|
pub fn push_note(set_id: Id, item: HistoryItem) -> MaybeError {
|
2026-08-24 01:22:00 +03:00
|
|
|
let app_dir = history_dir()?;
|
2026-07-29 12:57:46 +03:00
|
|
|
let path = app_dir.clone().join(format!("set_{}_history.csv", set_id));
|
2026-08-01 19:43:07 +03:00
|
|
|
|
|
|
|
|
let mut file = OpenOptions::new()
|
|
|
|
|
.create(true)
|
|
|
|
|
.append(true)
|
|
|
|
|
.open(path)
|
2026-08-24 01:22:00 +03:00
|
|
|
.map_err(|_| PermissionDenied)?;
|
2026-08-01 19:43:07 +03:00
|
|
|
let line_str = format!(
|
|
|
|
|
"{};{};{};{};{}",
|
|
|
|
|
item.timestamp.timestamp(),
|
|
|
|
|
item.word_id,
|
|
|
|
|
match item.mode {
|
|
|
|
|
WordOpenMode::Easy => 4,
|
|
|
|
|
WordOpenMode::Ok => 3,
|
|
|
|
|
WordOpenMode::Hard => 2,
|
|
|
|
|
WordOpenMode::None => 1,
|
|
|
|
|
},
|
|
|
|
|
item.before,
|
|
|
|
|
item.after
|
|
|
|
|
);
|
2026-08-24 01:22:00 +03:00
|
|
|
writeln!(&mut file, "{}", line_str).map_err(|_| PermissionDenied)?;
|
|
|
|
|
Ok(())
|
2026-08-04 16:53:09 +03:00
|
|
|
}
|