domain-handlers: move backend handler traits to separate crate

This commit is contained in:
Simon Broeng Jensen
2025-02-19 23:48:05 +01:00
committed by nitnelave
parent e22d17dca6
commit ca1c6ff645
25 changed files with 149 additions and 104 deletions
Generated
+19
View File
@@ -2536,6 +2536,7 @@ dependencies = [
"lettre",
"lldap_auth",
"lldap_domain",
"lldap_domain_handlers",
"lldap_domain_model",
"lldap_validation",
"log",
@@ -2645,6 +2646,24 @@ dependencies = [
"uuid 1.11.0",
]
[[package]]
name = "lldap_domain_handlers"
version = "0.1.0"
dependencies = [
"async-trait",
"base64 0.21.7",
"chrono",
"derive_more 1.0.0",
"ldap3_proto",
"lldap_auth",
"lldap_domain",
"lldap_domain_model",
"pretty_assertions",
"serde",
"serde_bytes",
"uuid 1.11.0",
]
[[package]]
name = "lldap_domain_model"
version = "0.1.0"
+1
View File
@@ -3,6 +3,7 @@ members = [
"crates/auth",
"crates/domain",
"crates/domain-model",
"crates/domain-handlers",
"crates/validation",
"server",
"app",
+41
View File
@@ -0,0 +1,41 @@
[package]
authors = ["Valentin Tolmer <valentin@tolmer.fr>"]
name = "lldap_domain_handlers"
version = "0.1.0"
edition = "2021"
[features]
test = []
[dependencies]
async-trait = "0.1"
base64 = "0.21"
ldap3_proto = "0.6.0"
serde = "1"
serde_bytes = "0.11"
[dev-dependencies]
pretty_assertions = "1"
[dependencies.chrono]
features = ["serde"]
version = "0.4"
[dependencies.derive_more]
features = ["debug", "display", "from", "from_str"]
default-features = false
version = "1"
[dependencies.lldap_auth]
path = "../auth"
features = ["opaque_server", "opaque_client", "sea_orm"]
[dependencies.lldap_domain]
path = "../domain"
[dependencies.lldap_domain_model]
path = "../domain-model"
[dependencies.uuid]
features = ["v1", "v3"]
version = "1"
@@ -1,4 +1,5 @@
use async_trait::async_trait;
use ldap3_proto::proto::LdapSubstringFilter;
use lldap_domain::{
requests::{
CreateAttributeRequest, CreateGroupRequest, CreateUserRequest, UpdateGroupRequest,
@@ -51,6 +52,22 @@ impl SubStringFilter {
}
}
impl From<LdapSubstringFilter> for SubStringFilter {
fn from(
LdapSubstringFilter {
initial,
any,
final_,
}: LdapSubstringFilter,
) -> Self {
Self {
initial,
any,
final_,
}
}
}
#[derive(PartialEq, Eq, Debug, Serialize, Deserialize, Clone)]
pub enum UserRequestFilter {
And(Vec<UserRequestFilter>),
+1
View File
@@ -0,0 +1 @@
pub mod handler;
+3
View File
@@ -94,6 +94,9 @@ features = ["test"]
[dependencies.lldap_domain_model]
path = "../crates/domain-model"
[dependencies.lldap_domain_handlers]
path = "../crates/domain-handlers"
[dependencies.lldap_validation]
path = "../crates/validation"
+1 -1
View File
@@ -6,7 +6,6 @@ use tracing::{debug, instrument, warn};
use crate::domain::{
deserialize::deserialize_attribute_value,
handler::{GroupListerBackendHandler, GroupRequestFilter},
ldap::{
error::{LdapError, LdapResult},
utils::{
@@ -21,6 +20,7 @@ use crate::domain::{
use lldap_domain::types::{
AttributeName, AttributeType, Group, GroupId, LdapObjectClass, UserId, Uuid,
};
use lldap_domain_handlers::handler::{GroupListerBackendHandler, GroupRequestFilter};
pub fn get_group_attribute(
group: &Group,
+1 -1
View File
@@ -6,7 +6,6 @@ use tracing::{debug, instrument, warn};
use crate::domain::{
deserialize::deserialize_attribute_value,
handler::{UserListerBackendHandler, UserRequestFilter},
ldap::{
error::{LdapError, LdapResult},
utils::{
@@ -21,6 +20,7 @@ use crate::domain::{
use lldap_domain::types::{
AttributeName, AttributeType, GroupDetails, LdapObjectClass, User, UserAndGroups, UserId,
};
use lldap_domain_handlers::handler::{UserListerBackendHandler, UserRequestFilter};
use lldap_domain_model::model::UserColumn;
pub fn get_user_attribute(
+1 -18
View File
@@ -1,33 +1,16 @@
use std::collections::BTreeMap;
use chrono::TimeZone;
use ldap3_proto::{proto::LdapSubstringFilter, LdapResultCode};
use ldap3_proto::LdapResultCode;
use tracing::{debug, instrument, warn};
use crate::domain::{
handler::SubStringFilter,
ldap::error::{LdapError, LdapResult},
schema::PublicSchema,
};
use lldap_domain::types::{
Attribute, AttributeName, AttributeType, AttributeValue, Cardinality, GroupName, UserId,
};
impl From<LdapSubstringFilter> for SubStringFilter {
fn from(
LdapSubstringFilter {
initial,
any,
final_,
}: LdapSubstringFilter,
) -> Self {
Self {
initial,
any,
final_,
}
}
}
use lldap_domain_model::model::UserColumn;
fn make_dn_pair<I>(mut iter: I) -> LdapResult<(String, String)>
-1
View File
@@ -1,5 +1,4 @@
pub mod deserialize;
pub mod handler;
pub mod ldap;
pub mod opaque_handler;
pub mod schema;
+7 -12
View File
@@ -1,7 +1,8 @@
use crate::domain::{handler::BackendHandler, sql_tables::DbConnection};
use crate::infra::configuration::Configuration;
use crate::{domain::sql_tables::DbConnection, infra::configuration::Configuration};
use async_trait::async_trait;
use lldap_domain_handlers::handler::BackendHandler;
#[derive(Clone)]
pub struct SqlBackendHandler {
pub(crate) config: Configuration,
@@ -20,21 +21,15 @@ impl BackendHandler for SqlBackendHandler {}
#[cfg(test)]
pub mod tests {
use super::*;
use crate::{
domain::{
handler::{
GroupBackendHandler, UserBackendHandler, UserListerBackendHandler,
UserRequestFilter,
},
sql_tables::init_table,
},
infra::configuration::ConfigurationBuilder,
};
use crate::{domain::sql_tables::init_table, infra::configuration::ConfigurationBuilder};
use lldap_auth::{opaque, registration};
use lldap_domain::{
requests::{CreateGroupRequest, CreateUserRequest},
types::{Attribute as DomainAttribute, GroupId, UserId},
};
use lldap_domain_handlers::handler::{
GroupBackendHandler, UserBackendHandler, UserListerBackendHandler, UserRequestFilter,
};
use pretty_assertions::assert_eq;
use sea_orm::Database;
@@ -1,8 +1,5 @@
use crate::{
domain::{
handler::{GroupBackendHandler, GroupListerBackendHandler, GroupRequestFilter},
sql_backend_handler::SqlBackendHandler,
},
domain::sql_backend_handler::SqlBackendHandler,
infra::access_control::UserReadableBackendHandler,
};
use async_trait::async_trait;
@@ -10,6 +7,9 @@ use lldap_domain::{
requests::{CreateGroupRequest, UpdateGroupRequest},
types::{AttributeName, Group, GroupDetails, GroupId, Serialized, Uuid},
};
use lldap_domain_handlers::handler::{
GroupBackendHandler, GroupListerBackendHandler, GroupRequestFilter,
};
use lldap_domain_model::{
error::{DomainError, Result},
model::{self, deserialize, GroupColumn, MembershipColumn},
@@ -336,14 +336,12 @@ impl SqlBackendHandler {
#[cfg(test)]
mod tests {
use super::*;
use crate::domain::{
handler::{SchemaBackendHandler, SubStringFilter},
sql_backend_handler::tests::*,
};
use crate::domain::sql_backend_handler::tests::*;
use lldap_domain::{
requests::CreateAttributeRequest,
types::{Attribute, AttributeType, GroupName, UserId},
};
use lldap_domain_handlers::handler::{SchemaBackendHandler, SubStringFilter};
use pretty_assertions::assert_eq;
async fn get_group_ids(
+1 -1
View File
@@ -1,5 +1,4 @@
use super::{
handler::{BindRequest, LoginHandler},
opaque_handler::{login, registration, OpaqueHandler},
sql_backend_handler::SqlBackendHandler,
};
@@ -7,6 +6,7 @@ use async_trait::async_trait;
use base64::Engine;
use lldap_auth::opaque;
use lldap_domain::types::UserId;
use lldap_domain_handlers::handler::{BindRequest, LoginHandler};
use lldap_domain_model::{
error::{DomainError, Result},
model::{self, UserColumn},
@@ -1,13 +1,11 @@
use crate::domain::{
handler::{ReadSchemaBackendHandler, SchemaBackendHandler},
sql_backend_handler::SqlBackendHandler,
};
use crate::domain::sql_backend_handler::SqlBackendHandler;
use async_trait::async_trait;
use lldap_domain::{
requests::CreateAttributeRequest,
schema::{AttributeList, AttributeSchema, Schema},
types::{AttributeName, LdapObjectClass},
};
use lldap_domain_handlers::handler::{ReadSchemaBackendHandler, SchemaBackendHandler};
use lldap_domain_model::{
error::{DomainError, Result},
model,
@@ -177,13 +175,11 @@ impl SqlBackendHandler {
#[cfg(test)]
mod tests {
use super::*;
use crate::domain::{
handler::{UserBackendHandler, UserRequestFilter},
sql_backend_handler::tests::*,
};
use crate::domain::sql_backend_handler::tests::*;
use lldap_domain::requests::UpdateUserRequest;
use lldap_domain::schema::AttributeList;
use lldap_domain::types::{Attribute, AttributeType};
use lldap_domain_handlers::handler::{UserBackendHandler, UserRequestFilter};
use pretty_assertions::assert_eq;
#[tokio::test]
@@ -1,14 +1,12 @@
use crate::domain::{
handler::{
ReadSchemaBackendHandler, UserBackendHandler, UserListerBackendHandler, UserRequestFilter,
},
sql_backend_handler::SqlBackendHandler,
};
use crate::domain::sql_backend_handler::SqlBackendHandler;
use async_trait::async_trait;
use lldap_domain::{
requests::{CreateUserRequest, UpdateUserRequest},
types::{AttributeName, GroupDetails, GroupId, Serialized, User, UserAndGroups, UserId, Uuid},
};
use lldap_domain_handlers::handler::{
ReadSchemaBackendHandler, UserBackendHandler, UserListerBackendHandler, UserRequestFilter,
};
use lldap_domain_model::{
error::{DomainError, Result},
model::{self, deserialize, GroupColumn, UserColumn},
@@ -416,8 +414,9 @@ impl UserBackendHandler for SqlBackendHandler {
#[cfg(test)]
mod tests {
use super::*;
use crate::domain::{handler::SubStringFilter, sql_backend_handler::tests::*};
use crate::domain::sql_backend_handler::tests::*;
use lldap_domain::types::{Attribute, JpegPhoto};
use lldap_domain_handlers::handler::SubStringFilter;
use lldap_domain_model::model::UserColumn;
use pretty_assertions::{assert_eq, assert_ne};
+6 -7
View File
@@ -3,14 +3,13 @@ use std::collections::HashSet;
use async_trait::async_trait;
use tracing::info;
use crate::domain::{
handler::{
BackendHandler, GroupBackendHandler, GroupListerBackendHandler, GroupRequestFilter,
ReadSchemaBackendHandler, SchemaBackendHandler, UserBackendHandler,
UserListerBackendHandler, UserRequestFilter,
},
schema::PublicSchema,
use lldap_domain_handlers::handler::{
BackendHandler, GroupBackendHandler, GroupListerBackendHandler, GroupRequestFilter,
ReadSchemaBackendHandler, SchemaBackendHandler, UserBackendHandler, UserListerBackendHandler,
UserRequestFilter,
};
use crate::domain::schema::PublicSchema;
use lldap_domain::{
requests::{
CreateAttributeRequest, CreateGroupRequest, CreateUserRequest, UpdateGroupRequest,
+4 -4
View File
@@ -23,13 +23,13 @@ use tracing::{debug, info, instrument, warn};
use lldap_auth::{login, password_reset, registration, JWTClaims};
use lldap_domain::types::{GroupDetails, GroupName, UserId};
use lldap_domain_handlers::handler::{
BackendHandler, BindRequest, LoginHandler, UserRequestFilter,
};
use lldap_domain_model::{error::DomainError, model::UserColumn};
use crate::{
domain::{
handler::{BackendHandler, BindRequest, LoginHandler, UserRequestFilter},
opaque_handler::OpaqueHandler,
},
domain::opaque_handler::OpaqueHandler,
infra::{
access_control::{ReadonlyBackendHandler, UserReadableBackendHandler, ValidationResults},
tcp_backend_handler::*,
+9 -11
View File
@@ -1,15 +1,12 @@
use crate::{
domain::handler::BackendHandler,
infra::{
access_control::{
AccessControlledBackendHandler, AdminBackendHandler, ReadonlyBackendHandler,
UserReadableBackendHandler, UserWriteableBackendHandler, ValidationResults,
},
auth_service::check_if_token_is_valid,
cli::ExportGraphQLSchemaOpts,
graphql::{mutation::Mutation, query::Query},
tcp_server::AppState,
use crate::infra::{
access_control::{
AccessControlledBackendHandler, AdminBackendHandler, ReadonlyBackendHandler,
UserReadableBackendHandler, UserWriteableBackendHandler, ValidationResults,
},
auth_service::check_if_token_is_valid,
cli::ExportGraphQLSchemaOpts,
graphql::{mutation::Mutation, query::Query},
tcp_server::AppState,
};
use actix_web::FromRequest;
@@ -24,6 +21,7 @@ use juniper::{
EmptySubscription, FieldError, RootNode, ScalarValue,
};
use lldap_domain::types::UserId;
use lldap_domain_handlers::handler::BackendHandler;
use tracing::debug;
pub struct Context<Handler: BackendHandler> {
+2 -3
View File
@@ -1,9 +1,7 @@
use std::{collections::BTreeMap, sync::Arc};
use crate::{
domain::{
deserialize::deserialize_attribute_value, handler::BackendHandler, schema::PublicSchema,
},
domain::{deserialize::deserialize_attribute_value, schema::PublicSchema},
infra::{
access_control::{
AdminBackendHandler, ReadonlyBackendHandler, UserReadableBackendHandler,
@@ -25,6 +23,7 @@ use lldap_domain::{
LdapObjectClass, UserId,
},
};
use lldap_domain_handlers::handler::BackendHandler;
use lldap_validation::attributes::{validate_attribute_name, ALLOWED_CHARACTERS_DESCRIPTION};
use tracing::{debug, debug_span, Instrument, Span};
+2 -2
View File
@@ -3,7 +3,6 @@ use std::sync::Arc;
use crate::{
domain::{
deserialize::deserialize_attribute_value,
handler::{BackendHandler, ReadSchemaBackendHandler},
ldap::utils::{map_user_field, UserFieldType},
schema::PublicSchema,
},
@@ -18,11 +17,12 @@ use juniper::{graphql_object, FieldResult, GraphQLInputObject};
use lldap_domain::types::{
AttributeType, Cardinality, GroupDetails, GroupId, LdapObjectClass, UserId,
};
use lldap_domain_handlers::handler::{BackendHandler, ReadSchemaBackendHandler};
use lldap_domain_model::model::UserColumn;
use serde::{Deserialize, Serialize};
use tracing::{debug, debug_span, Instrument, Span};
type DomainRequestFilter = crate::domain::handler::UserRequestFilter;
type DomainRequestFilter = lldap_domain_handlers::handler::UserRequestFilter;
type DomainUser = lldap_domain::types::User;
type DomainGroup = lldap_domain::types::Group;
type DomainUserAndGroups = lldap_domain::types::UserAndGroups;
+7 -7
View File
@@ -1,7 +1,6 @@
use crate::{
domain::{
deserialize,
handler::{BackendHandler, BindRequest, LoginHandler, ReadSchemaBackendHandler},
ldap::{
error::{LdapError, LdapResult},
group::{convert_groups_to_ldap_op, get_groups_list},
@@ -30,6 +29,9 @@ use lldap_domain::{
requests::CreateUserRequest,
types::{Attribute, AttributeName, AttributeType, Email, Group, UserAndGroups, UserId},
};
use lldap_domain_handlers::handler::{
BackendHandler, BindRequest, LoginHandler, ReadSchemaBackendHandler,
};
use std::collections::HashMap;
use tracing::{debug, instrument, warn};
@@ -924,10 +926,7 @@ impl<Backend: BackendHandler + LoginHandler + OpaqueHandler> LdapHandler<Backend
#[cfg(test)]
mod tests {
use super::*;
use crate::{
domain::handler::*,
infra::test_utils::{setup_default_schema, MockTestBackendHandler},
};
use crate::infra::test_utils::{setup_default_schema, MockTestBackendHandler};
use chrono::TimeZone;
use ldap3_proto::proto::{
LdapDerefAliases, LdapSearchScope, LdapSubstringFilter, LdapWhoamiRequest,
@@ -937,6 +936,7 @@ mod tests {
types::*,
uuid,
};
use lldap_domain_handlers::handler::*;
use lldap_domain_model::model::UserColumn;
use mockall::predicate::eq;
use pretty_assertions::assert_eq;
@@ -1016,7 +1016,7 @@ mod tests {
async fn test_bind() {
let mut mock = MockTestBackendHandler::new();
mock.expect_bind()
.with(eq(crate::domain::handler::BindRequest {
.with(eq(lldap_domain_handlers::handler::BindRequest {
name: UserId::new("bob"),
password: "pass".to_string(),
}))
@@ -1049,7 +1049,7 @@ mod tests {
async fn test_admin_bind() {
let mut mock = MockTestBackendHandler::new();
mock.expect_bind()
.with(eq(crate::domain::handler::BindRequest {
.with(eq(lldap_domain_handlers::handler::BindRequest {
name: UserId::new("test"),
password: "pass".to_string(),
}))
+2 -4
View File
@@ -1,8 +1,5 @@
use crate::{
domain::{
handler::{BackendHandler, LoginHandler},
opaque_handler::OpaqueHandler,
},
domain::opaque_handler::OpaqueHandler,
infra::{
access_control::AccessControlledBackendHandler,
configuration::{Configuration, LdapsOptions},
@@ -15,6 +12,7 @@ use actix_service::{fn_service, ServiceFactoryExt};
use anyhow::{anyhow, Context, Result};
use ldap3_proto::{control::LdapControl, proto::LdapMsg, proto::LdapOp, LdapCodec};
use lldap_domain::types::AttributeName;
use lldap_domain_handlers::handler::{BackendHandler, LoginHandler};
use rustls::PrivateKey;
use tokio_rustls::TlsAcceptor as RustlsTlsAcceptor;
use tokio_util::codec::{FramedRead, FramedWrite};
+2 -4
View File
@@ -1,8 +1,5 @@
use crate::{
domain::{
handler::{BackendHandler, LoginHandler},
opaque_handler::OpaqueHandler,
},
domain::opaque_handler::OpaqueHandler,
infra::{
access_control::{AccessControlledBackendHandler, ReadonlyBackendHandler},
auth_service,
@@ -18,6 +15,7 @@ use actix_service::map_config;
use actix_web::{dev::AppConfig, guard, web, App, HttpResponse, Responder};
use anyhow::{Context, Result};
use hmac::Hmac;
use lldap_domain_handlers::handler::{BackendHandler, LoginHandler};
use lldap_domain_model::error::DomainError;
use sha2::Sha512;
use std::collections::HashSet;
+2 -1
View File
@@ -1,4 +1,4 @@
use crate::domain::{handler::*, opaque_handler::*};
use crate::domain::opaque_handler::*;
use lldap_domain::{
requests::{
CreateAttributeRequest, CreateGroupRequest, CreateUserRequest, UpdateGroupRequest,
@@ -7,6 +7,7 @@ use lldap_domain::{
schema::{AttributeList, AttributeSchema, Schema},
types::*,
};
use lldap_domain_handlers::handler::*;
use lldap_domain_model::error::Result;
use async_trait::async_trait;
+4 -4
View File
@@ -7,10 +7,6 @@ use std::time::Duration;
use crate::{
domain::{
handler::{
GroupBackendHandler, GroupListerBackendHandler, GroupRequestFilter, UserBackendHandler,
UserListerBackendHandler, UserRequestFilter,
},
sql_backend_handler::SqlBackendHandler,
sql_opaque_handler::register_password,
sql_tables::{get_private_key_info, set_private_key_info},
@@ -31,6 +27,10 @@ use sea_orm::{Database, DatabaseConnection};
use tracing::{debug, error, info, instrument, span, warn, Instrument, Level};
use lldap_domain::requests::{CreateGroupRequest, CreateUserRequest};
use lldap_domain_handlers::handler::{
GroupBackendHandler, GroupListerBackendHandler, GroupRequestFilter, UserBackendHandler,
UserListerBackendHandler, UserRequestFilter,
};
mod domain;
mod infra;