Accelerated Transfers & Load Balancer Sticky Sessions

Hi, I know that the current Accelerated Transfers plugin adds a header that can be used by load balancers to direct transfers to the same server.

AWS Application Load Balancers can’t be configured to support this, but they do provide a “Sticky Session” cookie that does the same thing.

I was looking in to creating a patch to provide support for sticky session cookies. I was wondering if you can point me in the right direction.

From the look of things, the HttpClient.execute method provides a way to get the response headers, but I don’t think this is surfaced through the OrthancPeers wrapper.

Do you have any pointers or are there any examples where response headers are used that can provide me a starting point?

Thanks for your help!

Cheers,

James

Hi James,

Let me get it right … You mean when you’ll send the first query to create the transfer, the load balancer will inject a HTTP header in the response and then, you’ll need to include that header in all following requests made to the load balancer for it to route the packet to the same target right ?

I just had a quick look. The good news is that the SDK is returning the answer headers but it is not forwarded to the OrthancPeers::DoPost and therefore not to the TransferToolbox::DoPostPeer, PushJob, …

The good starting point is then to replace the NULL here by a answerHeaders, and carry it up to all its callers ..

Hope this helps. If you get stuck, just tell me and I can have a look next week.

Alain.

1 Like

Brilliant. Let me give it a go.
James

Hi Alain,

Thanks for that. Attached is a patch to add cookie support for the Accelerated Transfers plugin.

I have uploaded the patch and tests to here - 20250518 Orthanc Transfers Cookie Suppport - Google Drive

This allows load balancers such as AWS Load Balancers (Edit target group attributes for your Application Load Balancer - Elastic Load Balancing) use cookies to forward multiple requests to the same target instance, allowing accelerated transfers to work in a load balanced environment.

The patch works by reading the set-cookie header returned in the first initialisation request.

The set-cookie header is parsed and any cookies are passed to the subsequent “bucket” transfers and “commit” job states.

Any subsequent http requests made in the same transfer job will include any cookie set in the initial request.

A couple of notes:

  • From my testing, orthanc converts the headers to a string map, meaning multiple set-cookie headers are merged on top of other, leaving only the last header. This means that not all cookies are captured and only the last header is included in subsequent requests associated with the transfer.
  • I have also uploaded the tests I used to verify it works. I wrote these in javascript as I was more familiar with creating a proxy and to be able to monitor the requests. I have added comments on how to run this in the index.spec.mjs.

I welcome your comments/thoughts or suggestions.

James

Hi James,

Great job !

I have included your patch in the mainline. I just made a few minor changes wrt coding styles.

Thanks a lot for this contribution !

Alain

Thanks Alain!

Just some additional notes from other experiments I ran today.

The underlying libcurl used by HttpClient has native support for cookies. I tried enabling this option in HttpClient where the curl handle is initialised today with curl_easy_setopt(easy, CURLOPT_COOKIEFILE, ""); that creates an in-memory cookie store.

From the looks of it, a new curl handle is created on every request, meaning the cookie engine isn’t re-used between connections.

I am not sure of the lifecycle of HttpClient if it is possible to reuse an instance (and associated curl handle), but if it is, then we could use libcurl’s proper cookie implementation to achieve the same.

It is also possible to read the cookies from the curl handle, the other thought I had would be to expose this through HttpClient allowing the caller to track the cookies and set them manually across multiple requests.

Another option would be to use libcurl shared state between handles Share data between handles - everything curl which would allow multiple handles to share cookies and other state like DNS lookups.

All these implementations would provide a more robust cookie implementation, but this is above my head for now, in such a highly concurrent system like Orthanc.

I wanted to share these notes, in case it helps others.

1 Like

Hi @James,
Have you ever tried to use HAProxy ? Is HAProxy able to automate inject Sticky Session to response’header back to the client like Amazon Load Balancer does ?

As I read in this article : 2 Ways to Enable Sticky Sessions in HAProxy (Guide) , HAProxy has sticky session but I am not sure it has the same ability as AWS LoadBalancer

Thanks
Christophe

Hi @Christophe I haven’t used HAProxy, but that article indicates it uses sticky session cookies, very similar (if not the same) as an AWS Load Balancer.
James