Skip to content

Commit

Permalink
feat: [torrust#56] trasnfer user data from v1.0.0 to v2.0.0
Browse files Browse the repository at this point in the history
TODO: transfer password
  • Loading branch information
josecelano committed Nov 30, 2022
1 parent d590972 commit d1059f5
Show file tree
Hide file tree
Showing 3 changed files with 132 additions and 1 deletion.
19 changes: 19 additions & 0 deletions src/upgrades/from_v1_0_0_to_v2_0_0/databases/sqlite_v1_0_0.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,17 @@ pub struct Category {
pub category_id: i64,
pub name: String,
}

#[derive(Debug, Serialize, Deserialize, sqlx::FromRow)]
pub struct User {
pub user_id: i64,
pub username: String,
pub email: String,
pub email_verified: bool,
pub password: String,
pub administrator: bool,
}

pub struct SqliteDatabaseV1_0_0 {
pub pool: SqlitePool,
}
Expand All @@ -30,4 +41,12 @@ impl SqliteDatabaseV1_0_0 {
.await
.map_err(|_| DatabaseError::Error)
}

pub async fn get_users(&self) -> Result<Vec<User>, sqlx::Error> {
query_as::<_, User>(
"SELECT * FROM torrust_users ORDER BY user_id ASC",
)
.fetch_all(&self.pool)
.await
}
}
38 changes: 38 additions & 0 deletions src/upgrades/from_v1_0_0_to_v2_0_0/databases/sqlite_v2_0_0.rs
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,44 @@ impl SqliteDatabaseV2_0_0 {
})
}

pub async fn insert_user(
&self,
user_id: i64,
date_registered: &str,
administrator: bool,
) -> Result<i64, sqlx::Error> {
query(
"INSERT INTO torrust_users (user_id, date_registered, administrator) VALUES (?, ?, ?)",
)
.bind(user_id)
.bind(date_registered)
.bind(administrator)
.execute(&self.pool)
.await
.map(|v| v.last_insert_rowid())
}

pub async fn insert_user_profile(
&self,
user_id: i64,
username: &str,
email: &str,
email_verified: bool,
bio: &str,
avatar: &str,
) -> Result<i64, sqlx::Error> {
query("INSERT INTO torrust_user_profiles (user_id, username, email, email_verified, bio, avatar) VALUES (?, ?, ?, ?, ?, ?)")
.bind(user_id)
.bind(username)
.bind(email)
.bind(email_verified)
.bind(bio)
.bind(avatar)
.execute(&self.pool)
.await
.map(|v| v.last_insert_rowid())
}

pub async fn delete_all_database_rows(&self) -> Result<(), DatabaseError> {
query("DELETE FROM torrust_categories;")
.execute(&self.pool)
Expand Down
76 changes: 75 additions & 1 deletion src/upgrades/from_v1_0_0_to_v2_0_0/upgrader.rs
Original file line number Diff line number Diff line change
@@ -1,9 +1,24 @@
//! It updates the application from version v1.0.0 to v2.0.0.
//!
//! NOTES for `torrust_users` table transfer:
//!
//! - In v2, the table `torrust_user` contains a field `date_registered` non existing in v1.
//! It's used the day when the upgrade command is executed.
//! - In v2, the table `torrust_user_profiles` contains two new fields: `bio` and `avatar`.
//! Empty string is used as default value.

use crate::upgrades::from_v1_0_0_to_v2_0_0::databases::sqlite_v1_0_0::SqliteDatabaseV1_0_0;
use crate::upgrades::from_v1_0_0_to_v2_0_0::databases::sqlite_v2_0_0::SqliteDatabaseV2_0_0;
use std::sync::Arc;
use chrono::prelude::{DateTime, Utc};
use std::{sync::Arc, time::SystemTime};

use crate::config::Configuration;

fn today_iso8601() -> String {
let dt: DateTime<Utc> = SystemTime::now().into();
format!("{}", dt.format("%Y-%m-%d"))
}

async fn current_db() -> Arc<SqliteDatabaseV1_0_0> {
// Connect to the old v1.0.0 DB
let cfg = match Configuration::load_from_file().await {
Expand Down Expand Up @@ -75,5 +90,64 @@ pub async fn upgrade() {
reset_destiny_database(dest_database.clone()).await;
transfer_categories(source_database.clone(), dest_database.clone()).await;

// Transfer `torrust_users`

let users = source_database.get_users().await.unwrap();

for user in &users {
// [v2] table torrust_users

println!(
"[v2][torrust_users] adding user: {:?} {:?} ...",
&user.user_id, &user.username
);

let default_data_registered = today_iso8601();

let id = dest_database
.insert_user(user.user_id, &default_data_registered, user.administrator)
.await
.unwrap();

if id != user.user_id {
panic!(
"Error copying user {:?} from source DB to destiny DB",
&user.user_id
);
}

println!(
"[v2][torrust_users] user: {:?} {:?} added.",
&user.user_id, &user.username
);

// [v2] table torrust_user_profiles

println!(
"[v2][torrust_user_profiles] adding user: {:?} {:?} ...",
&user.user_id, &user.username
);

let default_user_bio = "".to_string();
let default_user_avatar = "".to_string();

dest_database
.insert_user_profile(
user.user_id,
&user.username,
&user.email,
user.email_verified,
&default_user_bio,
&default_user_avatar,
)
.await
.unwrap();

println!(
"[v2][torrust_user_profiles] user: {:?} {:?} added.",
&user.user_id, &user.username
);
}

// TODO: WIP. We have to transfer data from the 5 tables in V1 and the torrent files in folder `uploads`.
}

0 comments on commit d1059f5

Please sign in to comment.