Author: doll
Date: Fri Jun 20 18:00:35 2008
New Revision: 670110
URL: http://svn.apache.org/viewvc?rev=670110&view=rev
Log:
SHINDIG-290
Patch from Dirk Balfanz. First impl of some basic oauth code. These classes
still need to be filled in, this is just a start.
Added:
incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/oauth/
incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/oauth/OAuthContext.java
incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/oauth/OAuthServletFilter.java
incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/oauth/
incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/oauth/OAuthContextTest.java
incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/oauth/OAuthServletFilterTest.java
Modified:
incubator/shindig/trunk/java/server/src/main/webapp/WEB-INF/web.social.xml
incubator/shindig/trunk/java/social-api/pom.xml
Modified:
incubator/shindig/trunk/java/server/src/main/webapp/WEB-INF/web.social.xml
URL:
http://svn.apache.org/viewvc/incubator/shindig/trunk/java/server/src/main/webapp/WEB-INF/web.social.xml?rev=670110&r1=670109&r2=670110&view=diff
==============================================================================
--- incubator/shindig/trunk/java/server/src/main/webapp/WEB-INF/web.social.xml
(original)
+++ incubator/shindig/trunk/java/server/src/main/webapp/WEB-INF/web.social.xml
Fri Jun 20 18:00:35 2008
@@ -29,6 +29,16 @@
<param-value>org.apache.shindig.common.CommonGuiceModule:org.apache.shindig.social.SocialApiGuiceModule</param-value>
</context-param>
+ <filter>
+ <filter-name>oauthFilter</filter-name>
+
<filter-class>org.apache.shindig.social.oauth.OAuthServletFilter</filter-class>
+ </filter>
+
+ <filter-mapping>
+ <filter-name>oauthFilter</filter-name>
+ <url-pattern>/social/*</url-pattern>
+ </filter-mapping>
+
<listener>
<listener-class>org.apache.shindig.common.servlet.GuiceServletContextListener</listener-class>
</listener>
Modified: incubator/shindig/trunk/java/social-api/pom.xml
URL:
http://svn.apache.org/viewvc/incubator/shindig/trunk/java/social-api/pom.xml?rev=670110&r1=670109&r2=670110&view=diff
==============================================================================
--- incubator/shindig/trunk/java/social-api/pom.xml (original)
+++ incubator/shindig/trunk/java/social-api/pom.xml Fri Jun 20 18:00:35 2008
@@ -100,5 +100,10 @@
<artifactId>jetty</artifactId>
<scope>test</scope>
</dependency>
+ <dependency>
+ <groupId>net.oauth</groupId>
+ <artifactId>core</artifactId>
+ <scope>compile</scope>
+ </dependency>
</dependencies>
</project>
Added:
incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/oauth/OAuthContext.java
URL:
http://svn.apache.org/viewvc/incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/oauth/OAuthContext.java?rev=670110&view=auto
==============================================================================
---
incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/oauth/OAuthContext.java
(added)
+++
incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/oauth/OAuthContext.java
Fri Jun 20 18:00:35 2008
@@ -0,0 +1,127 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations under the License.
+ */
+package org.apache.shindig.social.oauth;
+
+import javax.servlet.http.HttpServletRequest;
+
+/**
+ * A class that encapsulates the OAuth-related authentication information about
+ * an HTTP request. If a servlet requires that a request was made by a specific
+ * client, it could to the following:
+ *
+ * public void doGet(HttpServletRequest req, HttpServletResponse resp) {
+ * ...
+ * OAuthContext authContext = OAuthContext.forRequest(req);
+ * if (authContext.getAuthMethod() == OAuthContext.AuthMethod.NONE) {
+ * respondWithError();
+ * } else {
+ * String consumer = authContext.getConsumerKey();
+ * if (clientIsAllowed(consumer)) {
+ * handleRequest(req, resp);
+ * } else {
+ * respondWithError():
+ * }
+ * }
+ */
+public class OAuthContext {
+
+ /*
+ * The different authentication methods.
+ */
+ public enum AuthMethod {
+ NONE, // no authentication attempted, or authentication failed
+
+ OAUTH, // OAuth succeeded, which means we'll have a consumer key and an
+ // OAuth token
+
+ SIGNED // SignedFetch succeeded, in which case we'll just have a consumer
+ // key
+ }
+
+ static final String OAUTH_CONTEXT =
+ "org.apache.shindig.social.oauth.context";
+
+ private AuthMethod authMethod;
+ private String consumerKey;
+ private String oauthToken;
+
+ /**
+ * Returns the OAuth context object for this http request. If no OAuth
+ * context object exists, then a newly-created context object for this
+ * request is returned.
+ */
+ public static OAuthContext fromRequest(HttpServletRequest req) {
+ OAuthContext result = (OAuthContext)req.getAttribute(OAUTH_CONTEXT);
+ return (result == null)
+ ? newContextForRequest(req)
+ : result;
+ }
+
+ /**
+ * Makes a new OAuth context object and stores it in the HttpServletRequest
+ * @param req
+ * @return the newly-created object.
+ */
+ static OAuthContext newContextForRequest(HttpServletRequest req) {
+ OAuthContext context = new OAuthContext();
+ req.setAttribute(OAUTH_CONTEXT, context);
+ return context;
+ }
+
+ // newly-created contexts know of no authentication
+ OAuthContext() {
+ this.authMethod = AuthMethod.NONE;
+ this.consumerKey = null;
+ this.oauthToken = null;
+ }
+
+ /**
+ * Returns the method of authentication used by the client.
+ */
+ public AuthMethod getAuthMethod() {
+ return authMethod;
+ }
+
+ public void setAuthMethod(AuthMethod method) {
+ authMethod = method;
+ }
+
+ /**
+ * Returns the consumer key that was authenticated by the server. This value
+ * should only be trusted if getAuthMethod() returns OAUTH or SIGNED.
+ */
+ public String getConsumerKey() {
+ return consumerKey;
+ }
+
+ public void setConsumerKey(String key) {
+ consumerKey = key;
+ }
+
+ /**
+ * Returns the OAuth token that was authenticated by the server. This value
+ * should only be trusted if getAuthMethod() return OAUTH.
+ */
+ public String getOAuthToken() {
+ return oauthToken;
+ }
+
+ public void setOAuthToken(String token) {
+ oauthToken = token;
+ }
+}
Added:
incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/oauth/OAuthServletFilter.java
URL:
http://svn.apache.org/viewvc/incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/oauth/OAuthServletFilter.java?rev=670110&view=auto
==============================================================================
---
incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/oauth/OAuthServletFilter.java
(added)
+++
incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/oauth/OAuthServletFilter.java
Fri Jun 20 18:00:35 2008
@@ -0,0 +1,87 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations under the License.
+ */
+package org.apache.shindig.social.oauth;
+
+import net.oauth.OAuth;
+import net.oauth.OAuthMessage;
+import net.oauth.server.OAuthServlet;
+
+import org.apache.commons.lang.NotImplementedException;
+
+import java.io.IOException;
+
+import javax.servlet.Filter;
+import javax.servlet.FilterChain;
+import javax.servlet.FilterConfig;
+import javax.servlet.ServletException;
+import javax.servlet.ServletRequest;
+import javax.servlet.ServletResponse;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+public class OAuthServletFilter implements Filter {
+
+
+ public void init(FilterConfig filterConfig) {
+ }
+
+ public void destroy() {
+ }
+
+ public void doFilter(ServletRequest request, ServletResponse response,
+ FilterChain chain) throws IOException, ServletException {
+
+ if (!(request instanceof HttpServletRequest)) {
+ throw new ServletException("OAuth filter can only handle HTTP");
+ }
+
+ if (!(response instanceof HttpServletResponse)) {
+ throw new ServletException("OAuth filter can only handle HTTP");
+ }
+
+ HttpServletRequest req = (HttpServletRequest)request;
+ HttpServletResponse res = (HttpServletResponse)response;
+ OAuthContext authContext = OAuthContext.newContextForRequest(req);
+
+ OAuthMessage requestMessage = OAuthServlet.getMessage(req, null);
+
+ if (requestMessage.getParameter(OAuth.OAUTH_SIGNATURE) == null) {
+ // doesn't seem to be an OAuth request
+ chain.doFilter(request, response);
+ return;
+ }
+
+ if (requestMessage.getToken() == null) {
+ handleSignedFetch(requestMessage, authContext);
+ } else {
+ handleFullOAuth(requestMessage, authContext);
+ }
+
+ chain.doFilter(request, response);
+ }
+
+ private void handleFullOAuth(OAuthMessage requestMessage,
+ OAuthContext authContext) {
+ throw new NotImplementedException("full OAuth support not yet
implemented");
+ }
+
+ private void handleSignedFetch(OAuthMessage requestMessage,
+ OAuthContext context) {
+ // TODO implement this method
+ }
+}
Added:
incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/oauth/OAuthContextTest.java
URL:
http://svn.apache.org/viewvc/incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/oauth/OAuthContextTest.java?rev=670110&view=auto
==============================================================================
---
incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/oauth/OAuthContextTest.java
(added)
+++
incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/oauth/OAuthContextTest.java
Fri Jun 20 18:00:35 2008
@@ -0,0 +1,303 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations under the License.
+ */
+package org.apache.shindig.social.oauth;
+
+import junit.framework.TestCase;
+
+import org.apache.shindig.social.oauth.OAuthContext.AuthMethod;
+
+import java.io.BufferedReader;
+import java.security.Principal;
+import java.util.Collections;
+import java.util.Enumeration;
+import java.util.HashMap;
+import java.util.Locale;
+import java.util.Map;
+
+import javax.servlet.RequestDispatcher;
+import javax.servlet.ServletInputStream;
+import javax.servlet.http.Cookie;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpSession;
+
+public class OAuthContextTest extends TestCase {
+
+ public void testGettersAndSetters() throws Exception {
+ OAuthContext context = new OAuthContext();
+
+ // first, make sure it's constructed in the right state
+ assertEquals(OAuthContext.AuthMethod.NONE, context.getAuthMethod());
+ assertNull(context.getConsumerKey());
+ assertNull(context.getOAuthToken());
+
+ // then, test the getters and setters
+ context.setAuthMethod(AuthMethod.OAUTH);
+ assertEquals(OAuthContext.AuthMethod.OAUTH, context.getAuthMethod());
+
+ context.setConsumerKey("consumer");
+ assertEquals("consumer", context.getConsumerKey());
+
+ context.setOAuthToken("token");
+ assertEquals("token", context.getOAuthToken());
+ }
+
+ public void testCreationAndOverriding() throws Exception {
+
+ HttpServletRequest request = new FakeHttpServletRequest();
+
+ // make sure that we always get a OAuthContext object
+ OAuthContext context = OAuthContext.fromRequest(request);
+
+ assertNotNull(context);
+
+ // make sure that we can override existing contexts
+ OAuthContext context2 = OAuthContext.newContextForRequest(request);
+
+ assertNotSame(context, context2);
+ assertEquals(OAuthContext.AuthMethod.NONE, context2.getAuthMethod());
+
+ OAuthContext context3 = OAuthContext.fromRequest(request);
+ assertSame(context2, context3);
+ }
+
+ public static class FakeHttpServletRequest implements HttpServletRequest {
+
+ private HashMap<String, Object> attributes = new HashMap<String, Object>();
+
+ public String getAuthType() {
+ return null;
+ }
+
+ public String getContextPath() {
+ return null;
+ }
+
+ public Cookie[] getCookies() {
+ return null;
+ }
+
+ public long getDateHeader(String name) {
+ return 0;
+ }
+
+ public String getHeader(String name) {
+ return null;
+ }
+
+ @SuppressWarnings("unchecked")
+ public Enumeration getHeaderNames() {
+ return null;
+ }
+
+ @SuppressWarnings("unchecked")
+ public Enumeration getHeaders(String name) {
+ return null;
+ }
+
+ public int getIntHeader(String name) {
+ return 0;
+ }
+
+ public String getMethod() {
+ return null;
+ }
+
+ public String getPathInfo() {
+ return null;
+ }
+
+ public String getPathTranslated() {
+ return null;
+ }
+
+ public String getQueryString() {
+ return null;
+ }
+
+ public String getRemoteUser() {
+ return null;
+ }
+
+ public String getRequestURI() {
+ return null;
+ }
+
+ public StringBuffer getRequestURL() {
+ return new StringBuffer("http://foo.com/bar");
+ }
+
+ public String getRequestedSessionId() {
+ return null;
+ }
+
+ public String getServletPath() {
+ return null;
+ }
+
+ public HttpSession getSession() {
+ return null;
+ }
+
+ public HttpSession getSession(boolean create) {
+ return null;
+ }
+
+ public Principal getUserPrincipal() {
+ return null;
+ }
+
+ public boolean isRequestedSessionIdFromCookie() {
+ return false;
+ }
+
+ public boolean isRequestedSessionIdFromURL() {
+ return false;
+ }
+
+ public boolean isRequestedSessionIdFromUrl() {
+ return false;
+ }
+
+ public boolean isRequestedSessionIdValid() {
+ return false;
+ }
+
+ public boolean isUserInRole(String role) {
+ return false;
+ }
+
+ public Object getAttribute(String name) {
+ return attributes.get(name);
+ }
+
+ @SuppressWarnings("unchecked")
+ public Enumeration getAttributeNames() {
+ return Collections.enumeration(attributes.keySet());
+ }
+
+ public String getCharacterEncoding() {
+ return null;
+ }
+
+ public int getContentLength() {
+ return 0;
+ }
+
+ public String getContentType() {
+ return null;
+ }
+
+ public ServletInputStream getInputStream() {
+ return null;
+ }
+
+ public String getLocalAddr() {
+ return null;
+ }
+
+ public String getLocalName() {
+ return null;
+ }
+
+ public int getLocalPort() {
+ return 0;
+ }
+
+ public Locale getLocale() {
+ return null;
+ }
+
+ @SuppressWarnings("unchecked")
+ public Enumeration getLocales() {
+ return null;
+ }
+
+ public String getParameter(String name) {
+ return null;
+ }
+
+ @SuppressWarnings("unchecked")
+ public Map getParameterMap() {
+ return new HashMap();
+ }
+
+ @SuppressWarnings("unchecked")
+ public Enumeration getParameterNames() {
+ return null;
+ }
+
+ public String[] getParameterValues(String name) {
+ return new String[0];
+ }
+
+ public String getProtocol() {
+ return null;
+ }
+
+ public BufferedReader getReader() {
+ return null;
+ }
+
+ public String getRealPath(String path) {
+ return null;
+ }
+
+ public String getRemoteAddr() {
+ return null;
+ }
+
+ public String getRemoteHost() {
+ return null;
+ }
+
+ public int getRemotePort() {
+ return 0;
+ }
+
+ public RequestDispatcher getRequestDispatcher(String path) {
+ return null;
+ }
+
+ public String getScheme() {
+ return null;
+ }
+
+ public String getServerName() {
+ return null;
+ }
+
+ public int getServerPort() {
+ return 0;
+ }
+
+ public boolean isSecure() {
+ return false;
+ }
+
+ public void removeAttribute(String name) {
+ attributes.remove(name);
+ }
+
+ public void setAttribute(String name, Object o) {
+ attributes.put(name, o);
+ }
+
+ public void setCharacterEncoding(String env) {
+ }
+ }
+}
Added:
incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/oauth/OAuthServletFilterTest.java
URL:
http://svn.apache.org/viewvc/incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/oauth/OAuthServletFilterTest.java?rev=670110&view=auto
==============================================================================
---
incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/oauth/OAuthServletFilterTest.java
(added)
+++
incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/oauth/OAuthServletFilterTest.java
Fri Jun 20 18:00:35 2008
@@ -0,0 +1,53 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations under the License.
+ */
+package org.apache.shindig.social.oauth;
+
+import org.apache.shindig.social.EasyMockTestCase;
+import org.apache.shindig.social.oauth.OAuthContextTest.FakeHttpServletRequest;
+
+import javax.servlet.FilterChain;
+import javax.servlet.http.HttpServletResponse;
+
+public class OAuthServletFilterTest extends EasyMockTestCase {
+
+ private FakeHttpServletRequest request;
+ private HttpServletResponse response;
+ private FilterChain chain;
+
+ private OAuthServletFilter filter;
+
+ @Override
+ protected void setUp() throws Exception {
+ super.setUp();
+
+ request = new FakeHttpServletRequest();
+ response = mock(HttpServletResponse.class);
+ chain = mock(FilterChain.class);
+
+ filter = new OAuthServletFilter();
+ }
+
+ public void testUnauthenticated() throws Exception {
+ filter.doFilter(request, response, chain);
+
+ assertEquals(OAuthContext.AuthMethod.NONE,
+ OAuthContext.fromRequest(request).getAuthMethod());
+ }
+
+
+}