How do AEM 6.1 components share context/data for requests - content-management-system

Trying to build an authenticated page with components that request data about the authenticated user from a backend service. The idea is that the authN response from the backend be as light as possible (e.g. a userID and authToken) and the components on the page would use those to make subsequent calls to retrieve further details, but I'm not quite sure the best way to share that data/context for all components on the page to access.
What's the best way to have that context shared?

You have a few options. You can set variables in components that scope them to apply beyond just that JSP. See http://www.java2s.com/Code/Java/JSTL/JSTLSetVariablesScope.htm
With scoping you can make variables accessible with session scope or request scope so that once set any other components that are processed during the same request will be able to access the variables.
So you could make your authentication component set variables with request scope for the userID and authToken, and then subsequent components would be able to access those variables and use them for their needs. An example is shown in https://stackoverflow.com/a/21352909/230055

Related

How to plug authentication information with a URL based load test using VSTS/C#

I referred this article here Run URL based load test VSTS which describes an easy way to create a url based load test.
I want the user authentication information to be passed to the header of the url
such that the authentication should happen by fetching a token through Active directory. I am clue less how to plug such authentication information with url based load test.
I suggest breaking it into two parts to solve this:
Passing authentication information to the URL based load test. You can do this by adding the appropriate header for your test case. For e.g. if the app uses a bearer token, you can pass the bearer token in header.
The link you shared already shows how you can add header values -
Create a separate test case which has to run before the URL based load test case. In fact it could be a pre-requisite/dependency for your load test case. In this test case, just get the required token that will be later passed in as header.
To get the token, I'm assuming you would not want any interactive flow that requires a browser and user login, since it's a test case, so you can use code similar to this - https://github.com/Azure-Samples/active-directory-dotnet-daemon
The most important piece of code in that sample is the method to acquire token
authContext.AcquireTokenAsync(todoListResourceId, clientCredential);
You will need to register a new application to represent your tests in Azure AD to get the client id/client secret (or can use one of the existing registered AD apps that have access to call the endpoint you will use in your URL based load test).

Capturing audit trail information via REST

I'm struggling with coming up with the "right" way to capture audit information via a REST service. Let's say I've got an internal REST API for an Employee resource. I want to capture things when an Employee is added/modified/removed such as the user who did the change, the application the user was using, when it was done (assume this could be asynchronous so the user's action may have taken place at a different time than the REST call), etc. Also, the user that initiated the change may not be the authenticated user making the REST call.
My thoughts are that those properties do not belong in the body of the request - meaning that they are not attributes of the Employee object. They are not something that would be retrieved and returned on a GET, so they shouldn't be in the POST/PUT. They also do not belong as a parameter because parameters should be for specifying additional things about Employees or a search/filter critiera on GET requests for Employees.
My current thoughts are to have the client specify this information in the HTTP headers. That keeps the URL parameters & body pure for the Employee resource. Is that an appropriate use of the headers? Are there other options that I'm not seeing?
I'm working on a project with a very similar problem, and we did end up using HTTP headers to track auditing information. Actually, this was a byproduct of requiring an Authorization header which specifies the client user and application, and we use this information inside the REST service to store details in an audit log.
In your case, I don't think it's "wrong" to add custom X headers to specify the original user/application/time the request was made and storing these to an audit history in the service somewhere. Basically proxying on information via extra request headers. I also agree that these should not be part of the request body or URL parameters.

What is the best way of passing user info/profile/context via web API service

I am a newbie who is writting ASP.Net web API service for the very first time. The issue I am having is how to pass user information or different contexts via service request. For example I want to pass user context (i.e username, user preferences etc.) and lets say security context (i.e. api key, secret etc.) thru each service call. The options I found
1. using Query string
2. custom HTTP headers
3. overload authorization header to pass Jason object
4. cookie
I ditch the idea of using query string as it has 2k limitation, custom header could be ripped by proxy services, dont want to use cookie,creating a jason object of all the context and send it via auth header can work but seems like not a smart way. Any idea? what is the best way of passing those extra information.
I really appreciate if someone help me with some examples.

REST Hypermedia: Should the actions be filtered based on the user's permissions?

According to Roy Fielding's Hypermedia As The Engine of Application State (HATEOAS), each resource should be accompagnied with a list of actions (or links) that can be done on that resource.
If the actions are included in the entity (as apposed to using the links attribute of Json-Schema), how do I tell the user-agent that a specific option is not available to the authenticated user?
The backend could do the filtering, but then the same resource URL could have different representations depending on the authenticated user. And this does not seem REST-friendly or caching friendly.
The other option is to leave all links, and let the user-agent receive a 403 Forbidden when the action is not available to the authenticated user. This can be annoying to the user.
How to inform the user-agent on the available actions when those can change depending on the authenticated user, while remaining REST-friendly?
You are correct. Creating representations that vary based on user permission is not particularly cache friendly. Is it possible to classify permission variants into just a few categories? e.g. resource-low-security, resource-medium-security resource-high-security
Sometimes this approach is possible, sometimes it is not. The other aspect to consider is whether caching is critical for this particular resource. Maybe it is now?
Also, it is not necessary to wait until the user clicks on a link to find out if the user has the permissions to follow it. The client could perform an OPTIONS request on links in the background to discover which links are available and dynamically disable the links that are not accessible.
There is no single answer to this problem. Different solutions will work in different cases depending on the requirements.
Consider that a REST API is a website for a robot to browse.
Do websites return HTML resources (pages) containing links that you're not permitted to see?
Whether it does or not, it doesn't change how "hypermediary" the website is.
but then the same resource URL could have different representations depending on the authenticated user
Consider the same about the homepage of a website. A resource is conceptual, the home page is the concept, what it looks like changes.
How does the web deal with the caching of pages for logged-in and logged-out views?
The first way is to bar caching of those resources; not everything must be cachable, the constraint is simply that resources can be labeled accordingly.
The second is using control semantics, or headers if you're using HTTP for your REST API.
https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Vary

is there a deep dive on google's oauth2 scopes?

I'm looking for some deep down detailed information on google's use of oauth scopes
My Drive app is working, so I get the simple use of scopes. However I have the following detailed questions/issues..
I specify scopes twice. Once in my app and then also in the API
Console. What is the respective significance of these two scope
declarations?
If I remove scopes, must my user re-authorise my app, or is this
only required for adding additional scopes?
If the answer to 2, is 'I can't silently remove scopes', will the
Google libraries deal gracefully with re-authorising the user, or
will I just get 403 failures? I've read How should an application add/remove scopes to an existing grant? but the accepted answer specifically references adding scopes, whereas my question is about removing scopes.
Can different modules within my app request different scopes within
the superset specified in the API console? To explain, my app has 3
components: a chrome extension accessing Drive, a web client using
JS to access Drive and YouTube (in online mode), and a server
component which accesses Drive (in offline mode)..
Can my app. enquire what scopes it has been granted?
A general question, I'm sure I face the same dilemma as many app authors. If I increase functionality (a good thing since it attracts users), I also need to increase permissions/trust a user places in my app (a bad thing since it repels users). Are there any recommendations on how apps should best handle this conflict of interests?
List of scopes in your client code - this is what a user authorizes your app to do
When you request authorization from a user, you need to specify what you would like the user to consent to. This is what the list of scopes is used for - it controls the text the user sees when they authorize your application, and the refresh / access tokens granted by that authorization are limited to making API calls that are allowed by those scopes.
List of enabled services in the API Console - this is what your app authorizes users to do
To my knowledge there is no list of scopes specified in the API Console. There is however a list of Google services that can enabled. Enabling/disabling a service here is more about turning on/off ability to make API calls and managing quota and/or accepting terms of service related to that API, than it is authorization.
When an API call is made - you send along an access token
The access token encapsulates the user making the request, the scopes the user authorized you for, and the client ID used for the authorization (which in turn belongs to your project). At this point you need to have the service that the API call is sent to enabled on the project, and the correct scope for the API request - or you will get a 403.
When your list of required scopes changes - you should expect users to need to re-authorize
At the point you request an access token (typically by sending a refresh token) you need to be prepared for that request not to succeed. Maybe it's because you've added scopes - but maybe a user has chosen to visit https://accounts.google.com/IssuedAuthSubTokens and has revoked your applications access. I'm not sure whether if you request less scopes than was granted by the user initially will trigger this, I would experiment to test - but the point is that regardless your code needs to be able to handle this scenario. I believe the OAuth2DecoratorFromClientSecrets (from the linked question) will handle this gracefully for you but am not certain - it should be easy enough to verify.
Using the same authorization across multiple clients - suggest reading through this doc and see if it covers all of your scenarios: https://developers.google.com/accounts/docs/CrossClientAuth
To see scopes granted to an access token - use the OAuth2 API: https://www.googleapis.com/oauth2/v1/tokeninfo?access_token=yaxxxxxxxxxxxxxxx