Customize ServiceStack v3 JsConfig based on request header - servicestack

I have an existing v3 ServiceStack implementation and I want to change the way in which the dates are serialized/deserialized. However, since there are a large number of existing external customers using this service I can't just make that change globally without breaking their mobile applications that use my services.
As a result I want to change the JsConfig<DateTime>.SerializeFn but only when a particular request header is identified.
How would I go about this per request, rather than at the application level?

Related

Is it possible to update parts/directives in the "content-security-policy" header using DeclarativeNetRequest API?

I am in the process of migrating from Manifest V2 to V3, from Web Request API to Declarative Net Request API. Using Web Request, I modify the "content-security-policy" header by adding a domain into the list of various directives (default-src, frame-src, etc). I tried using the "append" operation in the rule action. Is it possible to target a directive? What if the directive does not exist? Does append just add the supplied string to the end? With Web Request, I was able to examine each directive and update each accordingly, before returning the new value. This allowed me to inject a script that is needed into each frame.
Instead, would it be possible to continue to use the Web Request API with V3? In my setup, I have my chrome extension "Published - unlisted". I do use the force install option when deploying the extension to our internal users, and the only reason I have it unlisted and not private is so that the users who have the extension can get updated whenever a new version is released. Would it be possible to have users updated without having the extension listed? Perhaps by hosting the extension in my own server? Please advise on what can be done to have the ability to update the response header, specifically the "content-security-policy" header the way I have done before, and whether I can continue to use Web Request API going forward (using V3). In the Chrome dev website, there's a mention about continuing to use Web Request if force install is used, and only if its "deployed to a given domain or to trusted testers", but I'm not sure what that actually means. What would I need to do to meet the criteria?
I tried using the append operation in the rule action via the Declarative Net Request API, but its not working as expected. I dont see the security policy being updated when I inspect the response header in dev tools. I also get errors stating that many scripts, images, etc violate the security policy for websites that did not have one to begin with (My extension targets any website).

How to extract value from URL and check cache to load data in varnish

I have a scenario where my URL will be either contains a comma delimiter with value or without.
i.e. /api/parameters/XXXXXXXXXX?tables=x0 or tables=x0;x1;x2.
now based on this URL I want to check in the varnish that, if URL contains multiple values as tables then separate that out and pass each table name in seperate URL (/api/parameters/XXXXXXXXXX?tables=x0, /api/parameters/XXXXXXXXXX?tables=x1, /api/parameters/XXXXXXXXXX?tables=x2) either to cache if miss then backend server.
then based on the response of this need to combine the result and return it to the client.
my question here is:
How to segregate the value from the URL and pass a modified URL to varnish cache or backend.
after returning the result I want to return it as a combined JSON object in a sequence of which it was originally requested with a comma delimiter(i.e. x0 result;x1 result;x2 result).
It is possible to turn a single request into multiple subrequests in Varnish. Unfortunately this cannot be done with the open source version, only with the Enterprise version.
vmod_http
https://docs.varnish-software.com/varnish-cache-plus/vmods/http/ describes how you can perform HTTP calls from within Varnish using vmod_http.
By sending HTTP requests to other URLs through Varnish, you can get multiple objects out of the cache and aggregate them into a single response
No looping
The fact that Varnish doesn't have loops makes matters a bit more complicated. You'll have so set an upper limit to the amount of values the tables querystring parameter has and you'll have to check the values using individual if-statements.
Returning the combined JSON output
Once you have fetched the results from the various URLs, you can create a JSON string and return it via return(synth(200,req.http.json)). Where req.http.json contains the JSON string.
This will create a synthetic response.
In Varnish Enterprise it is also possible to cache synthetic output. See https://docs.varnish-software.com/varnish-cache-plus/vmods/synthbackend/ to learn more about vmod_synthbackend.
Varnish Enterprise disclaimer
The solution I suggested in my answer uses Varnish Enterprise, the commercial version of Varnish. It extends Varnish capabilities with additional VMODs and features, which you can read about here. One easy way to try it out without upfront licensing payments, if you’re interested, is to spin up an instance on cloud infrastructure:
Varnish Enterprise on AWS
Varnish Enterprise on Azure
Varnish Enterprise on GCP

Serving some files from Azure CDN to only certain users

Suppose I have a website that is served by an Azure CDN endpoint (via files that have been uploaded to blob storage).
I want the minified website content to be available to everyone -- that part is easy, since that's what the CDN does by default.
Ideally, I would also have the sourcemaps available on that same CDN (so that the default behavior of //# sourceMappingURL=0-8d1d0e3cc4594b2c2758.js.map within my JS files would "just work"). However, I'd like for those sourcemaps to only be served to a subset of users.
Is there a way of accomplishing this scenario? I'm happy to defined "subset" in any way that would make this scenario work (e.g., being connected to a certain VPN or being in a certain IP-address range; or using Fiddler to set a secret header; etc.)
Thanks!
I assume that what you need is to build a system that, in production, allows to offer sourcemaps to a certain group of users, for instance, a team of developers, but not to everyone, the sourcemaps should not be publicly accessible.
There are different alternatives that can help achieve this goal.
On the one hand, we can try to use a rules engine that analyzes the received HTTP traffic and offers one or the other response depending on the criteria deemed appropriate.
These rules engines allows you to customize how HTTP requests are handled, by defining a set of possible match condition(s) on the incoming requests, and actions to be performed if the match condition(s) apply.
Azure CDN provides two types of rules engines, one standard rule engine for Azure CDN from Microsoft, and other premium from Verizon, which provide more advanced features.
How you use these rule engines depends largely on how you need to identify your user group and what you want to do to condition the response offered by your application to a sourcemap request.
For instance, one of the standard rule engines match conditions - also available in the premium rule engine - is the remote IP address where the request comes from: maybe it could be a good criterion to discriminate between your different subsets of users.
Or, as you suggested with the use of Fiddle, you can analyze incoming request header in search of a custom one.
The Azure CDN Verizon Premium rule engine provides more advanced match conditions based in browser, device type, etcetera.
Once the users have been identified, the system must consider the action to take depending on whether they belong to one or another group.
Both the standard and Verizon rules engines provides that could be relevant for this purpose.
I think that the best option, if you can use the Verizon rule engine, will be to deny access to the HTTP requests send by users that does not belong to the group allowed to access the sourcemaps.
Other options, although I think more difficult to implement if your are working with webpack and SPA, can be redirect the requests received from one subset of users to certain files which contains the sourcemaps - or to different index.html pages if you are using SPA in your frontend, each with different js and css resources, with sourcemaps or not -, or rewrite the URL to directly deliver a different set of files.
Another possible action could be to not include the inline sourcemap location in your minified files and to take advantage of the capabilities to modify response headers and Append a SourceMap header that points to the actual sourcemaps instead. This header will only be sent for the desired user group. Again, depending of how you are building your frontend it could not be an easy task.
Finally, if you are using Webpack and the SourceMapDevToolPlugin to build your frontend, you can use the publicPath option to point, in production, your sourcemaps to a non public, more developer oriented, URL location. This is the approach followed in this article. I think this approach is also worth looking into.

how to use cache data in mvc architecture

As the title suggest. I'm trying to figure out where I should cache data in my node.js application.
I'm using a express.js and controllers to handle the routes in the application. The controller for a particular route will get data via the model layer using REST API and then it uses handlebars for the view rendering on the server.
For this particular route, I'm displaying a menu and the data I have got for this has been done in the model and a remote REST call.
When the user select different items in the menu, I do not want to make a new REST call to get the same data for the menu again, I just need to get the data for this menu once since it will never change.
I need to find out a way to cache it, but do not know where I should implement it?
Best Regards
You could just cache the response from the REST API or DB lookup using a memory-store like Redis or Memcached, both have good modules available on npm - (Redis, memcached).
You would need to attempt to fetch the data from the memory-store (in your controller), if no matching data was found, you would make the request to the API or database to get the data, and then store it in your chosen memory-store so future requests will hit the cache.
note: There are also some pure JavaScript caches available such as memory-cache or lru-cache if you don't want to add an additional application.

Use of OData in a web application instead of other

I read in an article that odata can be used for different combination of clients/servers.
Say I would like to develop a web application where i store data(say information about all mobile products on market) using mongoDB and use python as backend with Bottle framework to access data through browser as GET.
Then i decide to extend web app as android app. i can extend it to android without any code change on server side.
My doubt is does using odata here helps in any way? Say if i want to extend it to other clients?
Yes, you are right, you don't need to change even a single line of code on the server side if you change a client app. OData defines many conventions for the communications between the client and the server. such as:
What the URL looks like if you want to query some data
http://services.odata.org/V4/OData/OData.svc/Products?$filter=ID gt 2&$select=ID,Name,Rating,Price&$orderby=Price desc
Which http method should be used to Create/Retrieve/Update/Delete an entity
Generally speaking, Post for Create, Get for Retrieve, Patch/Put for Update, Delete for Delete.
What the payload looks like.
How to invoke a function/action
As long as the requests conform to these conventions, the server side always returns the predictable responsese regardless whether the clients is a browser or a mobile device.
I also find the examples for the odata:
https://aspnet.codeplex.com/SourceControl/latest#Samples/WebApi/OData/v4/ .
Hope this helps you.

Resources