-
Notifications
You must be signed in to change notification settings - Fork 361
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
Connect to multiple instances (clusters) at the same time #314
Comments
Hi @sagikazarmark, Have you any ideas on what you would like to see in this @sagikazarmark @johnweldon? On an initial pass, I would think that we have a |
@stefanmcshane glad to hear, I think it would help the consumers of this library facing similar use cases. I'm not intimately familiar with the library, but here are a couple thoughts:
Those are my initial thoughts about the problem. We can probably discuss retries and timeouts in more detail (for example when and how to retry requests? Should the implementation move to the next connection until it runs out?) |
Thanks @sagikazarmark for the suggestions. The way I like to think of Conn vs Client is akin to how postgres do it in that there could be many connections for a given client. When implementing this library, I tend to call the implementing package the client as I usually setup retries, or various connections there. Granted, this is a personal opinion and wasnt necessarily the consideration when @johnweldon started the package.
I agree with this. Do you know of any libraries that implement something similar/implement this in a way that you think is seamless? If you want to suggest a draft PR on what you believe would be a desirable user-facing experience, that would also be helpful in the design decisions.
Whilst this is true and would hurt retries as an example (try next), it could be useful on the assumption that the user will want to change the primary connection on a given request type. An example here could be on a globally deployed platform, they might want to add a new user, which is seen in US first, without waiting on their replication strategy kicking in. I suspect that in a naive implementation, we would have to setup a map of the given hosts to connect to, as well as a slice for the given maps to order them.
My initial thought at this would be to implement a basic round-robin, but expose a way that the user can implement their own retry/timeout. Let me know what you think. If you're up for collaborating on this one, I'd appreciate that also. |
I think a naive round robin can just be implemented as a counter (ie. uint32) that you keep increasing atomically and calculate the counter modulo number of connections to choose the next connection.
As long as the load balancing algorithm is explicit and doesn't depend on the random randomness of map access, I think the internal data structure is less important. BTW that scenario sounds like a different type of retry. For example instead of choosing a specific connection, I'd implement a weighted list, prioritizing the closest server first and the primary later, but in that case, retrying the query happens if the closest server returns an empty result, not when an error is returned. I'm not sure that makes sense for LDAP, but it makes sense for tackling replication issues. But again, different story.
I'd start with something stupid simple and add configuration later when some feedback arrives.
TBH I'm not very familiar with LDAP or this library, so I'm happy to discuss design, test the implementation in Dex or review code even, but I'd leave the implementation to someone more familiar with the library and LDAP. |
I like the collaboration and discussion here; it sounds like it's heading in the right direction. I'd like to clarify that I didn't actually start this project, I just moved it to a more canonical name and tried to support it a little bit over the years. The original author I believe is @mmitton and this was the original repo before https://github.com/mmitton/ldap |
Hi All! 👋 Here's a use case: Large US furniture manufacturer is using Dex for Kubernetes authentication, but they're only able to connect to a single LDAP/Active Directory backend and would like to prevent a single fault domain by allowing for 2 or more LDAP backends (adding on their behalf). |
I can speak to our use case a bit - we are also using Dex for authentication in corporate environments. It's common for IT to provide us with several URLs for LDAP servers in different on-premise data centres. As @scaranoj mentioned it's a way of preventing a single fault domain for the directory, usually not using an (on-premise) load balancer because that would have to be hosted in one of the data centres and would reintroduce a single point of failure. In some cases we can use Keycloak, which does support LDAP failover through the Java JNDI LDAP provider. I think the implementation there is effectively a round-robin which attempts to connect to each server in turn until a connection is successful, then continues to use that server. From the doco:
|
Just iterating through a list seems to be a very common pattern that could be the starting point or default algorithm. This could be implemented first and more sophisticated algorithms could follow (round-robin, weighted-connection, least-response-time). The simpler algorithms could just reorder the list before iterating through it. The simple list approach can be found in
Requests for service discovery like #329 need the same base work: you get a list of servers that has to be sorted by priority and weight. Then you iterate through that list until you find a server you can connect to. |
Another advantage of a simple list: it also works with only one element. What we use today without loadbalancing or HA. |
At least in the AD-Context it seems to be the responsibility of the Client to |
@alexei-matveev for AD this boils down to the following:
Which means the ability to go through a list of servers until you find a working one is an essential core functionality |
From time to time I see feature requests in software consuming LDAP to add cluster support. I assume it's useful in environments when there is no load balancer in front of the different LDAP servers?
Anyway, I was wondering if it would be doable on the LDAP Client level or if there is an existing implementation somewhere. Couple searches in the repo and issues yielded no results.
Here is an example of those requests: dexidp/dex#1904
I'm not particularly a fan of the implementation in this PR and I'd like to find a better/lower-level solution if possible.
Any ideas? Thanks in advance!
The text was updated successfully, but these errors were encountered: