I'm in an ASP.Net Core environment and want my classes to use a named HttpClient which they retrieve from an IHttpClientFactory.
They need to add a Bearer token into the Authorization header. In order to do that, they need to make an async call which will either get the token from an OAuth endpoint, or retrieve it from the cache.
I know there are calls for services.AddHttpClient(...) which I can use to modify the HttpClient instances which are retrieved from the IHttpClientFactory. However that only allows for sync methods (It is an Action<ServiceProvider, HttpClient>), because IHttpClientFactory.GetClient(string name) is sync too.
Is there anything built into that I can use to make that async call and add the header either when retrieving the client, or when making the request by calling SendAsync(...)?
I think that AOP, for Aspect Oriented Programming, could interest you for your kind of problems.
The point of this paradigm is to increase the modularity of your code by separating the different sections and defining rules called pointcut to execute one or many specific functions before, after, when it calls an exception, etc.
In your case, you could define a Pointcut that execute your async method on entry (on the startup of the function but before any code is called) of SendAsync.
To do so, there are many AOP framework existing in C#. I know PostSharp is a good framework for AOP but I encourage you to try many of them to find which one fit the most for your needs.
Here is the link to PostSharp : https://www.postsharp.net/
I hope my answer could help you.
Have a good day.
#alexei-levenkov pointed me in the right direction in the comments.
DelegatingHandler is the way to solve this problem.
Actually I'm using Microsoft.Identity.Web which comes with its own AddMicrosoftIdentityAppAuthenticationHandler() which will automatically insert the handler, I was looking for.
Related
I am trying to ensure that a token exists when sending a request using Microsoft.Odata.Client v7 in Blazor WebAssembly. I am aware the DataServiceContext contains a SendingRequest2, but this is synchronous. The problem is that Blazor does not like to use wait monitors, so waiting for a task to finish in this event will not work. I want to ensure a token exists and is valid, and otherwise get a new token when a request is made. I want to make sure the client contains this behaviour, rather than creating a wrapper method that does this. This ensures the behaviour is not forgotten by accident in the future, and is cleaner in general.
DataServiceContext contains many virtual methods that can be overidden, but I could not figure out which one should be used (I debugged this by logging a message in all of them. None appeared).
DataServiceQuery also has methods that can be overidden, and I in fact use these. But I can not override these with a new class as I am unable to create an inherited class due to the fact that there is no documentation on how to manually create a DataServiceQuery. Normally you would use DataServiceContext's CreateQuery method for this, but this will not work with inherited classes. Making your own variant requires arguments that are not accessible as far as I found out.
Does anybody know how I can add custom asynchronous behaviour to sending requests with OData Client?
I was reading Resource-based authorization in ASP.NET Core on learn.microsoft.com and I am confused about complexity required to check author of a document.
In this example we need to create Operations and DocumentAuthorizationCrudHandler classes, register DI in Startup, call and await AuthorizeAsync and then perform checks.
Instead of writing 30 lines of code in 4 files we can accomplish everything in just one line of code
if (User.Identity?.Name == Document.Author) return Page();
If we want be able to reuse this we can extract it to a method and still it will be far less complicated solution.
Is there anything wrong with one line solution or I am missing something?
Edit:
To clarify my question - Is there any concrete example why would it be better to implement AuthorizationHandler and OperationAuthorizationRequirement for resource authorization instead of going with simple check? I am genuinely curious about what are the benefits, because I prefer simple solutions but I am afraid that I will hit some case in future that is already covered by AuthorizationHandler/OperationAuthorizationRequirement.
As the doc has said that Operations and DocumentAuthorizationCrudHandler classes enable you to write a single handler instead of an individual class for each operation type.
If we want be able to reuse this we can extract it to a method and still it will be far less complicated solution.
The recommended recourse-based authorization uses DI,which could be more clear and powerful, instead of repeating if / else code everywhere.
Besides,we could also handle different status code (401,403...) in the custom Authorization Handler.We could use IAuthorizationService on view or in blazor razor component.
I have downloaded IdentityServer4 Quickstart example and I am going through it to try and understand everything that happens here. What I have managed to do so far is replace the TestUsers with my own custom Identity Implementation that uses Identity Core + Dapper. However, there are still some parts of the code that do not make sense to me and I cannot figure out what they do. The full code example can be found here: https://github.com/IdentityServer/IdentityServer4.Quickstart.UI/tree/release/Quickstart
Throughout the many of these controllers I find the following line of code:
await _events.RaiseAsync(new UserLoginSuccessEvent(provider, providerUserId, user.Id.ToString(), user.Email));
now the UserLoginSuccessEvent is part of the IdentityServer4.Events library and the _events is actually IEventService. There are other calls such as UserLogoutSuccessEvent, ConsentDeniedEvent, and more.
My question is what does the above actually do? Is it supposed to trigger some sort of logging, if so where? Am I suppose to maybe implement something that would inject here and trigger my own thing or something completely else.
DefaultEventService class, provided by IdentityServer4, is the default implementation of IEventService.
DefaultEventService uses an IEventSink object to sink the raised events. (see its RaiseAsync implementation). DefaultEventSink, again part of IdentityServer4, is registered as IEventSink. DefaultEventSink persists\logs the events.
So, caller code calls DefaultEventService.RaiseAsync(..) method which in turns calls DefaultEventSink.PersistAsync method which logs the events.
You can provide your own implementation of IEventService or IEventSink interface or both.
We have small lifetime scopes in our applications. It would be interesting to be able to intercept all services registered in autofac. By doing so we can see exactly which path the code takes for every lifetime scope and which method arguments are used. Not really usable for production but when really great for debugging/diagnostics/refactoring as you ge the whole picture and not just unit level.
But AFAIK it's only possible to register an interceptor for each single registration?
Nothing like this is supported out of the box with the Autofac.Extras.DynamicProxy2 library. You could potentially implement something like a module that handles OnActivating for every component using code similar to the stuff in Autofac.Extras.DynamicProxy2, but you'll run into trouble like...
Do you want class interceptors or interface interceptors? The type of service being resolved vs. the limit type of the component backing it will influence what kind of dynamic proxy you want to make. I believe the current A.E.D2 code only generates interception for either/or - not every interface a class implements, etc.
Do you use WCF client proxies? Client proxies are an interesting beast of their own so you have to special-case them. You'll see that in A.E.D2.
Generally problems like this get solved by aspect-oriented programming solutions (e.g., PostSharp) or profilers (e.g., ANTS)... or a combination of both. You might want to look into those solutions if you have the ability.
For an example of what sort of module implementation I'm talking about, check out the log4net integration page on the Autofac wiki. That shows how to handle OnPreparing for every component in the system. You can do the same thing, but handle OnActivating instead and use the sample on the Lifetime Events wiki page to show you how to swap one resolved thing for another (swap the real object for the generated proxy).
I have an .net assembly at C#. I have both: binary and source which has no logger, for example.
All I need is to insert property which will be initialised specific logger. Then I need to introduce logger invoker in all methods. The first way - is manually write property and their invokes. And the second way - is to write another class\method (I suppose in the same assembly) which will do it automatically.
Is it possible? Any suggestions?
I think it is possible, cause it was one of the questions at the interview. But there is no proof that this is possible, and they wanted to hear "no, do this manually".
This is what we call in architectural terms a 'cross cutting concern'. Logging is something that straddles many aspects of an application.
There are features to take care of it in the Microsoft Enterprise Library. The part you want is the Policy Injection library. You can then specify, in the config, methods to match (based on method name/structure) and a function to be called. In this way you can include logging as a proper cross-cutting concern of your app, rather than something which must be manually coded into every method.
It is not possible to alter the execution of a method without altering the source code and recompiling. You could write a wrapper class that would expose all classes and methods which would first call your logger and then the methods, but that's not what they asked.
So the answer to their question is 1. is possible, 2. isn't possible, and if you would have to add logging support, you would need to add it to each method manually.