Hi Ryan, Thanks a lot for following-up and providing the detailed responses. The answers are very helpful.
>> I don't think I can answer everything. Acknowledged. This is inherently due to the complex nature of the OAuth 2.0 / SSO specification and host system implementation details / custom authorization requirements. Also, Adam (from the CRE / w3 Connections teams) has reached out to me offline and graciously provided me with very valuable information, feedback & insight as well. >> First at a high level I am wondering if you are trying to avoid the >> typical OAuth dance where the user has to log in and grant access to the app/gadget? In this case, lets assume that our gadgets (Jazz) are trusted and perform makeRequest operations via OAuth 2.0 / SSO. We want to support two use cases: (a) Add our gadgets to our OpenSocial gadget container (e.g. Jazz) (b) Add our gadgets to another tools OpenSocial gadget container (e.g. JIRA). For case (a), the answer is yes. Ideally, we would like to avoid the typical OAuth dance. Our gadgets are trusted and the user has already authenticated with our Authorization Server; since the page hosting our OpenSocial gadget container is a protected resource and the application serving the page already has a SSO access token. For case (b), I suspect we want to explicitly support the OAuth dance; since, we are at the mercy of the host applications OpenSocial gadget container implementation (although we control the server's deployment and have the ability to inject adapters via plug-ins, so we may be able to overcome various limitations to some extent). To simply things from a gadget development standpoint, we decided (for the time being) to explicitly support the OAuth dance in the gadget in order to support both case (a) & case (b) in order to avoid any hacky or insecure solutions. >> I could see this hindering the user experience if you have a gadget asking a user to do the OAuth dance with itself. Agree, this is a concern that would need to be addressed before our release ships. For case (a), our current implementation so far opens the OAuth dialog pop-up window and Shindig quickly closes it via the response from the OAuth2CallbackServlet; since, the user has already authenticated with the Authorization Server. This event results in a dialog "flash" which is irksome from a user experience perspective. For case (a), Adam mentioned that his team successfully implemented a custom gadget feature that facilitates the OAuth dance via a hidden iframe. For case (b), they fall back to using the oauthpopup feature if their custom feature is not detected in the container (via hasFeature). This is definitely a solution we are looking to explore as well. >> Shindig has guice modules which are responsible for fetching and storing access tokens (keyed on the gadget and the user). >> If you could point Shindig at the place where the access tokens are stored than Shindig could use those access tokens. >> Essentially it might make sense to have a centralized store for access tokens that both the application/container and the Shindig server use. e.g. org.apache.shindig.gadgets.oauth2.persistence.sample.OAuth2PersistenceModule: This is a very good idea. I'm going to bring this suggestion to our PMC / architects. >> What questions do you have about OAuth popup? There isn't really much complex code in there. >> The one tricky think to keep in mind is that the OAuth callback servlets do interact with the JavaScript in that >> feature. For example that is how the popup window is closed automatically. Yes, I see now that the pop-up window is closed via a successful response from the OAuth2CallbackServlet. i.e. org.apache.shindig.gadgets.servlet.OAuth2CallbackServlet.RESP_BODY One concern I have with this flow is that the gadget is informed via the callback that authentication was successful; but, has no way to know whether the second part of the OAuth 2.0 dance completely successfully (i.e. Shindig successfully exchanged the authorization code with the Authorization Server for the access token). Unless I'm missing something, there is no communication between Shindig (client) and the gadget (user-agent) in order to notify the gadget that it is safe to perform another makeRequest operation. Ideally, we would like to automatically perform another makeRequest once the OAuth pop-up dialog closes (like the sample OAuth gadgets provided by Shindig); however, it can result in infinite OAuth pop-up windows being opened if something goes awry during the token exchange (if gadget safeguards are not put in place). Is this a valid concern? After reading the OAuth 2.0 specification, it seems to be a problem with the specification - not Shindig. >> But I am guessing you should be able to enable logging for Shindig the same way you would do for other apps >> in the web container. Yes, I figured it out. In my Shindig development workspace, I configured my Tomcat server launch to include the following Java system property in the "VM arguments" section: -Djava.util.logging.config.file=<path>\Workspaces\Jazz\ShindigTrunk\Servers \shindig-project-config\logging.properties" -------------------------------------------------------------------- logging.properties -------------------------------------------------------------------- handlers=java.util.logging.ConsoleHandler java.util.logging.ConsoleHandler.level=ALL java.util.logging.ConsoleHandler.formatter= java.util.logging.SimpleFormatter .level=INFO # Shindig gadgets org.apache.shindig.gadgets.level=FINEST -------------------------------------------------------------------- >> There are a lot of them, as far as which ones are related to grant types I am not sure. Found them. I am using a variation of the following handlers (copied and referenced in their own module): CodeAuthorizationResponseHandler CodeGrantTypeHandler (which are injected via Guice by this module: OAuth2HandlerModule) Thanks, Mike From: Ryan Baxter <rbaxte...@apache.org> To: "dev@shindig.apache.org" <dev@shindig.apache.org>, Date: 2013-10-02 07:41 PM Subject: Re: Questions about configuring outbound SSO / OAuth 2.0 support in Shindig to facilitate gadget makeRequest calls Mike I will try to answer some of the questions the best I can, but I don't think I can answer everything. Hopefully I can get your going in the right direction. First at a high level I am wondering if you are trying to avoid the typical OAuth dance where the user has to log in and grant access to the app/gadget? I could see this hindering the user experience if you have a gadget asking a user to do the OAuth dance with itself. On Tue, Oct 1, 2013 at 7:25 PM, Mike Pawlowski <mpaw...@ca.ibm.com> wrote: > > > Hi, > > --------------------------------------------------------------------------------------------------- > Use Case > --------------------------------------------------------------------------------------------------- > > We are trying to integrate a Shindig application as a direct member in our > SSO group based on the > OAuth 2.0 protocol (i.e. Assigned a client key and secret). > Specifically, we want to be able to execute a makeRequest from a gadget > against a protected > resource located on member applications in the SSO group. > > --------------------------------------------------------------------------------------------------- > Problem > --------------------------------------------------------------------------------------------------- > > Unfortunately, I haven't had any success in configuring Shindig to work > out-of-the-box with > our SSO Authorization Server. Ostensibly, our Authorization Server does not > strictly conform to > the OAuth 2.0 protocol (http://tools.ietf.org/html/rfc6749 ). > > We support a variant of the Authorization Code flow with an SSO twist. > > e.g. We use response and grant type values that differ from the > specification: > > 4.1.1. Authorization Request > response_type > REQUIRED. Value MUST be set to "code". > > 4.1.3. Access Token Request > grant_type > REQUIRED. Value MUST be set to "authorization_code". > > --------------------------------------------------------------------------------------------------- > Questions > --------------------------------------------------------------------------------------------------- > > (Q 1) As a meta-question, what is the recommended way to configure Shindig > to facilitate gadget makeRequest calls to protected resources using SSO / > OAuth 2.0? If you are just looking to test OAuth with Shindig out of the box the only thing you need to worry about configuring is the oauth.json and oauth2.json files. For example if you want to test the oauth2_google.xml gadget in the sample container in Shindig you would have to go to the Google API Console register the gadget to get an API key and secret and then add them to the oauth2.json file. > > I just want to validate whether we are taking the right approach by making > Shindig directly participate as a member our SSO group. > I'm following the OAuth 2 examples shipped with Shindig > (e.g. /gadgets/oauth2/oauth2_google.xml) > > On the surface, the easier alternative would be to get the access token and > pass it in as a parameter to the makeRequest call > (essentially Shindig would strictly proxy the request to the protected > resource rather than explicitly handle authorization). > i.e. > params[gadgets.io.RequestParameters.OAUTH_REQUEST_TOKEN] = "some-token"; > (or "some-token" is provided as a value to some custom Authorization > header) This is generally discouraged. All information related to OAuth is kept on the server. When the gadget makes a request the requires OAuth the proxy will add the access token to the request if it has one. If it doesn't have one will send back the authorization URL for the gadget to then use the oauth-popup feature to do the OAuth dance. > > In our case, the OpenSocial gadget container is located on a page that is > itself a protected resource. > The user will already be authenticated with our Authorization Server and > the server hosting the > page / OpenSocial gadget container will already have the corresponding > access token. > Unfortunately, the server hosting the page is on a different domain than > the Shindig server. > As a result, securely passing the access token to the gadget container / > gadget is very problematic. > I'm not sure if there is API in the Common Container that we could leverage > or some other established > procedure / method we could employ to get the access token securely... > Shindig has guice modules which are responsible for fetching and storing access tokens (keyed on the gadget and the user). If you could point Shindig at the place where the access tokens are stored than Shindig could use those access tokens. Essentially it might make sense to have a centralized store for access tokens that both the application/container and the Shindig server use. > Is there another option (i.e. Third approach)? > > Also, I'm curious if you know if other Shindig consumers have similar SSO > integration requirements and how they > implemented their support with respect to gadget makeRequest calls. It > would be a good point of reference. > > > (Q 2) Is there any documentation or guidance or examples on configuring > SSO / OAuth 2.0 support in Shindig and gadgets? > > I'm currently reverse engineering the Shindig source to figure out things, > relying on > comments in the various configuration files and reading the relevant > gadget / RFC specification > > e.g. > http://opensocial-resources.googlecode.com/svn/spec/2.5/Core-Gadget.xml#gadgets.io.makeRequest > > http://opensocial-resources.googlecode.com/svn/spec/2.5/Core-Gadget.xml#OAuth > > http://tools.ietf.org/html/rfc6749 > > For example, I noticed that there appears to be a degree of magic being > used in the "oauthpopup" gadget feature > to handle the OAuth 2.0 user authentication and redirection flow - which > isn't explained to a large degree. > This link might be helpful https://cwiki.apache.org/confluence/display/SHINDIG/OAuth+2.0+Service +Provider+Implementation+in+Apache+Shindig What questions do you have about OAuth popup? There isn't really much complex code in there. The one tricky think to keep in mind is that the OAuth callback servlets do interact with the JavaScript in that feature. For example that is how the popup window is closed automatically. > > (Q 3) What are the OAuth 2.0 / SSO specific classes / configuration files / > etc I should be focusing on or be aware of? > > I'm just trying to get an inventory of all the Shindig files I need to > modify or potentially be aware of (for debugging purposes) that would > assist me > in my integration task: > > e.g. Examples > /gadgets/oauth2 > > e.g. Configuration files > /WEB-INF/classes/config/oauth2.json > shindig.properties > > e.g. Servlets > /src/main/java/org/apache/shindig/gadgets/servlet/OAuth2CallbackServlet.java > > e.g. Packages / Classes > org.apache.shindig.gadgets.oauth2 > > e.g. JavaScript > src/main/javascript/features/oauthpopup/oauthpopup.js > > Anything else? > I think that covers it. > > (Q 4) How do I enable server logging in Shindig? > > I'd like to start by turning on all Shindig server logging across the board > and then progressively > filtering it down by log level and then only by OAuth specific classes: > e.g. > > if (OAuth2CallbackServlet.LOGGER.isLoggable(Level.FINE)) { > OAuth2CallbackServlet.LOGGER.log(Level.FINE, " callback exception " > , t); > } > > Is it just a matter of adding a log4j.properties file in a certain > directory and configuring by class? > e.g. > log4j.logger.net.jazz.ajax.service/ProxyOperation=TRACE > log4j.logger.net.jazz.ajax.service/AuthClient=TRACE > Hmmm haven't done this one yet. But I am guessing you should be able to enable logging for Shindig the same way you would do for other apps in the web container. > > (Q 5) How do I inject support for custom OAuth 2.0 grant types into > Shindig? > > Assuming we are following the right approach defined in the "Use Case" > section and (Q 1), there > appears to be injection points for consumers to add support for custom > grant types (which I *believe* is required in our case): > (a) org.apache.shindig.gadgets.oauth2.handler.GrantRequestHandler > (b) > org.apache.shindig.gadgets.oauth2.handler.AuthorizationEndpointResponseHandler > > Are there any other injection points that are relevant to the SSO / OAuth > 2.0 integration task? There are a lot of them, as far as which ones are related to grant types I am not sure. At some level I am sure most of the OAuth implementation is replaceable via Guice injection however there are probably only a few key pieces that you probably want to replace. There are several Guice modules for OAuth in the web.xml, that is probably the best place to start. > Just to confirm, is this accomplished via Guice? > Is this the best resource for learning how to use Guice: > https://code.google.com/p/google-guice/ ? That and a little bit of debugging ;) That is how I learned anyways. > > > Thanks in advance, > > Mike >