Add installed versions tracking

This commit is contained in:
Augusto Gunsch 2022-01-09 14:39:06 -03:00
parent 47f65f8a96
commit 8925fb87a9
No known key found for this signature in database
GPG Key ID: F7EEFE29825C72DC
4 changed files with 61 additions and 16 deletions

View File

@ -13,6 +13,7 @@ use serde_json;
use crate::language::Language; use crate::language::Language;
use crate::entry::{WiktionaryEntries, WiktionaryEntry}; use crate::entry::{WiktionaryEntries, WiktionaryEntry};
use crate::entry::Form; use crate::entry::Form;
use crate::{MAJOR, MINOR, PATCH};
const DB_DIR: &str = "/usr/share/inflectived/"; const DB_DIR: &str = "/usr/share/inflectived/";
const CACHE_DIR: &str = "/var/cache/"; const CACHE_DIR: &str = "/var/cache/";
@ -38,7 +39,15 @@ impl WordDb {
let mut conn = self.connect(); let mut conn = self.connect();
let transaction = conn.transaction().unwrap(); let transaction = conn.transaction().unwrap();
if let Err(e) = transaction.execute(&format!("DROP TABLE IF EXISTS {0}_words", &lang.code), []) { if let Err(e) = transaction.execute("
CREATE TABLE IF NOT EXISTS langs (
id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,
code TINYTEXT UNIQUE NOT NULL,
name TINYTEXT NOT NULL,
major INTEGER NOT NULL,
minor INTEGER NOT NULL,
patch INTEGER NOT NULL
)", []) {
match e { match e {
SqliteFailure(f, _) => match f.code { SqliteFailure(f, _) => match f.code {
ErrorCode::ReadOnly => { ErrorCode::ReadOnly => {
@ -52,12 +61,15 @@ impl WordDb {
} }
} }
transaction.execute("DELETE FROM langs WHERE code = ?", [&lang.code]).unwrap();
transaction.execute(&format!("DROP TABLE IF EXISTS {0}_words", &lang.code), []).unwrap();
transaction.execute(&format!("DROP TABLE IF EXISTS {0}_types", &lang.code), []).unwrap(); transaction.execute(&format!("DROP TABLE IF EXISTS {0}_types", &lang.code), []).unwrap();
transaction.execute(&format!(" transaction.execute(&format!("
CREATE TABLE {0}_types ( CREATE TABLE {0}_types (
id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL, id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,
name TINYTEXT UNIQUE NOT NULL name TINYTEXT UNIQUE NOT NULL
)", &lang.code), []).unwrap(); )", &lang.code), []).unwrap();
for type_ in &lang.types { for type_ in &lang.types {
@ -70,12 +82,12 @@ impl WordDb {
transaction.execute(&format!(" transaction.execute(&format!("
CREATE TABLE {0}_words ( CREATE TABLE {0}_words (
id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL, id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,
word TINYTEXT NOT NULL, word TINYTEXT NOT NULL,
type_id INTEGER NOT NULL, type_id INTEGER NOT NULL,
content MEDIUMTEXT NOT NULL, content MEDIUMTEXT NOT NULL,
FOREIGN KEY (type_id) FOREIGN KEY (type_id)
REFERENCES {0}_types (id) REFERENCES {0}_types (id)
)", &lang.code), []).unwrap(); )", &lang.code), []).unwrap();
transaction.execute(&format!(" transaction.execute(&format!("
@ -83,6 +95,11 @@ impl WordDb {
ON {0}_words (word) ON {0}_words (word)
", &lang.code), []).unwrap(); ", &lang.code), []).unwrap();
transaction.execute("
INSERT INTO langs (code, name, major, minor, patch)
VALUES (?, ?, ?, ?, ?)
", params![&lang.code, &lang.name, MAJOR, MINOR, PATCH]).unwrap();
transaction.commit().unwrap(); transaction.commit().unwrap();
} }

View File

@ -1,13 +1,15 @@
#[derive(Debug)] #[derive(Debug)]
pub struct Language { pub struct Language {
pub code: String, pub code: String,
pub name: String,
pub types: Vec<String> pub types: Vec<String>
} }
impl Language { impl Language {
pub fn new(code: &str, types: Vec<String>) -> Self { pub fn new(code: &str, name: &str, types: Vec<String>) -> Self {
Self { Self {
code: String::from(code), code: String::from(code),
name: String::from(name),
types types
} }
} }

View File

@ -8,11 +8,16 @@ use clap::{App, AppSettings, Arg, SubCommand};
mod database; mod database;
mod language; mod language;
mod entry; mod entry;
mod routes; mod views;
use database::WordDb; use database::WordDb;
use language::Language; use language::Language;
const MAJOR: i32 = 0;
const MINOR: i32 = 1;
const PATCH: i32 = 0;
#[rocket::main] #[rocket::main]
async fn main() { async fn main() {
let matches = App::new("inflectived") let matches = App::new("inflectived")
@ -51,7 +56,8 @@ async fn main() {
let mut db = WordDb::new("inflectived.db"); let mut db = WordDb::new("inflectived.db");
let lang = Language::new("polish", let lang = Language::new("pl",
"Polish",
vec![String::from("adj"), vec![String::from("adj"),
String::from("noun"), String::from("noun"),
String::from("verb"), String::from("verb"),
@ -84,9 +90,10 @@ async fn main() {
rocket::custom(figment) rocket::custom(figment)
.manage(db) .manage(db)
.mount("/static", FileServer::from("static/")) .mount("/static", FileServer::from("static/"))
.mount("/", routes![routes::get_entries, .mount("/", routes![views::get_entries,
routes::get_entries_like, views::get_entries_like,
routes::frontend]) views::get_langs,
views::frontend])
.launch() .launch()
.await.unwrap(); .await.unwrap();
}, },

View File

@ -9,7 +9,7 @@ use rusqlite::params;
use crate::database::WordDb; use crate::database::WordDb;
#[get("/frontend")] #[get("/")]
pub fn frontend() -> Option<content::Html<String>> { pub fn frontend() -> Option<content::Html<String>> {
match fs::read_to_string("static/index.html") { match fs::read_to_string("static/index.html") {
Ok(file) => Some(content::Html(file)), Ok(file) => Some(content::Html(file)),
@ -70,3 +70,22 @@ pub fn get_entries_like(db: &State<WordDb>, lang: &str, like: &str, limit: usize
Json(words) Json(words)
} }
#[get("/langs?<installed>")]
pub fn get_langs(db: &State<WordDb>, installed: bool) -> Json<Vec<String>> {
let conn = db.connect();
let mut langs: Vec<String> = Vec::new();
if installed {
let mut statement = conn.prepare("SELECT name FROM langs").unwrap();
let mut rows = statement.query([]).unwrap();
while let Some(row) = rows.next().unwrap() {
langs.push(row.get(0).unwrap());
}
}
Json(langs)
}