First version of basic self-CA
This commit is contained in:
parent
23c040930f
commit
8c4921f797
13 changed files with 419 additions and 12 deletions
2
.gitignore
vendored
2
.gitignore
vendored
|
@ -4,6 +4,8 @@
|
|||
|
||||
# Private files
|
||||
.env
|
||||
private-key.pem
|
||||
private-bytes
|
||||
|
||||
# Misc
|
||||
regexes.yaml
|
62
Cargo.lock
generated
62
Cargo.lock
generated
|
@ -17,6 +17,16 @@ dependencies = [
|
|||
"generic-array",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "aead"
|
||||
version = "0.5.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5c192eb8f11fc081b0fe4259ba5af04217d4e0faddd02417310a927911abd7c8"
|
||||
dependencies = [
|
||||
"crypto-common",
|
||||
"generic-array",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "aes"
|
||||
version = "0.7.5"
|
||||
|
@ -35,7 +45,7 @@ version = "0.9.4"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "df5f85a83a7d8b0442b6aa7b504b8212c1733da07b98aae43d4bc21b2cb3cdf6"
|
||||
dependencies = [
|
||||
"aead",
|
||||
"aead 0.4.3",
|
||||
"aes",
|
||||
"cipher 0.3.0",
|
||||
"ctr",
|
||||
|
@ -549,6 +559,30 @@ version = "1.0.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd"
|
||||
|
||||
[[package]]
|
||||
name = "chacha20"
|
||||
version = "0.9.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c7fc89c7c5b9e7a02dfe45cd2367bae382f9ed31c61ca8debe5f827c420a2f08"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"cipher 0.4.3",
|
||||
"cpufeatures",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "chacha20poly1305"
|
||||
version = "0.10.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "10cd79432192d1c0f4e1a0fef9527696cc039165d729fb41b3f4f4f354c2dc35"
|
||||
dependencies = [
|
||||
"aead 0.5.1",
|
||||
"chacha20",
|
||||
"cipher 0.4.3",
|
||||
"poly1305",
|
||||
"zeroize",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "chrono"
|
||||
version = "0.4.22"
|
||||
|
@ -582,6 +616,7 @@ checksum = "d1873270f8f7942c191139cb8a40fd228da6c3fd2fc376d7e92d47aa14aeb59e"
|
|||
dependencies = [
|
||||
"crypto-common",
|
||||
"inout",
|
||||
"zeroize",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
@ -727,6 +762,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|||
checksum = "1bfb12502f3fc46cca1bb51ac28df9d618d813cdc3d2f25b9fe775a34af26bb3"
|
||||
dependencies = [
|
||||
"generic-array",
|
||||
"rand_core",
|
||||
"typenum",
|
||||
]
|
||||
|
||||
|
@ -896,6 +932,7 @@ dependencies = [
|
|||
"axum",
|
||||
"base64ct",
|
||||
"blake3",
|
||||
"chacha20poly1305",
|
||||
"chrono",
|
||||
"dotenv",
|
||||
"futures",
|
||||
|
@ -1966,6 +2003,17 @@ dependencies = [
|
|||
"winapi",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "poly1305"
|
||||
version = "0.8.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8159bd90725d2df49889a078b54f4f79e87f1f8a8444194cdca81d38f5393abf"
|
||||
dependencies = [
|
||||
"cpufeatures",
|
||||
"opaque-debug",
|
||||
"universal-hash 0.5.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "polyval"
|
||||
version = "0.5.3"
|
||||
|
@ -1975,7 +2023,7 @@ dependencies = [
|
|||
"cfg-if",
|
||||
"cpufeatures",
|
||||
"opaque-debug",
|
||||
"universal-hash",
|
||||
"universal-hash 0.4.1",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
@ -3150,6 +3198,16 @@ dependencies = [
|
|||
"subtle",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "universal-hash"
|
||||
version = "0.5.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7d3160b73c9a19f7e2939a2fdad446c57c1bbbbf4d919d3213ff1267a580d8b5"
|
||||
dependencies = [
|
||||
"crypto-common",
|
||||
"subtle",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "untrusted"
|
||||
version = "0.7.1"
|
||||
|
|
|
@ -22,12 +22,12 @@ ulid = "1.0.0"
|
|||
axum = "0.6.0-rc.1"
|
||||
tower = "0.4.13"
|
||||
|
||||
chacha20poly1305 = "0.10.1"
|
||||
argon2 = "0.4.1"
|
||||
blake3 = "1.3.1"
|
||||
base64ct = { version = "1.5.2", features = ["alloc"] }
|
||||
rand = "0.8.5"
|
||||
|
||||
argon2 = "0.4.1"
|
||||
|
||||
tokio = { version = "1.21.0", features = ["full"] }
|
||||
|
||||
pretty_env_logger = "0.4.0"
|
||||
|
@ -47,4 +47,7 @@ user-agent-parser = "0.3.3"
|
|||
|
||||
lapin = "2.1.1"
|
||||
|
||||
picky = "7.0.0-rc.3"
|
||||
picky = "7.0.0-rc.3"
|
||||
|
||||
[profile.dev.package.num-bigint-dig]
|
||||
opt-level = 3
|
|
@ -23,7 +23,8 @@ For more information, visit https://driptorch.net/
|
|||
| DATABASE_URL | PostgreSQL database connection URL | Y |
|
||||
| AMQP_ADDR | Message queue (RabbitMQ) connection URL | Y |
|
||||
| UAP_REGEXES | Path to the [BrowserScope UA regex YAML](https://github.com/ua-parser/uap-core/blob/master/regexes.yaml) | N |
|
||||
| RSA_KEY | Path to the RSA private key used to create certificates !!! KEEP THIS SAFE !!! SERIOUSLY !!! | Y |
|
||||
| RSA_KEY | Path to the RSA private key used to create certificates !!! KEEP THIS SAFE | Y |
|
||||
| XCC20_KEY | Path to the XChaCha20-Poly1305 key used to encrypt private keys !!! KEEP THIS SAFE | Y |
|
||||
|
||||
---
|
||||
|
||||
|
|
|
@ -29,6 +29,11 @@ impl MigrationTrait for Migration {
|
|||
.binary()
|
||||
.not_null()
|
||||
)
|
||||
.col(ColumnDef::new(Certificate::Nonce)
|
||||
.binary()
|
||||
.not_null()
|
||||
.unique_key()
|
||||
)
|
||||
.col(ColumnDef::new(Certificate::CertType)
|
||||
.string()
|
||||
.not_null()
|
||||
|
@ -52,5 +57,6 @@ pub enum Certificate {
|
|||
Id,
|
||||
Data,
|
||||
Key,
|
||||
Nonce,
|
||||
CertType
|
||||
}
|
||||
|
|
76
src/cert/generate.rs
Normal file
76
src/cert/generate.rs
Normal file
|
@ -0,0 +1,76 @@
|
|||
use std::fmt;
|
||||
use std::fmt::Formatter;
|
||||
use picky::x509::{Cert, KeyIdGenMethod};
|
||||
use picky::x509::certificate::{CertError, CertificateBuilder};
|
||||
use picky::x509::date::UtcDate;
|
||||
|
||||
use chrono::prelude::*;
|
||||
use picky::hash::HashAlgorithm;
|
||||
use picky::key::PrivateKey;
|
||||
use picky::signature::SignatureAlgorithm;
|
||||
use picky::x509::name::DirectoryName;
|
||||
|
||||
pub enum InterTarget {
|
||||
CLIENT,
|
||||
PROXY
|
||||
}
|
||||
|
||||
impl fmt::Display for InterTarget {
|
||||
fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
|
||||
match self {
|
||||
InterTarget::CLIENT => write!(f, "CLIENT"),
|
||||
InterTarget::PROXY => write!(f, "PROXY")
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub async fn generate_root_cert(key: &PrivateKey) -> Result<Cert, CertError> {
|
||||
let current_date: DateTime<Utc> = Utc::now();
|
||||
|
||||
CertificateBuilder::new()
|
||||
.validity(
|
||||
UtcDate::ymd(
|
||||
current_date.year() as u16,
|
||||
current_date.month() as u8,
|
||||
current_date.day() as u8
|
||||
).unwrap(),
|
||||
UtcDate::ymd(
|
||||
(current_date.year() + 20) as u16,
|
||||
current_date.month() as u8,
|
||||
current_date.day() as u8
|
||||
).unwrap()
|
||||
)
|
||||
.self_signed(DirectoryName::new_common_name("Driptorch"), key)
|
||||
.ca(true)
|
||||
.signature_hash_type(SignatureAlgorithm::RsaPkcs1v15(HashAlgorithm::SHA2_512))
|
||||
.key_id_gen_method(KeyIdGenMethod::SPKFullDER(HashAlgorithm::SHA2_512))
|
||||
.build()
|
||||
}
|
||||
|
||||
pub async fn generate_inter_cert(key: &PrivateKey, target: InterTarget, root: (&Cert, &PrivateKey)) -> Result<Cert, CertError> {
|
||||
let current_date: DateTime<Utc> = Utc::now();
|
||||
|
||||
CertificateBuilder::new()
|
||||
.validity(
|
||||
UtcDate::ymd(
|
||||
current_date.year() as u16,
|
||||
current_date.month() as u8,
|
||||
current_date.day() as u8
|
||||
).unwrap(),
|
||||
UtcDate::ymd(
|
||||
(current_date.year() + 5) as u16,
|
||||
current_date.month() as u8,
|
||||
current_date.day() as u8
|
||||
).unwrap()
|
||||
)
|
||||
.issuer_cert(&root.0, &root.1)
|
||||
.ca(true)
|
||||
.signature_hash_type(SignatureAlgorithm::RsaPkcs1v15(HashAlgorithm::SHA2_512))
|
||||
.key_id_gen_method(KeyIdGenMethod::SPKFullDER(HashAlgorithm::SHA2_512))
|
||||
.pathlen(0)
|
||||
.subject(
|
||||
DirectoryName::new_common_name(format!("Driptorch {}", target.to_string())),
|
||||
key.to_public_key()
|
||||
)
|
||||
.build()
|
||||
}
|
39
src/cert/mod.rs
Normal file
39
src/cert/mod.rs
Normal file
|
@ -0,0 +1,39 @@
|
|||
use std::{env, fmt, fs};
|
||||
use std::fmt::Formatter;
|
||||
use std::path::Path;
|
||||
use chacha20poly1305::{AeadCore, KeyInit, XChaCha20Poly1305};
|
||||
use chacha20poly1305::aead::{Aead, OsRng};
|
||||
|
||||
pub mod generate;
|
||||
|
||||
pub enum Types {
|
||||
ROOT,
|
||||
CLIENTINTER,
|
||||
PROXYINTER,
|
||||
CLIENTLEAF,
|
||||
PROXYLEAF
|
||||
}
|
||||
|
||||
impl fmt::Display for Types {
|
||||
fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
|
||||
match self {
|
||||
Types::ROOT => write!(f, "ROOT"),
|
||||
Types::CLIENTINTER => write!(f, "CLIENTINTER"),
|
||||
Types::PROXYINTER => write!(f, "PROXYINTER"),
|
||||
Types::CLIENTLEAF => write!(f, "CLIENTLEAF"),
|
||||
Types::PROXYLEAF => write!(f, "PROXYLEAF")
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub async fn encrypt_priv_key(key: Vec<u8>) -> (Vec<u8>, Vec<u8>) {
|
||||
let cipher = XChaCha20Poly1305::new_from_slice(
|
||||
fs::read(
|
||||
Path::new(&env::var("XCC20_KEY").expect("XCC20_KEY must be set!"))
|
||||
).expect("Failed to load the XCC20 key!").as_slice()
|
||||
).expect("Error creating chacha20 cipher!");
|
||||
|
||||
let nonce = XChaCha20Poly1305::generate_nonce(&mut OsRng);
|
||||
|
||||
(nonce.to_vec(), cipher.encrypt(&nonce, key.as_slice()).expect("Failed to encrypt private key!"))
|
||||
}
|
37
src/entities/certificate.rs
Normal file
37
src/entities/certificate.rs
Normal file
|
@ -0,0 +1,37 @@
|
|||
//! SeaORM Entity. Generated by sea-orm-codegen 0.9.2
|
||||
|
||||
use sea_orm::entity::prelude::*;
|
||||
|
||||
#[derive(Clone, Debug, PartialEq, DeriveEntityModel)]
|
||||
#[sea_orm(table_name = "certificate")]
|
||||
pub struct Model {
|
||||
#[sea_orm(primary_key, auto_increment = false)]
|
||||
pub id: String,
|
||||
pub data: Vec<u8>,
|
||||
pub key: Vec<u8>,
|
||||
#[sea_orm(unique)]
|
||||
pub nonce: Vec<u8>,
|
||||
pub cert_type: String,
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
|
||||
pub enum Relation {
|
||||
#[sea_orm(has_many = "super::proxy::Entity")]
|
||||
Proxy,
|
||||
#[sea_orm(has_many = "super::client::Entity")]
|
||||
Client,
|
||||
}
|
||||
|
||||
impl Related<super::proxy::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::Proxy.def()
|
||||
}
|
||||
}
|
||||
|
||||
impl Related<super::client::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::Client.def()
|
||||
}
|
||||
}
|
||||
|
||||
impl ActiveModelBehavior for ActiveModel {}
|
|
@ -15,14 +15,24 @@ pub struct Model {
|
|||
pub dns: bool,
|
||||
pub proxy: bool,
|
||||
pub health: String,
|
||||
pub certificate: String,
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone, Debug, EnumIter)]
|
||||
pub enum Relation {}
|
||||
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
|
||||
pub enum Relation {
|
||||
#[sea_orm(
|
||||
belongs_to = "super::certificate::Entity",
|
||||
from = "Column::Certificate",
|
||||
to = "super::certificate::Column::Id",
|
||||
on_update = "NoAction",
|
||||
on_delete = "Cascade"
|
||||
)]
|
||||
Certificate,
|
||||
}
|
||||
|
||||
impl RelationTrait for Relation {
|
||||
fn def(&self) -> RelationDef {
|
||||
panic!("No RelationDef")
|
||||
impl Related<super::certificate::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::Certificate.def()
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -2,6 +2,7 @@
|
|||
|
||||
pub mod prelude;
|
||||
|
||||
pub mod certificate;
|
||||
pub mod client;
|
||||
pub mod proxy;
|
||||
pub mod record;
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
//! SeaORM Entity. Generated by sea-orm-codegen 0.9.2
|
||||
|
||||
pub use super::certificate::Entity as Certificate;
|
||||
pub use super::client::Entity as Client;
|
||||
pub use super::proxy::Entity as Proxy;
|
||||
pub use super::record::Entity as Record;
|
||||
|
|
|
@ -10,10 +10,19 @@ pub struct Model {
|
|||
pub record: String,
|
||||
pub port: i32,
|
||||
pub active: bool,
|
||||
pub certificate: String,
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
|
||||
pub enum Relation {
|
||||
#[sea_orm(
|
||||
belongs_to = "super::certificate::Entity",
|
||||
from = "Column::Certificate",
|
||||
to = "super::certificate::Column::Id",
|
||||
on_update = "NoAction",
|
||||
on_delete = "Cascade"
|
||||
)]
|
||||
Certificate,
|
||||
#[sea_orm(
|
||||
belongs_to = "super::record::Entity",
|
||||
from = "Column::Record",
|
||||
|
@ -24,6 +33,12 @@ pub enum Relation {
|
|||
Record,
|
||||
}
|
||||
|
||||
impl Related<super::certificate::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::Certificate.def()
|
||||
}
|
||||
}
|
||||
|
||||
impl Related<super::record::Entity> for Entity {
|
||||
fn to() -> RelationDef {
|
||||
Relation::Record.def()
|
||||
|
|
160
src/main.rs
160
src/main.rs
|
@ -10,15 +10,24 @@ use axum::routing::{delete, get, post};
|
|||
use dotenv::dotenv;
|
||||
use lapin::ConnectionProperties;
|
||||
use picky::key::PrivateKey;
|
||||
use sea_orm::{ConnectOptions, Database};
|
||||
use picky::x509::Cert;
|
||||
use sea_orm::{ActiveValue, ColumnTrait, ConnectOptions, Database, EntityTrait, QueryFilter};
|
||||
use sea_orm_migration::prelude::*;
|
||||
use tower::ServiceBuilder;
|
||||
use ulid::Ulid;
|
||||
use crate::cert::encrypt_priv_key;
|
||||
use crate::cert::generate::{generate_inter_cert, generate_root_cert};
|
||||
use crate::cert::generate::InterTarget::{CLIENT, PROXY};
|
||||
use crate::cert::Types::{CLIENTINTER, PROXYINTER, ROOT};
|
||||
use crate::certificate::Model;
|
||||
use crate::entities::certificate;
|
||||
|
||||
mod entities;
|
||||
mod dns;
|
||||
mod util;
|
||||
mod routes;
|
||||
mod rpc;
|
||||
mod cert;
|
||||
|
||||
const VERSION: &str = env!("CARGO_PKG_VERSION");
|
||||
|
||||
|
@ -58,6 +67,9 @@ async fn main() {
|
|||
if !Path::new(&env::var("RSA_KEY").expect("RSA_KEY must be set! Halting start-up.")).exists() {
|
||||
error!("Please generate an RSA private key for creating certificates!")
|
||||
}
|
||||
if !Path::new(&env::var("XCC20_KEY").expect("XCC20_KEY must be set! Halting start-up.")).exists() {
|
||||
error!("Please generate a 32 bits of randomness to encrypt private keys!")
|
||||
}
|
||||
|
||||
let root_rsa_key = PrivateKey::from_pem_str(
|
||||
&*fs::read_to_string(
|
||||
|
@ -78,6 +90,152 @@ async fn main() {
|
|||
.await
|
||||
.expect("Failed to run migrations! Halting start-up.");
|
||||
|
||||
info!("Checking for root cert...");
|
||||
let root_cert_model: Option<Model> = certificate::Entity::find()
|
||||
.filter(certificate::Column::CertType.eq(cert::Types::ROOT.to_string()))
|
||||
.one(&connection)
|
||||
.await
|
||||
.expect("Failed to retrieve the root cert from the database! Halting start-up.");
|
||||
|
||||
let root_cert: Cert;
|
||||
|
||||
match root_cert_model {
|
||||
None => {
|
||||
info!("Generating new root cert...");
|
||||
|
||||
let new_root_cert = generate_root_cert(&root_rsa_key)
|
||||
.await
|
||||
.expect("Failed to generate the root cert from private key! Halting start-up.");
|
||||
|
||||
root_cert = new_root_cert.clone();
|
||||
|
||||
let root_insert = certificate::Entity::insert(certificate::ActiveModel {
|
||||
id: ActiveValue::Set(Ulid::new().to_string()),
|
||||
data: ActiveValue::Set(
|
||||
new_root_cert.to_der().expect("Failed to convert cert into der!")
|
||||
),
|
||||
key: ActiveValue::set(vec![145, 66, 62, 61, 56, 156, 145, 164]),
|
||||
nonce: ActiveValue::set(vec![145, 71, 62, 66, 56, 156, 145, 164]),
|
||||
cert_type: ActiveValue::Set(ROOT.to_string())
|
||||
})
|
||||
.exec(&connection)
|
||||
.await
|
||||
.expect("Failed to insert new root cert into database! Halting start-up.");
|
||||
|
||||
info!("Generated new root cert: {}", root_insert.last_insert_id);
|
||||
}
|
||||
Some(root_cert_model) => {
|
||||
info!("Found root cert: {}", root_cert_model.id);
|
||||
|
||||
root_cert = Cert::from_der(&root_cert_model.data)
|
||||
.expect("Failed to decode root cert!");
|
||||
}
|
||||
}
|
||||
|
||||
info!("Checking for proxy intermediate cert...");
|
||||
let proxy_inter_model: Option<Model> = certificate::Entity::find()
|
||||
.filter(certificate::Column::CertType.eq(PROXYINTER.to_string()))
|
||||
.one(&connection)
|
||||
.await
|
||||
.expect("Failed to retrieve the proxy intermediate cert from the database! Halting start-up.");
|
||||
|
||||
let proxy_inter_cert: Cert;
|
||||
|
||||
match proxy_inter_model {
|
||||
None => {
|
||||
info!("Generating proxy intermediate cert...");
|
||||
|
||||
// Generate 4096 bit RSA private key
|
||||
let priv_key = PrivateKey::generate_rsa(4096)
|
||||
.expect("Failed to generate a key");
|
||||
|
||||
let encrypted_priv_key = encrypt_priv_key(priv_key
|
||||
.clone()
|
||||
.to_pkcs8()
|
||||
.expect("Failed to convert generated private key to pkcs8!")
|
||||
).await;
|
||||
|
||||
let new_proxy_inter_cert = generate_inter_cert(&priv_key, PROXY, (&root_cert, &root_rsa_key))
|
||||
.await
|
||||
.expect("Failed to generate new proxy intermediate cert");
|
||||
|
||||
proxy_inter_cert = new_proxy_inter_cert.clone();
|
||||
|
||||
let proxy_inter_insert = certificate::Entity::insert(certificate::ActiveModel {
|
||||
id: ActiveValue::Set(Ulid::new().to_string()),
|
||||
data: ActiveValue::Set(
|
||||
new_proxy_inter_cert.to_der().expect("Failed to convert cert into der!")
|
||||
),
|
||||
key: ActiveValue::set(encrypted_priv_key.1),
|
||||
nonce: ActiveValue::set(encrypted_priv_key.0),
|
||||
cert_type: ActiveValue::Set(PROXYINTER.to_string())
|
||||
})
|
||||
.exec(&connection)
|
||||
.await
|
||||
.expect("Failed to insert new proxy intermediate cert into database! Halting start-up.");
|
||||
|
||||
info!("Generated new proxy intermediate cert: {}", proxy_inter_insert.last_insert_id)
|
||||
}
|
||||
Some(proxy_inter_model) => {
|
||||
info!("Found proxy intermediate cert: {}", proxy_inter_model.id);
|
||||
|
||||
proxy_inter_cert = Cert::from_der(&proxy_inter_model.data)
|
||||
.expect("Failed to decode proxy intermediate cert!");
|
||||
}
|
||||
}
|
||||
|
||||
info!("Checking for client intermediate cert...");
|
||||
let client_inter_model: Option<Model> = certificate::Entity::find()
|
||||
.filter(certificate::Column::CertType.eq(CLIENTINTER.to_string()))
|
||||
.one(&connection)
|
||||
.await
|
||||
.expect("Failed to retrieve the client intermediate cert from the database! Halting start-up.");
|
||||
|
||||
let client_inter_cert: Cert;
|
||||
|
||||
match client_inter_model {
|
||||
None => {
|
||||
info!("Generating client intermediate cert...");
|
||||
|
||||
// Generate 4096 bit RSA private key
|
||||
let priv_key = PrivateKey::generate_rsa(4096)
|
||||
.expect("Failed to generate a key");
|
||||
|
||||
let encrypted_priv_key = encrypt_priv_key(priv_key
|
||||
.clone()
|
||||
.to_pkcs8()
|
||||
.expect("Failed to convert generated private key to pkcs8!")
|
||||
).await;
|
||||
|
||||
let new_client_inter_cert = generate_inter_cert(&priv_key, CLIENT, (&root_cert, &root_rsa_key))
|
||||
.await
|
||||
.expect("Failed to generate new client intermediate cert");
|
||||
|
||||
client_inter_cert = new_client_inter_cert.clone();
|
||||
|
||||
let client_inter_insert = certificate::Entity::insert(certificate::ActiveModel {
|
||||
id: ActiveValue::Set(Ulid::new().to_string()),
|
||||
data: ActiveValue::Set(
|
||||
new_client_inter_cert.to_der().expect("Failed to convert cert into der!")
|
||||
),
|
||||
key: ActiveValue::set(encrypted_priv_key.1),
|
||||
nonce: ActiveValue::set(encrypted_priv_key.0),
|
||||
cert_type: ActiveValue::Set(CLIENTINTER.to_string())
|
||||
})
|
||||
.exec(&connection)
|
||||
.await
|
||||
.expect("Failed to insert new client intermediate cert into database! Halting start-up.");
|
||||
|
||||
info!("Generated new client intermediate cert: {}", client_inter_insert.last_insert_id)
|
||||
}
|
||||
Some(client_inter_model) => {
|
||||
info!("Found client intermediate cert: {}", client_inter_model.id);
|
||||
|
||||
client_inter_cert = Cert::from_der(&client_inter_model.data)
|
||||
.expect("Failed to decode client intermediate cert!");
|
||||
}
|
||||
}
|
||||
|
||||
info!("Connecting to message broker...");
|
||||
let amqp_addr = env::var("AMQP_ADDR")
|
||||
.expect("AMQP_ADDR mut be set! Halting start-up.");
|
||||
|
|
Loading…
Add table
Reference in a new issue