Request scope / Ability for parts to supply specific structured data to the response filter?


#1

Does XP support any kind of request scope that lets parts set data that can be read in the response filter when the page is being assembled?

We want to implement an x-key based Varnish cache on the frontend, that knows what content has been involved in building the current page.

I am basically hoping that I can set some data in the return object of the part, and that all those return objects are available later on in the response filter? Is there some way of doing this? The hope is that each part will be able to report which IDs has been involved in building its fragment of the response, and that all those individual part responses can be merged together by the response filter when the page is being built.


#2

So, you want to set an “internal header/variable” as the request is being processed, and let various processing steps i .e. filters or parts can read/write to this when they are executed?


#3

Exactly. A way for multiple parts to communicate some structured data back to a filter, so it can act on that information later in the request handling :slight_smile:

I assume parts are executed in parallel, so it would make sense that each part can write to this, but not read other parts information. Maybe just have it as a key in the response returned from the controller method in the part.

Maybe something like:
return {
body: freemarker.render(view, model),
requestScope: { idsUsed: dataFromQuery.ids }
};

We need a way for each part to tell the system what IDs have been involved in building their part of the request. This will allow us to build response headers that lets Varnish identify which cache elements to purge when a certain ID has been changed.


#4

You can try passing the values as headers. The parts can return the values in the HTTP response headers, I believe the filter will get the response with the headers that were set in the parts. It is limited to string values, but you can use serialize as JSON for complex objects.
And of course you should remove the headers from the final response, in the filter, otherwise they will be sent to the clients.
This is a hack, but might be a workaround for the short term.


#5

Interesting. We actually want the headers to get sent (at least out from Enonic) so Varnish can pick them up. Sounds like we might be able to just set the headers in each part then.

Do you know what happens if more than one part sets the same header? Does the header just get added multiple times to the response, with different values?


#6

I think the values for the same header name will be overwritten, and the one set in the last evaluated part will be the one sent.

You could use different header names, with some prefix and the part name
E.g.{ "varnish-part1": "value1", "varnish-part2": "value2" },

And process them in the filter to get the expected headers sent out:
{"varnish" : "value1, value2"}


#7

Hi! We are adding a task to the backlog for adding a new property in the response object where one can add custom JSON. We will see how this is done in the JSGI spec to see if we can reuse the same approach.