Skip to content

Commit

Permalink
feat: allow preventing a reset of the database
Browse files Browse the repository at this point in the history
  • Loading branch information
ctron committed Apr 4, 2024
1 parent 3653677 commit 435c5bb
Show file tree
Hide file tree
Showing 6 changed files with 78 additions and 38 deletions.
85 changes: 59 additions & 26 deletions common/src/db/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -101,6 +101,15 @@ enum DbStrategy {
Managed(Arc<(PostgreSQL, TempDir)>),
}

#[derive(Copy, Clone, Debug, Default, PartialEq, Eq, clap::ValueEnum)]
pub enum CreationMode {
#[default]
Default,
#[value(name("refresh"))]
RefreshSchema,
Bootstrap,
}

#[derive(Clone, Debug)]
pub struct Database {
pub db: DatabaseConnection,
Expand All @@ -115,6 +124,7 @@ impl Database {
port: impl Into<Option<u16>>,
db_name: &str,
db_strategy: DbStrategy,
refresh_schema: bool,
) -> Result<Self, anyhow::Error> {
let port = port.into().unwrap_or(5432);
let url = format!("postgres://{username}:{password}@{host}:{port}/{db_name}");
Expand All @@ -126,9 +136,15 @@ impl Database {

let db = sea_orm::Database::connect(opt).await?;

log::debug!("applying migrations");
Migrator::refresh(&db).await?;
log::debug!("applied migrations");
if refresh_schema {
log::warn!("refreshing database schema...");
Migrator::refresh(&db).await?;
log::warn!("refreshing database schema... done!");
} else {
log::debug!("applying migrations");
Migrator::up(&db, None).await?;
log::debug!("applied migrations");
}

Ok(Self {
db,
Expand All @@ -138,29 +154,45 @@ impl Database {

pub async fn with_external_config(
database: &crate::config::Database,
bootstrap: bool,
creation: CreationMode,
) -> Result<Self, anyhow::Error> {
if bootstrap {
log::warn!("Bootstrapping database");
Self::bootstrap(
&database.username,
&database.password,
&database.host,
database.port,
&database.name,
DbStrategy::External,
)
.await
} else {
Self::new(
&database.username,
&database.password,
&database.host,
database.port,
&database.name,
DbStrategy::External,
)
.await
match creation {
CreationMode::Default => {
Self::new(
&database.username,
&database.password,
&database.host,
database.port,
&database.name,
DbStrategy::External,
false,
)
.await
}
CreationMode::RefreshSchema => {
Self::new(
&database.username,
&database.password,
&database.host,
database.port,
&database.name,
DbStrategy::External,
true,
)
.await
}
CreationMode::Bootstrap => {
log::warn!("Bootstrapping database");
Self::bootstrap(
&database.username,
&database.password,
&database.host,
database.port,
&database.name,
DbStrategy::External,
)
.await
}
}
}

Expand Down Expand Up @@ -226,7 +258,8 @@ impl Database {

db.close().await?;

Self::new(username, password, host, port, db_name, db_strategy).await
// we don't need to refresh the schema as we just re-created the database
Self::new(username, password, host, port, db_name, db_strategy, false).await
}

pub async fn close(self) -> anyhow::Result<()> {
Expand Down
8 changes: 5 additions & 3 deletions common/src/test_util.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
use crate::config::{Database, DbStrategy};
use crate::db;
use crate::{
config::{Database, DbStrategy},
db,
};
use std::sync::Arc;

pub async fn bootstrap_system(name: &str) -> Result<db::Database, anyhow::Error> {
Expand All @@ -12,7 +14,7 @@ pub async fn bootstrap_system(name: &str) -> Result<db::Database, anyhow::Error>
port: 5432,
name: name.to_string(),
},
true,
db::CreationMode::Bootstrap,
)
.await
}
3 changes: 2 additions & 1 deletion importer/src/csaf/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,8 @@ impl ImportCsafCommand {
pub async fn run_once(self, progress: Progress) -> Result<Report, ScannerError> {
let report = Arc::new(Mutex::new(ReportBuilder::new()));

let db = db::Database::with_external_config(&self.database, false).await?;
let db =
db::Database::with_external_config(&self.database, db::CreationMode::Default).await?;
let system = Graph::new(db);

let source: DispatchSource = match Url::parse(&self.source) {
Expand Down
3 changes: 2 additions & 1 deletion importer/src/sbom/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,8 @@ impl ImportSbomCommand {
async fn run_once(self, progress: Progress) -> Result<Report, ScannerError> {
let report = Arc::new(Mutex::new(ReportBuilder::new()));

let db = db::Database::with_external_config(&self.database, false).await?;
let db =
db::Database::with_external_config(&self.database, db::CreationMode::Default).await?;
let system = Graph::new(db);

let source: DispatchSource = match Url::parse(&self.source) {
Expand Down
7 changes: 4 additions & 3 deletions server/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -41,8 +41,9 @@ pub struct Run {
#[command(flatten)]
pub database: Database,

#[arg(long, env)]
pub bootstrap: bool,
/// The database creation mode
#[arg(long, env, value_enum, default_value_t = db::CreationMode::Default)]
pub creation: db::CreationMode,

#[arg(long, env)]
pub devmode: bool,
Expand Down Expand Up @@ -108,7 +109,7 @@ impl InitData {
.await?
.map(Arc::new);

let db = db::Database::with_external_config(&run.database, run.bootstrap).await?;
let db = db::Database::with_external_config(&run.database, run.creation).await?;
let graph = Graph::new(db.clone());

let check = Local::spawn_periodic("no database connection", Duration::from_secs(1), {
Expand Down
10 changes: 6 additions & 4 deletions trustd/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ use tokio::task::JoinSet;
use trustify_auth::auth::AuthConfigArguments;
use trustify_auth::swagger_ui::SwaggerUiOidcConfig;
use trustify_common::config::{Database, DbStrategy, StorageConfig};
use trustify_common::db::CreationMode;
use trustify_infrastructure::app::http::HttpServerConfig;
use trustify_infrastructure::endpoint::Trustify;
use trustify_infrastructure::InfrastructureConfig;
Expand All @@ -28,8 +29,9 @@ pub struct Trustd {
#[command(subcommand)]
pub(crate) command: Option<Command>,

#[arg(long, env)]
pub bootstrap: bool,
/// The database creation mode
#[arg(long, env, value_enum, default_value_t = CreationMode::Default)]
pub creation: CreationMode,

#[arg(long, env, default_value_t = true, requires = "auth")]
pub with_http: bool,
Expand Down Expand Up @@ -99,7 +101,7 @@ impl Trustd {

let port = postgresql.settings().port;
self.database.port = port;
self.bootstrap = true;
self.creation = CreationMode::Bootstrap;

managed_db.replace(postgresql);

Expand All @@ -113,7 +115,7 @@ impl Trustd {
let http = trustify_server::Run {
database: self.database.clone(),
storage: self.storage.clone(),
bootstrap: self.bootstrap,
creation: self.creation,
devmode: self.devmode,
infra: self.infra.clone(),
auth: self.auth.clone(),
Expand Down

0 comments on commit 435c5bb

Please sign in to comment.