Comments (20)
Right, I believe we may rely on database sort order -- be it this or that -- the point is to just compact related records, imo.
from lldap.
Hmm, I can't reproduce the panic. Could you post a sql dump of the DB, or send it to me privately on Discord? Don't worry, I won't be able to get the passwords.
from lldap.
@nitnelave sorry, no, I don't own it.
Indeed I saw no sorting in migration tool hence user ids come assorted from the source LDAP.
At first I tried to sort them:
--- a/migration-tool/src/main.rs
+++ b/migration-tool/src/main.rs
@@ -23,11 +23,12 @@ fn ask_generic_confirmation(name: &str, message: &str) -> Result<bool> {
fn get_users_to_add(users: &[User], existing_users: &[String]) -> Result<Option<Vec<User>>> {
let existing_users = HashSet::<&String>::from_iter(existing_users);
let num_found_users = users.len();
- let input_users: Vec<_> = users
+ let mut input_users: Vec<_> = users
.iter()
.filter(|u| !existing_users.contains(&u.user_input.id))
.map(User::clone)
.collect();
+ input_users.sort_by(|u1, u2| u1.user_input.id.cmp(&u2.user_input.id));
println!(
"Found {} users, of which {} new users: [\n {}\n]",
num_found_users,
but the error persisted.
Then I commented out the assertion:
--- a/server/src/domain/sql_user_backend_handler.rs
+++ b/server/src/domain/sql_user_backend_handler.rs
@@ -145,11 +145,13 @@ impl UserListerBackendHandler for SqlBackendHandler {
let mut attributes_iter = attributes.into_iter().peekable();
use itertools::Itertools; // For take_while_ref
for user in users.iter_mut() {
+ /*
assert!(attributes_iter
.peek()
.map(|u| u.user_id >= user.user.user_id)
.unwrap_or(true),
"Attributes are not sorted, users are not sorted, or previous user didn't consume all the attributes");
+ */
user.user.attributes = attributes_iter
.take_while_ref(|u| u.user_id == user.user.user_id)
and it worked.
Still I can not use it: I cured symptom but indeed I broke the logic. And I do not understand the logic.
from lldap.
The ordering comes from the SQL query, not the migration: the query is ordered by user id, and so are the attributes. Is there a debug mode in PostgreSQL that prints out the queries? Otherwise, you can run LLDAP with RUST_LOG=debug, I think that should print a lot of things, including the SQL queries used.
As for the logic, we're iterating over the users and the attributes vectors, associating every run of attributes with the same user id with the corresponding user. That relies on both users and attributes to be sorted by user id.
from lldap.
Just to confirm, you used the migration tool provided by LLDAP, correct? Can you confirm that all the user IDs are lowercase in the DB? Something like "SELECT user_id FROM users;" (or select I'd maybe)
from lldap.
Yes, exactly.
Lowercased:
lldap=# select user_id from users where user_id != lower(user_id);
user_id
---------
(0 rows)
from lldap.
I see when listing users in web ui:
auth-lldap-1 | 2024-01-30T18:53:58.923828459+00:00 INFO LDAP session [ 84.5µs | 36.77% / 100.00% ]
auth-lldap-1 | 2024-01-30T18:53:58.923836389+00:00 INFO ┕━ LDAP request [ 53.4µs | 63.23% ]
auth-lldap-1 | 2024-01-30T18:53:58.923842956+00:00 DEBUG ┝━ 🐛 [debug]: | msg: LdapMsg { msgid: 0, op: SearchRequest(LdapSearchRequest { base: "", scope: Base, alias
es: Never, sizelimit: 0, timelimit: 0, typesonly: false, filter: Present("objectClass"), attrs: ["supportedExtension"] }), ctrl: [] }
auth-lldap-1 | 2024-01-30T18:53:58.923844536+00:00 DEBUG ┝━ 🐛 [debug]: rootDSE request
auth-lldap-1 | 2024-01-30T18:53:58.923857301+00:00 DEBUG ┝━ 🐛 [debug]: | response: SearchResultEntry(LdapSearchResultEntry { dn: "", attributes: [LdapPartialAttribu
te { atype: "objectClass", vals: ["top"] }, LdapPartialAttribute { atype: "vendorName", vals: ["LLDAP"] }, LdapPartialAttribute { atype: "vendorVersion", vals: ["lldap_0.5.1-
alpha"] }, LdapPartialAttribute { atype: "supportedLDAPVersion", vals: ["3"] }, LdapPartialAttribute { atype: "supportedExtension", vals: ["1.3.6.1.4.1.4203.1.11.1"] }, LdapP
artialAttribute { atype: "supportedControl", vals: [] }, LdapPartialAttribute { atype: "supportedFeatures", vals: ["1.3.6.1.4.1.4203.1.5.1"] }, LdapPartialAttribute { atype:
"defaultNamingContext", vals: ["dc=example,dc=com"] }, LdapPartialAttribute { atype: "namingContexts", vals: ["dc=example,dc=com"] }, LdapPartialAttribute { atype: "isGlobalCat
alogReady", vals: ["false"] }] })
auth-lldap-1 | 2024-01-30T18:53:58.923879452+00:00 DEBUG ┕━ 🐛 [debug]: | response: SearchResultDone(LdapResult { code: Success, matcheddn: "", message: "", referral
: [] })
auth-lldap-1 | 2024-01-30T18:54:00.764995685+00:00 DEBUG check_if_token_is_valid [ 81.0µs | 100.00% ]
auth-lldap-1 | 2024-01-30T18:54:00.765075553+00:00 DEBUG ┕━ 🐛 [debug]: | return: ValidationResults { user: UserId(CaseInsensitiveString("admin")), permission: Admin }
auth-lldap-1 | thread 'actix-rt|system:0|arbiter:0' panicked at server/src/domain/sql_user_backend_handler.rs:148:13:
auth-lldap-1 | Attributes are not sorted, users are not sorted, or previous user didn't consume all the attributes
auth-lldap-1 | stack backtrace:
auth-lldap-1 | 0: rust_begin_unwind
auth-lldap-1 | at /rustc/a28077b28a02b92985b3a3faecf92813155f1ea1/library/std/src/panicking.rs:597:5
auth-lldap-1 | 1: core::panicking::panic_fmt
auth-lldap-1 | at /rustc/a28077b28a02b92985b3a3faecf92813155f1ea1/library/core/src/panicking.rs:72:14
auth-lldap-1 | 2: lldap::domain::sql_user_backend_handler::<impl lldap::domain::handler::UserListerBackendHandler for lldap::domain::sql_backend_handler::SqlBackendHandle
r>::list_users::{{closure}}
auth-lldap-1 | 3: <Handler as lldap::infra::access_control::ReadonlyBackendHandler>::list_users::{{closure}}
auth-lldap-1 | 4: <tracing::instrument::Instrumented<T> as core::future::future::Future>::poll
auth-lldap-1 | 5: <lldap::infra::graphql::query::Query<Handler> as juniper::types::async_await::GraphQLValueAsync<__S>>::resolve_field_async::{{closure}}
auth-lldap-1 | 6: juniper::types::async_await::resolve_selection_set_into_async_recursive::{{closure}}
auth-lldap-1 | 7: juniper::types::async_await::GraphQLValueAsync::resolve_async::{{closure}}
auth-lldap-1 | 8: juniper::http::GraphQLRequest<S>::execute::{{closure}}.34508
auth-lldap-1 | 9: actix_web::handler::handler_service::{{closure}}::{{closure}}
auth-lldap-1 | 10: <actix_web::resource::Resource<T> as actix_web::service::HttpServiceFactory>::register::{{closure}}::{{closure}}
auth-lldap-1 | 11: <core::pin::Pin<P> as core::future::future::Future>::poll
auth-lldap-1 | 12: <actix_web::scope::Scope<T> as actix_web::service::HttpServiceFactory>::register::{{closure}}::{{closure}}
auth-lldap-1 | 13: <actix_web::middleware::condition::ConditionMiddlewareFuture<E,D> as core::future::future::Future>::poll
auth-lldap-1 | 14: actix_http::h1::dispatcher::InnerDispatcher<T,S,B,X,U>::poll_response
auth-lldap-1 | 15: <actix_http::h1::dispatcher::Dispatcher<T,S,B,X,U> as core::future::future::Future>::poll
auth-lldap-1 | 16: tokio::runtime::task::raw::poll
auth-lldap-1 | 17: tokio::task::local::LocalSet::tick
auth-lldap-1 | 18: <tokio::task::local::RunUntil<T> as core::future::future::Future>::poll
auth-lldap-1 | 19: tokio::task::local::LocalSet::run_until::{{closure}}
auth-lldap-1 | note: Some details are omitted, run with `RUST_BACKTRACE=full` for a verbose backtrace.
auth-lldap-1 | 2024-01-30T18:54:00.767786062+00:00 DEBUG [GraphQL query] users [ 184ms | 1.79% / 100.00% ]
auth-lldap-1 | 2024-01-30T18:54:00.767794830+00:00 DEBUG ┝━ 🐛 [debug]: | filters: None
auth-lldap-1 | 2024-01-30T18:54:00.769259284+00:00 DEBUG ┝━ 🐛 [debug]: | summary: "BEGIN" | db.statement: "" | rows_affected: 0 | rows_returned: 0 | elapsed: 647.479µs
auth-lldap-1 | 2024-01-30T18:54:00.772258135+00:00 DEBUG ┝━ 🐛 [debug]: | summary: "SELECT \"user_attribute_schema\".\"user_attribute_schema_name\", \"user_attribute_sc
hema\".\"user_attribute_schema_type\", \"user_attribute_schema\".\"user_attribute_schema_is_list\", …" | db.statement: "\n\nSELECT\n \"user_attribute_schema\".\"user_attribu
te_schema_name\",\n \"user_attribute_schema\".\"user_attribute_schema_type\",\n \"user_attribute_schema\".\"user_attribute_schema_is_list\",\n \"user_attribute_schema\".\"
user_attribute_schema_is_user_visible\",\n \"user_attribute_schema\".\"user_attribute_schema_is_user_editable\",\n \"user_attribute_schema\".\"user_attribute_schema_is_hard
coded\"\nFROM\n \"user_attribute_schema\"\nORDER BY\n \"user_attribute_schema\".\"user_attribute_schema_name\" ASC\n" | rows_affected: 3 | rows_returned: 3 | elapsed: 2.268
182ms
auth-lldap-1 | 2024-01-30T18:54:00.775296545+00:00 DEBUG ┝━ 🐛 [debug]: | summary: "SELECT \"group_attribute_schema\".\"group_attribute_schema_name\", \"group_attribute
_schema\".\"group_attribute_schema_type\", \"group_attribute_schema\".\"group_attribute_schema_is_list\", …" | db.statement: "\n\nSELECT\n \"group_attribute_schema\".\"group
_attribute_schema_name\",\n \"group_attribute_schema\".\"group_attribute_schema_type\",\n \"group_attribute_schema\".\"group_attribute_schema_is_list\",\n \"group_attribut
e_schema\".\"group_attribute_schema_is_group_visible\",\n \"group_attribute_schema\".\"group_attribute_schema_is_group_editable\",\n \"group_attribute_schema\".\"group_attr
ibute_schema_is_hardcoded\"\nFROM\n \"group_attribute_schema\"\nORDER BY\n \"group_attribute_schema\".\"group_attribute_schema_name\" ASC\n" | rows_affected: 0 | rows_retur
ned: 0 | elapsed: 2.237188ms
auth-lldap-1 | 2024-01-30T18:54:00.776090725+00:00 DEBUG ┝━ 🐛 [debug]: | summary: "COMMIT" | db.statement: "" | rows_affected: 0 | rows_returned: 0 | elapsed: 742.46µs
auth-lldap-1 | 2024-01-30T18:54:00.776229233+00:00 DEBUG ┕━ list_users [ 181ms | 98.21% ] filters: None | _get_groups: false
auth-lldap-1 | 2024-01-30T18:54:00.807388036+00:00 DEBUG ┝━ 🐛 [debug]: | summary: "SELECT \"users\".\"user_id\" AS \"A_user_id\", …" | db.statement: "\n\nSELECT\n
\"users\".\"user_id\" AS \"A_user_id\",\n \"users\".\"email\" AS \"A_email\",\n \"users\".\"lowercase_email\" AS \"A_lowercase_email\",\n \"users\".\"display_name\" AS \"A
_display_name\",\n \"users\".\"creation_date\" AS \"A_creation_date\",\n \"users\".\"password_hash\" AS \"A_password_hash\",\n \"users\".\"totp_secret\" AS \"A_totp_secret
\",\n \"users\".\"mfa_type\" AS \"A_mfa_type\",\n \"users\".\"uuid\" AS \"A_uuid\",\n \"r1\".\"group_id\" AS \"B_group_id\",\n \"r1\".\"display_name\" AS \"B_display_name
\",\n \"r1\".\"lowercase_display_name\" AS \"B_lowercase_display_name\",\n \"r1\".\"creation_date\" AS \"B_creation_date\",\n \"r1\".\"uuid\" AS \"B_uuid\"\nFROM\n \"user
s\"\n LEFT JOIN \"memberships\" AS \"r0\" ON \"users\".\"user_id\" = \"r0\".\"user_id\"\n LEFT JOIN \"groups\" AS \"r1\" ON \"r0\".\"group_id\" = \"r1\".\"group_id\"\nWHERE
\n $1\nORDER BY\n \"users\".\"user_id\" ASC,\n \"r1\".\"display_name\" ASC\n" | rows_affected: 1246 | rows_returned: 1246 | elapsed: 29.205577ms
auth-lldap-1 | 2024-01-30T18:54:00.845373003+00:00 DEBUG ┕━ 🐛 [debug]: | summary: "SELECT \"user_attributes\".\"user_attribute_user_id\", \"user_attributes\".\"user
_attribute_name\", \"user_attributes\".\"user_attribute_value\" …" | db.statement: "\n\nSELECT\n \"user_attributes\".\"user_attribute_user_id\",\n \"user_attributes\".\"use
r_attribute_name\",\n \"user_attributes\".\"user_attribute_value\"\nFROM\n \"user_attributes\"\nWHERE\n \"user_attributes\".\"user_attribute_user_id\" IN (\n $1,\n $
2,\n $3,\n $4,\n $5,\n $6,\n $7,\n $8,\n $9,\n $10,\n $11,\n $12,\n $13,\n $14,\n $15,\n $16,\n $17,\n $18,\n $19,\n $20
,\n $21,\n $22,\n $23,\n $24,\n $25,\n $26,\n $27,\n $28,\n $29,\n $30,\n $31,\n $32,\n $33,\n $34,\n $35,\n $36,\n $37,\n
$38,\n $39,\n $40,\n $41,\n $42,\n $43,\n $44,\n $45,\n $46,\n $47,\n $48,\n $49,\n $50,\n $51,\n $52,\n $53,\n $54,\n $
55,\n $56,\n $57,\n $58,\n $59,\n $60,\n $61,\n $62,\n $63,\n $64,\n $65,\n $66,\n $67,\n $68,\n $69,\n $70,\n $71,\n $72,\
n $73,\n $74,\n $75,\n $76,\n $77,\n $78,\n $79,\n $80,\n $81,\n $82,\n $83,\n $84,\n $85,\n $86,\n $87,\n $88,\n $89,\n
$90,\n $91,\n $92,\n $93,\n $94,\n $95,\n $96,\n $97,\n $98,\n $99,\n $100,\n $101,\n $102,\n $103,\n $104,\n $105,\n $106,\n
$107,\n $108,\n $109,\n $110,\n $111,\n $112,\n $113,\n $114,\n $115,\n $116,\n $117,\n $118,\n $119,\n $120,\n $121,\n $122,
\n $123,\n $124,\n $125,\n $126,\n $127,\n $128,\n $129,\n $130,\n $131,\n $132,\n $133,\n $134,\n $135,\n $136,\n $137,\n $13
8,\n $139,\n $140,\n $141,\n $142,\n $143,\n $144,\n $145,\n $146,\n $147,\n $148,\n $149,\n $150,\n $151,\n $152,\n $153,\n $
154,\n $155,\n $156,\n $157,\n $158,\n $159,\n $160,\n $161,\n $162,\n $163,\n $164,\n $165,\n $166,\n $167,\n $168,\n $169,\n
$170,\n $171,\n $172,\n $173,\n $174,\n $175,\n $176,\n $177,\n $178,\n $179,\n $180,\n $181,\n $182,\n $183,\n $184,\n $185,\n
$186,\n $187,\n $188,\n $189,\n $190,\n $191,\n $192,\n $193,\n $194,\n $195,\n $196,\n $197,\n $198,\n $199,\n $200,\n $201,\
n $202,\n $203,\n $204,\n $205,\n $206,\n $207,\n $208,\n $209,\n $210,\n $211,\n $212,\n $213,\n $214,\n $215,\n $216,\n $217
,\n $218,\n $219,\n $220,\n $221,\n $222,\n $223,\n $224,\n $225,\n $226,\n $227,\n $228,\n $229,\n $230,\n $231,\n $232,\n $2
33,\n $234,\n $235,\n $236,\n $237,\n $238,\n $239,\n $240,\n $241,\n $242,\n $243,\n $244,\n $245,\n $246,\n $247,\n $248,\n
$249,\n $250,\n $251,\n $252,\n $253,\n $254,\n $255,\n $256,\n $257,\n $258,\n $259,\n $260,\n $261,\n $262,\n $263,\n $264,\n
$265,\n $266,\n $267,\n $268,\n $269,\n $270,\n $271,\n $272,\n $273,\n $274,\n $275,\n $276,\n $277,\n $278,\n $279,\n $280,\n
$281,\n $282,\n $283,\n $284,\n $285,\n $286,\n $287,\n $288,\n $289,\n $290,\n $291,\n $292,\n $293,\n $294,\n $295,\n $296,
\n $297,\n $298,\n $299,\n $300,\n $301,\n $302,\n $303,\n $304,\n $305,\n $306,\n $307,\n $308,\n $309,\n $310,\n $311,\n $31
2,\n $313,\n $314,\n $315,\n $316,\n $317,\n $318,\n $319,\n $320,\n $321,\n $322,\n $323,\n $324,\n $325,\n $326,\n $327,\n $
328,\n $329,\n $330,\n $331,\n $332,\n $333,\n $334,\n $335,\n $336,\n $337,\n $338,\n $339,\n $340,\n $341,\n $342,\n $343,\n
$344,\n $345,\n $346,\n $347,\n $348,\n $349,\n $350,\n $351,\n $352,\n $353,\n $354,\n $355,\n $356,\n $357,\n $358,\n $359,\n
$360,\n $361,\n $362,\n $363,\n $364,\n $365,\n $366,\n $367,\n $368,\n $369,\n $370,\n $371,\n $372,\n $373,\n $374,\n $375,\
n $376,\n $377,\n $378,\n $379,\n $380,\n $381,\n $382,\n $383,\n $384,\n $385,\n $386,\n $387,\n $388,\n $389,\n $390,\n $391
,\n $392,\n $393,\n $394,\n $395,\n $396,\n $397,\n $398,\n $399,\n $400,\n $401,\n $402,\n $403,\n $404,\n $405,\n $406,\n $4
07,\n $408,\n $409,\n $410,\n $411,\n $412,\n $413,\n $414,\n $415,\n $416,\n $417,\n $418,\n $419,\n $420,\n $421,\n $422,\n
$423,\n $424,\n $425,\n $426,\n $427,\n $428,\n $429,\n $430,\n $431,\n $432,\n $433,\n $434,\n $435,\n $436,\n $437,\n $438,\n
$439,\n $440,\n $441,\n $442,\n $443,\n $444,\n $445,\n $446,\n $447,\n $448,\n $449,\n $450,\n $451,\n $452,\n $453,\n $454,\n
$455,\n $456,\n $457,\n $458,\n $459,\n $460,\n $461,\n $462,\n $463,\n $464,\n $465,\n $466,\n $467,\n $468,\n $469,\n $470,
\n $471,\n $472,\n $473,\n $474,\n $475,\n $476\n )\nORDER BY\n \"user_attributes\".\"user_attribute_user_id\" ASC,\n \"user_attributes\".\"user_attribu........
The only quirk I see is an awful monstrous ... IN (...)
clause. But I can not find the query source. Does it come from some ORM? Hmm. What if I'd have much more than 476 users?
IMO such queries should read select ... from ... where foo = any($1)
passing the array to the parameter.
from lldap.
Ah, yeah, LLDAP was not built with "big" servers in mind, more for self-hosted homelabs. But still, 476 users is not that much, it should work.
One limitation that we have is that we support only the subset of SQL common to PG, MySQL and SQLite. That often leads us to write less-than-ideal queries. I'll see if it's possible to pass an array, but I didn't think that an online table would be a problem.
from lldap.
I'm struggling with this:
let attributes = model::UserAttributes::find()
//.filter(model::UserAttributesColumn::UserId.is_in(user_ids)) // <-- this may choke
.filter(model::UserAttributesColumn::UserId.eq(Expr::cust_with_values("ANY(?)", [user_ids]))) <-- this does not compile
.order_by_asc(model::UserAttributesColumn::UserId)
.order_by_asc(model::UserAttributesColumn::AttributeName)
.all(&self.sql_pool)
.await?;
1.224 Compiling lldap v0.5.1-alpha (/app/server)
4.693 error[E0277]: the trait bound `sea_orm::Value: std::convert::From<std::iter::Map<std::slice::Iter<'_, UserAndGroups>, {closure@server/src/domain/sql_user_backend_handle
r.rs:138:41: 138:44}>>` is not satisfied
4.693 --> server/src/domain/sql_user_backend_handler.rs:141:60
4.693 |
4.693 141 | .filter(model::UserAttributesColumn::UserId.eq(Expr::cust_with_values("ANY(?)", [user_ids])))
4.693 | ^^^^^^^^^^^^^^^^^^^^^^ the trait `std::convert::From<std::iter::Map<std::slice::Iter<'_, UserAndGroups>
, {closure@server/src/domain/sql_user_backend_handler.rs:138:41: 138:44}>>` is not implemented for `sea_orm::Value`
4.693 |
4.693 = help: the following other types implement trait `std::convert::From<T>`:
4.693 <sea_orm::Value as std::convert::From<bool>>
4.693 <sea_orm::Value as std::convert::From<char>>
4.693 <sea_orm::Value as std::convert::From<i8>>
4.693 <sea_orm::Value as std::convert::From<i16>>
4.693 <sea_orm::Value as std::convert::From<i32>>
4.693 <sea_orm::Value as std::convert::From<i64>>
4.693 <sea_orm::Value as std::convert::From<u8>>
4.693 <sea_orm::Value as std::convert::From<u16>>
4.693 and 41 others
4.693 = note: required for `std::iter::Map<std::slice::Iter<'_, UserAndGroups>, {closure@server/src/domain/sql_user_backend_handler.rs:138:41: 138:44}>` to implement `Int
o<sea_orm::Value>`
...
Can you point out what's wrong there?
from lldap.
I'm not in front of the computer, but you can try with user_ids.collect::<Vec<_>>()
from lldap.
Got it to compile with:
let user_ids: Vec<_> = users.iter().map(|u| u.user.user_id.to_string()).collect();
let attributes = model::UserAttributes::find()
//.filter(model::UserAttributesColumn::UserId.eq(Func::cust(Any).arg(user_ids)))
.filter(Expr::cust_with_exprs(
"? = ANY(?)",
[
SimpleExpr::Column(model::UserAttributesColumn::UserId.into_column_ref()),
user_ids.into(),
],
))
.order_by_asc(model::UserAttributesColumn::UserId)
.order_by_asc(model::UserAttributesColumn::AttributeName)
.all(&self.sql_pool)
.await?;
But then we hit Sqlite doesn't support array arguments
.
Can you try https://github.com/lldap/lldap/tree/filters instead? I repeat the query above with the same filter as a filter subquery. It's a bit ugly, but it should work (and it passes the tests).
from lldap.
"filters" downs at the same assert
from lldap.
Well,
-- sqlite3
select 'test.tools' >= 'testsamba'; -- 0
-- mysql
select 'test.tools' >= 'testsamba'; -- 0
# rust
println!(">= {}", "test.tools" >= "testsamba"); // false
but
-- default postgres from docker
select 'test.tools' >= 'testsamba'; -- true
from lldap.
from lldap.
from lldap.
I fix the issue altering the collation of the database.
This one may be closed.
Will you pull filters' query so that no long IN (...)
live in the main branch?
from lldap.
@dvv sure. Can you give me the SQL command you ran to update the collation? I'd like to include that in the migration scripts.
from lldap.
On second thought, it shouldn't be necessary: the order should be the same, so just removing the assert should be enough.
from lldap.
@nitnelave first I tried https://stackoverflow.com/a/61595309
but then just recreated database as follows:
lldap-db:
image: postgres:16.1
environment:
...
LC_COLLATE: C
from lldap.
On third thought, I think the itertools utility used for grouping uses the ordering, so we have to re-sort.
from lldap.
Related Issues (20)
- [BUG] subpath don't work with image lldap/lldap:2024-03-07-debian|alpine HOT 4
- [INTEGRATION] AMP by cubecoders HOT 5
- [BUG] Ldap query to filter user present in two groups is always empty
- [FEATURE REQUEST] Paranoid logging mode
- [BUG] `lldap_password_manager` role does not see other users in the web UI HOT 5
- [INTEGRATION] Stalwart Mailserver HOT 3
- Traefik's PathPrefix supported? HOT 1
- [FEATURE REQUEST] Helm chart implementation details HOT 6
- [FEATURE REQUEST] Include bootstrap.sh in Docker image HOT 2
- [INTEGRATION] Trying to use LLDAP with LAM (Ldap Account Manager)
- [BUG] password reset: mail server error discloses user email
- Nested groups HOT 1
- [BUG] Email through Starttls not working HOT 2
- [FEATURE REQUEST] Return schema in RootDSE for better compatibility with Apache Directory Studio Browser HOT 6
- [FEATURE REQUEST] File-only database HOT 1
- [BUG] LDAP groups not working with Nextcloud HOT 2
- [FEATURE REQUEST] modifyTimestamp
- [FEATURE REQUEST] One checkbox per user to temporarily deny/allow access HOT 1
- [INTEGRATION] uidNumber: missing on nslcd authentication HOT 3
- [FEATURE REQUEST] Allow to disable the web UI HOT 11
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from lldap.