mirror of
https://github.com/mountain-loop/yaak.git
synced 2026-04-20 07:51:20 +02:00
[WIP] Encryption for secure values (#183)
This commit is contained in:
@@ -3,10 +3,11 @@ use crate::models::HttpRequestIden::{
|
||||
Authentication, AuthenticationType, Body, BodyType, CreatedAt, Description, FolderId, Headers,
|
||||
Method, Name, SortPriority, UpdatedAt, Url, UrlParameters, WorkspaceId,
|
||||
};
|
||||
use crate::util::{generate_prefixed_id, UpdateSource};
|
||||
use crate::util::{UpdateSource, generate_prefixed_id};
|
||||
use chrono::{NaiveDateTime, Utc};
|
||||
use rusqlite::Row;
|
||||
use sea_query::{enum_def, IntoIden, IntoTableRef, SimpleExpr};
|
||||
use sea_query::Order::Desc;
|
||||
use sea_query::{IntoColumnRef, IntoIden, IntoTableRef, Order, SimpleExpr, enum_def};
|
||||
use serde::{Deserialize, Deserializer, Serialize};
|
||||
use serde_json::Value;
|
||||
use std::collections::BTreeMap;
|
||||
@@ -124,6 +125,10 @@ impl UpsertModelInfo for Settings {
|
||||
panic!("Settings does not have unique IDs")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(SettingsIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -209,6 +214,7 @@ pub struct Workspace {
|
||||
pub updated_at: NaiveDateTime,
|
||||
pub name: String,
|
||||
pub description: String,
|
||||
pub encryption_key_challenge: Option<String>,
|
||||
|
||||
// Settings
|
||||
#[serde(default = "default_true")]
|
||||
@@ -231,6 +237,10 @@ impl UpsertModelInfo for Workspace {
|
||||
generate_prefixed_id("wk")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(WorkspaceIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -245,6 +255,7 @@ impl UpsertModelInfo for Workspace {
|
||||
(UpdatedAt, upsert_date(source, self.updated_at)),
|
||||
(Name, self.name.trim().into()),
|
||||
(Description, self.description.into()),
|
||||
(EncryptionKeyChallenge, self.encryption_key_challenge.into()),
|
||||
(SettingFollowRedirects, self.setting_follow_redirects.into()),
|
||||
(SettingRequestTimeout, self.setting_request_timeout.into()),
|
||||
(SettingValidateCertificates, self.setting_validate_certificates.into()),
|
||||
@@ -256,6 +267,7 @@ impl UpsertModelInfo for Workspace {
|
||||
WorkspaceIden::UpdatedAt,
|
||||
WorkspaceIden::Name,
|
||||
WorkspaceIden::Description,
|
||||
WorkspaceIden::EncryptionKeyChallenge,
|
||||
WorkspaceIden::SettingRequestTimeout,
|
||||
WorkspaceIden::SettingFollowRedirects,
|
||||
WorkspaceIden::SettingRequestTimeout,
|
||||
@@ -274,6 +286,7 @@ impl UpsertModelInfo for Workspace {
|
||||
updated_at: row.get("updated_at")?,
|
||||
name: row.get("name")?,
|
||||
description: row.get("description")?,
|
||||
encryption_key_challenge: row.get("encryption_key_challenge")?,
|
||||
setting_follow_redirects: row.get("setting_follow_redirects")?,
|
||||
setting_request_timeout: row.get("setting_request_timeout")?,
|
||||
setting_validate_certificates: row.get("setting_validate_certificates")?,
|
||||
@@ -281,16 +294,11 @@ impl UpsertModelInfo for Workspace {
|
||||
}
|
||||
}
|
||||
|
||||
impl Workspace {
|
||||
pub fn new(name: String) -> Self {
|
||||
Self {
|
||||
name,
|
||||
model: "workspace".to_string(),
|
||||
setting_validate_certificates: true,
|
||||
setting_follow_redirects: true,
|
||||
..Default::default()
|
||||
}
|
||||
}
|
||||
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default, TS)]
|
||||
#[serde(default, rename_all = "camelCase")]
|
||||
#[ts(export, export_to = "gen_models.ts")]
|
||||
pub struct EncryptedKey {
|
||||
pub encrypted_key: String,
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, Serialize, Deserialize, Default, TS)]
|
||||
@@ -304,6 +312,7 @@ pub struct WorkspaceMeta {
|
||||
pub workspace_id: String,
|
||||
pub created_at: NaiveDateTime,
|
||||
pub updated_at: NaiveDateTime,
|
||||
pub encryption_key: Option<EncryptedKey>,
|
||||
pub setting_sync_dir: Option<String>,
|
||||
}
|
||||
|
||||
@@ -320,6 +329,10 @@ impl UpsertModelInfo for WorkspaceMeta {
|
||||
generate_prefixed_id("wm")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(WorkspaceMetaIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -333,6 +346,7 @@ impl UpsertModelInfo for WorkspaceMeta {
|
||||
(CreatedAt, upsert_date(source, self.created_at)),
|
||||
(UpdatedAt, upsert_date(source, self.updated_at)),
|
||||
(WorkspaceId, self.workspace_id.into()),
|
||||
(EncryptionKey, self.encryption_key.map(|e| serde_json::to_string(&e).unwrap()).into()),
|
||||
(SettingSyncDir, self.setting_sync_dir.into()),
|
||||
])
|
||||
}
|
||||
@@ -340,6 +354,7 @@ impl UpsertModelInfo for WorkspaceMeta {
|
||||
fn update_columns() -> Vec<impl IntoIden> {
|
||||
vec![
|
||||
WorkspaceMetaIden::UpdatedAt,
|
||||
WorkspaceMetaIden::EncryptionKey,
|
||||
WorkspaceMetaIden::SettingSyncDir,
|
||||
]
|
||||
}
|
||||
@@ -348,12 +363,14 @@ impl UpsertModelInfo for WorkspaceMeta {
|
||||
where
|
||||
Self: Sized,
|
||||
{
|
||||
let encryption_key: Option<String> = row.get("encryption_key")?;
|
||||
Ok(Self {
|
||||
id: row.get("id")?,
|
||||
workspace_id: row.get("workspace_id")?,
|
||||
model: row.get("model")?,
|
||||
created_at: row.get("created_at")?,
|
||||
updated_at: row.get("updated_at")?,
|
||||
encryption_key: encryption_key.map(|e| serde_json::from_str(&e).unwrap()),
|
||||
setting_sync_dir: row.get("setting_sync_dir")?,
|
||||
})
|
||||
}
|
||||
@@ -413,6 +430,10 @@ impl UpsertModelInfo for CookieJar {
|
||||
generate_prefixed_id("cj")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(CookieJarIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -486,6 +507,10 @@ impl UpsertModelInfo for Environment {
|
||||
generate_prefixed_id("ev")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(EnvironmentIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -575,6 +600,10 @@ impl UpsertModelInfo for Folder {
|
||||
generate_prefixed_id("fl")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(FolderIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -673,7 +702,7 @@ pub struct HttpRequest {
|
||||
#[serde(default = "default_http_method")]
|
||||
pub method: String,
|
||||
pub name: String,
|
||||
pub sort_priority: f32,
|
||||
pub sort_priority: f64,
|
||||
pub url: String,
|
||||
pub url_parameters: Vec<HttpUrlParameter>,
|
||||
}
|
||||
@@ -691,6 +720,10 @@ impl UpsertModelInfo for HttpRequest {
|
||||
generate_prefixed_id("rq")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(HttpResponseIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.to_string()
|
||||
}
|
||||
@@ -745,21 +778,21 @@ impl UpsertModelInfo for HttpRequest {
|
||||
Ok(Self {
|
||||
id: r.get("id")?,
|
||||
model: r.get("model")?,
|
||||
sort_priority: r.get("sort_priority")?,
|
||||
workspace_id: r.get("workspace_id")?,
|
||||
created_at: r.get("created_at")?,
|
||||
updated_at: r.get("updated_at")?,
|
||||
url: r.get("url")?,
|
||||
url_parameters: serde_json::from_str(url_parameters.as_str()).unwrap_or_default(),
|
||||
method: r.get("method")?,
|
||||
authentication: serde_json::from_str(authentication.as_str()).unwrap_or_default(),
|
||||
authentication_type: r.get("authentication_type")?,
|
||||
body: serde_json::from_str(body.as_str()).unwrap_or_default(),
|
||||
body_type: r.get("body_type")?,
|
||||
description: r.get("description")?,
|
||||
authentication: serde_json::from_str(authentication.as_str()).unwrap_or_default(),
|
||||
authentication_type: r.get("authentication_type")?,
|
||||
headers: serde_json::from_str(headers.as_str()).unwrap_or_default(),
|
||||
folder_id: r.get("folder_id")?,
|
||||
headers: serde_json::from_str(headers.as_str()).unwrap_or_default(),
|
||||
method: r.get("method")?,
|
||||
name: r.get("name")?,
|
||||
sort_priority: r.get("sort_priority")?,
|
||||
url: r.get("url")?,
|
||||
url_parameters: serde_json::from_str(url_parameters.as_str()).unwrap_or_default(),
|
||||
})
|
||||
}
|
||||
}
|
||||
@@ -814,6 +847,10 @@ impl UpsertModelInfo for WebsocketConnection {
|
||||
generate_prefixed_id("wc")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(WebsocketConnectionIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -924,6 +961,10 @@ impl UpsertModelInfo for WebsocketRequest {
|
||||
generate_prefixed_id("wr")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(WebsocketRequestIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -1045,6 +1086,10 @@ impl UpsertModelInfo for WebsocketEvent {
|
||||
generate_prefixed_id("we")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(WebsocketEventIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -1158,6 +1203,10 @@ impl UpsertModelInfo for HttpResponse {
|
||||
generate_prefixed_id("rs")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(HttpResponseIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -1286,6 +1335,10 @@ impl UpsertModelInfo for GrpcRequest {
|
||||
generate_prefixed_id("gr")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(GrpcRequestIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -1409,6 +1462,10 @@ impl UpsertModelInfo for GrpcConnection {
|
||||
generate_prefixed_id("gc")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(GrpcConnectionIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -1525,6 +1582,10 @@ impl UpsertModelInfo for GrpcEvent {
|
||||
generate_prefixed_id("ge")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(GrpcEventIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -1612,6 +1673,10 @@ impl UpsertModelInfo for Plugin {
|
||||
generate_prefixed_id("pg")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(PluginIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -1690,6 +1755,10 @@ impl UpsertModelInfo for SyncState {
|
||||
generate_prefixed_id("ss")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(SyncStateIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -1769,6 +1838,10 @@ impl UpsertModelInfo for KeyValue {
|
||||
generate_prefixed_id("kv")
|
||||
}
|
||||
|
||||
fn order_by() -> (impl IntoColumnRef, Order) {
|
||||
(KeyValueIden::CreatedAt, Desc)
|
||||
}
|
||||
|
||||
fn get_id(&self) -> String {
|
||||
self.id.clone()
|
||||
}
|
||||
@@ -1919,13 +1992,18 @@ impl<'de> Deserialize<'de> for AnyModel {
|
||||
Some(m) if m == "key_value" => AnyModel::KeyValue(fv(value).unwrap()),
|
||||
Some(m) if m == "plugin" => AnyModel::Plugin(fv(value).unwrap()),
|
||||
Some(m) if m == "settings" => AnyModel::Settings(fv(value).unwrap()),
|
||||
Some(m) if m == "websocket_connection" => AnyModel::WebsocketConnection(fv(value).unwrap()),
|
||||
Some(m) if m == "websocket_connection" => {
|
||||
AnyModel::WebsocketConnection(fv(value).unwrap())
|
||||
}
|
||||
Some(m) if m == "websocket_event" => AnyModel::WebsocketEvent(fv(value).unwrap()),
|
||||
Some(m) if m == "websocket_request" => AnyModel::WebsocketRequest(fv(value).unwrap()),
|
||||
Some(m) if m == "workspace" => AnyModel::Workspace(fv(value).unwrap()),
|
||||
Some(m) if m == "workspace_meta" => AnyModel::WorkspaceMeta(fv(value).unwrap()),
|
||||
Some(m) => {
|
||||
return Err(serde::de::Error::custom(format!("Failed to deserialize AnyModel {}", m)));
|
||||
return Err(serde::de::Error::custom(format!(
|
||||
"Failed to deserialize AnyModel {}",
|
||||
m
|
||||
)));
|
||||
}
|
||||
None => {
|
||||
return Err(serde::de::Error::custom("Missing or invalid model"));
|
||||
@@ -1963,6 +2041,7 @@ pub trait UpsertModelInfo {
|
||||
fn table_name() -> impl IntoTableRef;
|
||||
fn id_column() -> impl IntoIden + Eq + Clone;
|
||||
fn generate_id() -> String;
|
||||
fn order_by() -> (impl IntoColumnRef, Order);
|
||||
fn get_id(&self) -> String;
|
||||
fn insert_values(
|
||||
self,
|
||||
|
||||
Reference in New Issue
Block a user