-
Notifications
You must be signed in to change notification settings - Fork 591
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Allow to use any ldap attribute as user id for batch role sync #804
base: master
Are you sure you want to change the base?
Allow to use any ldap attribute as user id for batch role sync #804
Conversation
The following commits need their title changed:
Please format your commit title into the form:
This allows us to easily generate changelogs & determine semantic version numbers when cutting releases. You can read more about commit conventions here. |
63c9743
to
9ec5d75
Compare
fiat-ldap/src/main/java/com/netflix/spinnaker/fiat/config/LdapConfig.java
Outdated
Show resolved
Hide resolved
I haven't actually peer reviewed the code, but I wanted to add a general comment on breaking changes. We can't just abruptly introduce breaking changes to core functionality, as this produces a very unstable user experience for Spinnakers enterprise customers. The general approach i'd like to see for something like this is that it is opt in for x releases, then it becomes the default for y releases but you can opt into the legacy provider and announce after z releases you will be deleting the legacy impl. So i'd like to see the UX for enabling this be like so
this might involve making a new module in this project ☝️ something like this allows us to responsibly deprecate and replace functionality. EDIT I pulled those configuration paths out of a hat, and would need to be tweaked to something that made sense. Then we would also update this: https://spinnaker.io/community/releases/next-release-preview/ to talk about the new V2 provider and any plans to make it the default and remove the other one, etc. |
9ec5d75
to
6da8a63
Compare
@fieldju Hi, i've moved all changes to different module could you have a look to it. Also i've changed the way how to get users from ldap by one query. Now i've construct one query joining the userSearchFilter for all users by | (or operator). As i known ldap support query size up to 10Mb and sounds like it should works for any condition. |
...-ldap/src/test/groovy/com/netflix/spinnaker/fiat/roles/ldap/LdapUserRolesProviderTest.groovy
Outdated
Show resolved
Hide resolved
6da8a63
to
f84b8a9
Compare
fiat-ldap-v2/src/main/java/com/netflix/spinnaker/fiat/roles/ldap/LdapUserRolesProviderV2.java
Outdated
Show resolved
Hide resolved
35ff094
to
d32578a
Compare
fiat-ldap/src/main/java/com/netflix/spinnaker/fiat/roles/ldap/LdapUserRolesProvider.java
Show resolved
Hide resolved
d32578a
to
4e19537
Compare
4e19537
to
05886d3
Compare
05886d3
to
93c6b6e
Compare
93c6b6e
to
c1ecbdc
Compare
StringBuilder filter = new StringBuilder(); | ||
filter.append("(|"); | ||
users.forEach( | ||
u -> filter.append(MessageFormat.format(configProps.getUserSearchFilter(), u.getId()))); | ||
filter.append(")"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You can create a new OrFilter
and run filter.or(Filter)
on each filter to or together.
Currently we're have two options for batch sync users roles:
Sync roles for each user by making request to ldap with userSearchFilter. That way allow us to use any ldap attribute as user id but it very slow ~ 16min for 1000 users.
Sync users roles by making 1 request to ldap using ** groupSearchBase** perf(auth/ldap): Use group to user mapping to role sync #573. For that case all user related information gets from member attribute which consists of only DN(distinguished name) because ldap doesn't support join queries. That way dramatically faster ~ 14sec for 1000 users, but we're couldn't use sAMAccountName or any other ldap attributes which we're used to use in userSearchFilter and have to use only CN as user id.
Usually ldap contains a lot of users and few roles and in that case we could change our approach for sync users roles.
First of all we can get all users with role by one ldap call like that
(&(objectCategory=user)(memberOf={ROLE_DN}))
. That query return all objects which takes part of the group, but we're allowed to use only strong equality by DN for a memberOf filter.As a result we'll make N+1 requests to ldap where N is number of groups and it seems to be fast also we could use the same ldap attribute as user id which we using in userSearchFilter for syncing single user. In our case it takes 7sec for syncing 250 users in 2 roles.
I understand that request contains breaking changes but maintains 3 different ways to sync roles doesn't sounds like good idea and such approach looks like best compromise: it still fast for large ldap instalation and not so slow for small instalations.
Linked issue: spinnaker/spinnaker#6150