Updated Branches:
  refs/heads/master 51bdf0996 -> 342bfe1dc

CAMEL-6424: camel-netty-http added support for basic auth. Work in progress.


Project: http://git-wip-us.apache.org/repos/asf/camel/repo
Commit: http://git-wip-us.apache.org/repos/asf/camel/commit/8042c338
Tree: http://git-wip-us.apache.org/repos/asf/camel/tree/8042c338
Diff: http://git-wip-us.apache.org/repos/asf/camel/diff/8042c338

Branch: refs/heads/master
Commit: 8042c338420cfe490e04bfc73a3a5e51c63d1f2d
Parents: 51bdf09
Author: Claus Ibsen <davscl...@apache.org>
Authored: Tue Jul 16 12:30:25 2013 +0200
Committer: Claus Ibsen <davscl...@apache.org>
Committed: Tue Jul 16 12:30:33 2013 +0200

----------------------------------------------------------------------
 .../ConstraintMappingContextPathMatcher.java    | 103 ---------------
 .../netty/http/DefaultSecurityConstraint.java   | 127 +++++++++++++++++++
 .../netty/http/JAASSecurityAuthenticator.java   |  39 +++++-
 .../component/netty/http/NettyHttpEndpoint.java |   2 +-
 .../http/NettyHttpSecurityConfiguration.java    |  23 +++-
 .../netty/http/SecurityAuthenticator.java       |  10 ++
 .../netty/http/SecurityConstraint.java          |  31 +++++
 .../http/handlers/HttpServerChannelHandler.java |  50 +++++++-
 ...ConstraintMappingContextPathMatcherTest.java | 108 ----------------
 .../http/DefaultSecurityConstraintTest.java     | 108 ++++++++++++++++
 .../NettyHttpBasicAuthConstraintMapperTest.java |   4 +-
 ...asicAuthCustomSecurityAuthenticatorTest.java |  10 ++
 ...HttpSimpleBasicAuthConstraintMapperTest.java |   4 +-
 13 files changed, 388 insertions(+), 231 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/camel/blob/8042c338/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/ConstraintMappingContextPathMatcher.java
----------------------------------------------------------------------
diff --git 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/ConstraintMappingContextPathMatcher.java
 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/ConstraintMappingContextPathMatcher.java
deleted file mode 100644
index 4a71b64..0000000
--- 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/ConstraintMappingContextPathMatcher.java
+++ /dev/null
@@ -1,103 +0,0 @@
-/**
- * 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.camel.component.netty.http;
-
-import java.util.LinkedHashSet;
-import java.util.Set;
-
-import org.apache.camel.util.EndpointHelper;
-
-/**
- * A {@link ContextPathMatcher} which can be used to define a set of mappings 
to
- * as constraints.
- * <p/>
- * This matcher will match as <tt>true</tt> if no inclusions has been defined.
- * First all the inclusions is check for matching. If a inclusion matches,
- * then the exclusion is checked, and if any of them matches, then the 
exclusion
- * will override the match and force returning <tt>false</tt>.
- * <p/>
- * Wildcards and regular expressions is supported as this implementation uses
- * {@link EndpointHelper#matchPattern(String, String)} method for matching.
- * <p/>
- * This constraint matcher allows you to setup context path rules that will 
restrict
- * access to paths, and then override and have exclusions that may allow 
access to
- * public paths.
- */
-public class ConstraintMappingContextPathMatcher implements ContextPathMatcher 
{
-
-    private Set<String> inclusions;
-    private Set<String> exclusions;
-
-    @Override
-    public boolean matches(String target) {
-        boolean matches = true;
-
-        if (inclusions != null && !inclusions.isEmpty()) {
-            boolean found = false;
-            for (String constraint : inclusions) {
-                if (EndpointHelper.matchPattern(target, constraint)) {
-                    found = true;
-                    break;
-                }
-            }
-            matches = found;
-        }
-
-        // if matches check for any exclusions
-        if (matches && exclusions != null && !exclusions.isEmpty()) {
-            for (String constraint : exclusions) {
-                if (EndpointHelper.matchPattern(target, constraint)) {
-                    // force false if this was an exclusion
-                    matches = false;
-                    break;
-                }
-            }
-        }
-
-        return matches;
-    }
-
-    public void addInclusion(String constraint) {
-        if (inclusions == null) {
-            inclusions = new LinkedHashSet<String>();
-        }
-        inclusions.add(constraint);
-    }
-
-    public void addExclusion(String constraint) {
-        if (exclusions == null) {
-            exclusions = new LinkedHashSet<String>();
-        }
-        exclusions.add(constraint);
-    }
-
-    public Set<String> getInclusions() {
-        return inclusions;
-    }
-
-    public void setInclusions(Set<String> inclusions) {
-        this.inclusions = inclusions;
-    }
-
-    public Set<String> getExclusions() {
-        return exclusions;
-    }
-
-    public void setExclusions(Set<String> exclusions) {
-        this.exclusions = exclusions;
-    }
-}

http://git-wip-us.apache.org/repos/asf/camel/blob/8042c338/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/DefaultSecurityConstraint.java
----------------------------------------------------------------------
diff --git 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/DefaultSecurityConstraint.java
 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/DefaultSecurityConstraint.java
new file mode 100644
index 0000000..91effe5
--- /dev/null
+++ 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/DefaultSecurityConstraint.java
@@ -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.camel.component.netty.http;
+
+import java.util.LinkedHashSet;
+import java.util.Map;
+import java.util.Set;
+
+import org.apache.camel.util.EndpointHelper;
+
+/**
+ * A default {@link SecurityConstraint} which can be used to define a set of 
mappings to
+ * as constraints.
+ * <p/>
+ * This constraint will match as <tt>true</tt> if no inclusions has been 
defined.
+ * First all the inclusions is check for matching. If a inclusion matches,
+ * then the exclusion is checked, and if any of them matches, then the 
exclusion
+ * will override the match and force returning <tt>false</tt>.
+ * <p/>
+ * Wildcards and regular expressions is supported as this implementation uses
+ * {@link EndpointHelper#matchPattern(String, String)} method for matching.
+ * <p/>
+ * This restricted constraint allows you to setup context path rules that will 
restrict
+ * access to paths, and then override and have exclusions that may allow 
access to
+ * public paths.
+ */
+public class DefaultSecurityConstraint implements SecurityConstraint {
+
+    // url -> roles
+    private Map<String, String> inclusions;
+    // url
+    private Set<String> exclusions;
+
+    @Override
+    public String restricted(String url) {
+        // check excluded first
+        if (excludedUrl(url)) {
+            return null;
+        }
+
+        // is the url restricted?
+        String constraint = includedUrl(url);
+        if (constraint == null) {
+            return null;
+        }
+
+        // is there any roles for the restricted url?
+        String roles = inclusions != null ? inclusions.get(constraint) : null;
+        if (roles == null) {
+            // use wildcard to indicate any role is accepted
+            return "*";
+        } else {
+            return roles;
+        }
+    }
+
+    private String includedUrl(String url) {
+        if (inclusions != null && !inclusions.isEmpty()) {
+            for (String constraint : inclusions.keySet()) {
+                if (EndpointHelper.matchPattern(url, constraint)) {
+                    return constraint;
+                }
+            }
+            // not in included so return null as its not restricted
+            return null;
+        }
+
+        // by default if no included has been configured then everything is 
restricted
+        return "*";
+    }
+
+    private boolean excludedUrl(String url) {
+        if (exclusions != null && !exclusions.isEmpty()) {
+            for (String constraint : exclusions) {
+                if (EndpointHelper.matchPattern(url, constraint)) {
+                    // force not matches if this was an exclusion
+                    return true;
+                }
+            }
+        }
+
+        return false;
+    }
+
+    public void addInclusion(String constraint) {
+        if (inclusions == null) {
+            inclusions = new java.util.LinkedHashMap<String, String>();
+        }
+        inclusions.put(constraint, null);
+    }
+
+    public void addInclusion(String constraint, String roles) {
+        if (inclusions == null) {
+            inclusions = new java.util.LinkedHashMap<String, String>();
+        }
+        inclusions.put(constraint, roles);
+    }
+
+    public void addExclusion(String constraint) {
+        if (exclusions == null) {
+            exclusions = new LinkedHashSet<String>();
+        }
+        exclusions.add(constraint);
+    }
+
+    public void setInclusions(Map<String, String> inclusions) {
+        this.inclusions = inclusions;
+    }
+
+    public void setExclusions(Set<String> exclusions) {
+        this.exclusions = exclusions;
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/8042c338/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/JAASSecurityAuthenticator.java
----------------------------------------------------------------------
diff --git 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/JAASSecurityAuthenticator.java
 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/JAASSecurityAuthenticator.java
index a34f16b..fd52ca8 100644
--- 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/JAASSecurityAuthenticator.java
+++ 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/JAASSecurityAuthenticator.java
@@ -17,6 +17,8 @@
 package org.apache.camel.component.netty.http;
 
 import java.io.IOException;
+import java.security.Principal;
+import java.util.Locale;
 import javax.security.auth.Subject;
 import javax.security.auth.callback.Callback;
 import javax.security.auth.callback.CallbackHandler;
@@ -37,6 +39,7 @@ public class JAASSecurityAuthenticator implements 
SecurityAuthenticator {
 
     private static final Logger LOG = 
LoggerFactory.getLogger(JAASSecurityAuthenticator.class);
     private String name;
+    private String roleClassNames;
 
     public void setName(String name) {
         this.name = name;
@@ -46,17 +49,28 @@ public class JAASSecurityAuthenticator implements 
SecurityAuthenticator {
         return name;
     }
 
+    public void setRoleClassNames(String roleClassNames) {
+        this.roleClassNames = roleClassNames;
+    }
+
     @Override
     public Subject login(HttpPrincipal principal) throws LoginException {
         if (ObjectHelper.isEmpty(getName())) {
             throw new IllegalArgumentException("Realm has not been configured 
on this SecurityAuthenticator: " + this);
         }
 
-        LOG.debug("Login username: {} using realm: {}", principal.getName(), 
getName());
+        LOG.trace("Login username: {} using realm: {}", principal.getName(), 
getName());
         LoginContext context = new LoginContext(getName(), new 
HttpPrincipalCallbackHandler(principal));
         context.login();
         Subject subject = context.getSubject();
         LOG.debug("Login username: {} successful returning Subject: {}", 
principal.getName(), subject);
+
+        if (LOG.isTraceEnabled()) {
+            for (Principal p : subject.getPrincipals()) {
+                LOG.trace("Principal on subject {} -> {}", 
p.getClass().getName(), p.getName());
+            }
+        }
+
         return subject;
     }
 
@@ -70,12 +84,33 @@ public class JAASSecurityAuthenticator implements 
SecurityAuthenticator {
         if (!subject.getPrincipals().isEmpty()) {
             username = subject.getPrincipals().iterator().next().getName();
         }
-        LOG.debug("Logging out username: {} using realm: {}", username, 
getName());
+        LOG.trace("Logging out username: {} using realm: {}", username, 
getName());
         LoginContext context = new LoginContext(getName(), subject);
         context.logout();
         LOG.debug("Logout username: {} successful", username);
     }
 
+    @Override
+    public String getUserRoles(Subject subject) {
+        StringBuilder sb = new StringBuilder();
+        for (Principal p : subject.getPrincipals()) {
+            if (roleClassNames == null) {
+                // by default assume its a role when the classname has role in 
its name
+                if (p.getName().toLowerCase(Locale.US).contains("role")) {
+                    if (sb.length() > 0) {
+                        sb.append(",");
+                    }
+                    sb.append(p.getName());
+                }
+            }
+        }
+        if (sb.length() > 0) {
+            return sb.toString();
+        } else {
+            return null;
+        }
+    }
+
     /**
      * {@link CallbackHandler} that provides the username and password.
      */

http://git-wip-us.apache.org/repos/asf/camel/blob/8042c338/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpEndpoint.java
----------------------------------------------------------------------
diff --git 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpEndpoint.java
 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpEndpoint.java
index b97f12c..5e5de9d 100644
--- 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpEndpoint.java
+++ 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpEndpoint.java
@@ -189,7 +189,7 @@ public class NettyHttpEndpoint extends NettyEndpoint 
implements HeaderFilterStra
 
         if (securityConfiguration != null) {
             ObjectHelper.notEmpty(securityConfiguration.getRealm(), "realm", 
securityConfiguration);
-            ObjectHelper.notEmpty(securityConfiguration.getConstraint(), 
"constraint", securityConfiguration);
+            ObjectHelper.notEmpty(securityConfiguration.getConstraint(), 
"restricted", securityConfiguration);
 
             if (securityConfiguration.getSecurityAuthenticator() == null) {
                 // setup default JAAS authenticator if none was configured

http://git-wip-us.apache.org/repos/asf/camel/blob/8042c338/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpSecurityConfiguration.java
----------------------------------------------------------------------
diff --git 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpSecurityConfiguration.java
 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpSecurityConfiguration.java
index ecc650f..65becd4 100644
--- 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpSecurityConfiguration.java
+++ 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpSecurityConfiguration.java
@@ -26,9 +26,10 @@ public class NettyHttpSecurityConfiguration {
     private boolean authenticate = true;
     private String constraint = "Basic";
     private String realm;
-    private ContextPathMatcher constraintMapping;
+    private SecurityConstraint securityConstraint;
     private SecurityAuthenticator securityAuthenticator;
     private LoggingLevel loginDeniedLoggingLevel = LoggingLevel.DEBUG;
+    private String roleClassName;
 
     public boolean isAuthenticate() {
         return authenticate;
@@ -48,7 +49,7 @@ public class NettyHttpSecurityConfiguration {
     }
 
     /**
-     * The supported constraint.
+     * The supported restricted.
      * <p/>
      * Currently only Basic is supported.
      */
@@ -67,17 +68,17 @@ public class NettyHttpSecurityConfiguration {
         this.realm = realm;
     }
 
-    public ContextPathMatcher getConstraintMapping() {
-        return constraintMapping;
+    public SecurityConstraint getSecurityConstraint() {
+        return securityConstraint;
     }
 
     /**
-     * Sets a {@link ContextPathMatcher} to use for matching if a url is 
restricted or not.
+     * Sets a {@link SecurityConstraint} to use for checking if a web resource 
is restricted or not
      * <p/>
      * By default this is <tt>null</tt>, which means all resources is 
restricted.
      */
-    public void setConstraintMapping(ContextPathMatcher constraintMapping) {
-        this.constraintMapping = constraintMapping;
+    public void setSecurityConstraint(SecurityConstraint securityConstraint) {
+        this.securityConstraint = securityConstraint;
     }
 
     public SecurityAuthenticator getSecurityAuthenticator() {
@@ -103,4 +104,12 @@ public class NettyHttpSecurityConfiguration {
     public void setLoginDeniedLoggingLevel(LoggingLevel 
loginDeniedLoggingLevel) {
         this.loginDeniedLoggingLevel = loginDeniedLoggingLevel;
     }
+
+    public String getRoleClassName() {
+        return roleClassName;
+    }
+
+    public void setRoleClassName(String roleClassName) {
+        this.roleClassName = roleClassName;
+    }
 }

http://git-wip-us.apache.org/repos/asf/camel/blob/8042c338/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/SecurityAuthenticator.java
----------------------------------------------------------------------
diff --git 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/SecurityAuthenticator.java
 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/SecurityAuthenticator.java
index 1d903f6..e1be404 100644
--- 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/SecurityAuthenticator.java
+++ 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/SecurityAuthenticator.java
@@ -35,6 +35,8 @@ public interface SecurityAuthenticator {
      */
     String getName();
 
+    void setRoleClassNames(String names);
+
     /**
      * Attempts to login the {@link java.security.Principal} on this realm.
      * <p/>
@@ -54,4 +56,12 @@ public interface SecurityAuthenticator {
      */
     void logout(Subject subject) throws LoginException;
 
+    /**
+     * Gets the user roles from the given {@link Subject}
+     *
+     * @param subject the subject
+     * @return <tt>null</tt> if no roles, otherwise a String with roles 
separated by comma.
+     */
+    String getUserRoles(Subject subject);
+
 }

http://git-wip-us.apache.org/repos/asf/camel/blob/8042c338/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/SecurityConstraint.java
----------------------------------------------------------------------
diff --git 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/SecurityConstraint.java
 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/SecurityConstraint.java
new file mode 100644
index 0000000..2e3db94
--- /dev/null
+++ 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/SecurityConstraint.java
@@ -0,0 +1,31 @@
+/**
+ * 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.camel.component.netty.http;
+
+public interface SecurityConstraint {
+
+    /**
+     * Performs a security restricted check for the given web resource.
+     * <p/>
+     * The returned value indicates which roles the user must be in to access 
the restricted resource.
+     *
+     * @param url   the web resource
+     * @return <tt>null</tt> if not restricted, otherwise <tt>*</tt> 
(wildcard) matches any roles, otherwise a comma separated String with roles
+     */
+    String restricted(String url);
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/8042c338/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/handlers/HttpServerChannelHandler.java
----------------------------------------------------------------------
diff --git 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/handlers/HttpServerChannelHandler.java
 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/handlers/HttpServerChannelHandler.java
index 4ddaf83..c2e3731 100644
--- 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/handlers/HttpServerChannelHandler.java
+++ 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/handlers/HttpServerChannelHandler.java
@@ -20,6 +20,7 @@ import java.net.SocketAddress;
 import java.net.URI;
 import java.nio.channels.ClosedChannelException;
 import java.nio.charset.Charset;
+import java.util.Iterator;
 import javax.security.auth.Subject;
 import javax.security.auth.login.LoginException;
 
@@ -128,17 +129,36 @@ public class HttpServerChannelHandler extends 
ServerChannelHandler {
             String target = uri.getPath();
 
             // is it a restricted resource?
-            boolean restricted = security.getConstraintMapping() == null || 
security.getConstraintMapping().matches(target);
-            if (restricted) {
+            String roles;
+            if (security.getSecurityConstraint() != null) {
+                // if restricted returns null, then the resource is not 
restricted and we should not authenticate the user
+                roles = security.getSecurityConstraint().restricted(target);
+            } else {
+                // assume any roles is valid if no security constraint has 
been configured
+                roles = "*";
+            }
+            if (roles != null) {
                 // basic auth subject
                 HttpPrincipal principal = extractBasicAuthSubject(request);
-                boolean authenticated = principal != null
-                        && authenticate(security.getSecurityAuthenticator(), 
security.getLoginDeniedLoggingLevel(), principal) != null;
-                if (principal == null || !authenticated) {
+
+                // authenticate principal and check if the user is in role
+                Subject subject = null;
+                boolean inRole = true;
+                if (principal != null) {
+                    subject = 
authenticate(security.getSecurityAuthenticator(), 
security.getLoginDeniedLoggingLevel(), principal);
+                    if (subject != null) {
+                        String userRoles = 
security.getSecurityAuthenticator().getUserRoles(subject);
+                        inRole = matchesRoles(roles, userRoles);
+                    }
+                }
+
+                if (principal == null || subject == null || !inRole) {
                     if (principal == null) {
                         LOG.debug("Http Basic Auth required for resource: {}", 
url);
-                    } else {
+                    } else if (subject == null) {
                         LOG.debug("Http Basic Auth not authorized for 
username: {}", principal.getUsername());
+                    } else {
+                        LOG.debug("Http Basic Auth not in role for username: 
{}", principal.getUsername());
                     }
                     // restricted resource, so send back 401 to require valid 
username/password
                     HttpResponse response = new DefaultHttpResponse(HTTP_1_1, 
UNAUTHORIZED);
@@ -158,6 +178,24 @@ public class HttpServerChannelHandler extends 
ServerChannelHandler {
         super.messageReceived(ctx, messageEvent);
     }
 
+    protected boolean matchesRoles(String roles, String userRoles) {
+        // matches if no role restrictions or any role is accepted
+        if (roles.equals("*")) {
+            return true;
+        }
+
+        // see if any of the user roles is contained in the roles list
+        Iterator it = ObjectHelper.createIterator(userRoles);
+        while (it.hasNext()) {
+            String userRole = it.next().toString();
+            if (roles.contains(userRole)) {
+                return true;
+            }
+        }
+
+        return false;
+    }
+
     /**
      * Extracts the username and password details from the HTTP basic header 
Authorization.
      * <p/>

http://git-wip-us.apache.org/repos/asf/camel/blob/8042c338/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/ConstraintMappingContextPathMatcherTest.java
----------------------------------------------------------------------
diff --git 
a/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/ConstraintMappingContextPathMatcherTest.java
 
b/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/ConstraintMappingContextPathMatcherTest.java
deleted file mode 100644
index 6914c8c..0000000
--- 
a/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/ConstraintMappingContextPathMatcherTest.java
+++ /dev/null
@@ -1,108 +0,0 @@
-/**
- * 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.camel.component.netty.http;
-
-import junit.framework.TestCase;
-
-public class ConstraintMappingContextPathMatcherTest extends TestCase {
-
-    public void testDefault() {
-        ConstraintMappingContextPathMatcher matcher = new 
ConstraintMappingContextPathMatcher();
-
-        assertTrue(matcher.matches("/"));
-        assertTrue(matcher.matches("/foo"));
-    }
-
-    public void testFoo() {
-        ConstraintMappingContextPathMatcher matcher = new 
ConstraintMappingContextPathMatcher();
-        matcher.addInclusion("/foo");
-
-        assertFalse(matcher.matches("/"));
-        assertTrue(matcher.matches("/foo"));
-        assertFalse(matcher.matches("/foobar"));
-        assertFalse(matcher.matches("/foo/bar"));
-    }
-
-    public void testFooWildcard() {
-        ConstraintMappingContextPathMatcher matcher = new 
ConstraintMappingContextPathMatcher();
-        matcher.addInclusion("/foo*");
-
-        assertFalse(matcher.matches("/"));
-        assertTrue(matcher.matches("/foo"));
-        assertTrue(matcher.matches("/foobar"));
-        assertTrue(matcher.matches("/foo/bar"));
-    }
-
-    public void testFooBar() {
-        ConstraintMappingContextPathMatcher matcher = new 
ConstraintMappingContextPathMatcher();
-        matcher.addInclusion("/foo");
-        matcher.addInclusion("/bar");
-
-        assertFalse(matcher.matches("/"));
-        assertTrue(matcher.matches("/foo"));
-        assertFalse(matcher.matches("/foobar"));
-        assertFalse(matcher.matches("/foo/bar"));
-
-        assertTrue(matcher.matches("/bar"));
-        assertFalse(matcher.matches("/barbar"));
-        assertFalse(matcher.matches("/bar/bar"));
-    }
-
-    public void testFooBarWildcard() {
-        ConstraintMappingContextPathMatcher matcher = new 
ConstraintMappingContextPathMatcher();
-        matcher.addInclusion("/foo*");
-        matcher.addInclusion("/bar*");
-
-        assertFalse(matcher.matches("/"));
-        assertTrue(matcher.matches("/foo"));
-        assertTrue(matcher.matches("/foobar"));
-        assertTrue(matcher.matches("/foo/bar"));
-
-        assertTrue(matcher.matches("/bar"));
-        assertTrue(matcher.matches("/barbar"));
-        assertTrue(matcher.matches("/bar/bar"));
-    }
-
-    public void testFooExclusion() {
-        ConstraintMappingContextPathMatcher matcher = new 
ConstraintMappingContextPathMatcher();
-        matcher.addInclusion("/foo/*");
-        matcher.addExclusion("/foo/public/*");
-
-        assertFalse(matcher.matches("/"));
-        assertTrue(matcher.matches("/foo"));
-        assertTrue(matcher.matches("/foo/bar"));
-        assertFalse(matcher.matches("/foo/public"));
-        assertFalse(matcher.matches("/foo/public/open"));
-    }
-
-    public void testDefaultExclusion() {
-        // everything is restricted unless its from the public
-        ConstraintMappingContextPathMatcher matcher = new 
ConstraintMappingContextPathMatcher();
-        matcher.addExclusion("/public/*");
-        matcher.addExclusion("/index");
-        matcher.addExclusion("/index.html");
-
-        assertTrue(matcher.matches("/"));
-        assertTrue(matcher.matches("/foo"));
-        assertTrue(matcher.matches("/foo/bar"));
-        assertFalse(matcher.matches("/public"));
-        assertFalse(matcher.matches("/public/open"));
-        assertFalse(matcher.matches("/index"));
-        assertFalse(matcher.matches("/index.html"));
-    }
-
-}

http://git-wip-us.apache.org/repos/asf/camel/blob/8042c338/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/DefaultSecurityConstraintTest.java
----------------------------------------------------------------------
diff --git 
a/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/DefaultSecurityConstraintTest.java
 
b/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/DefaultSecurityConstraintTest.java
new file mode 100644
index 0000000..16790f7
--- /dev/null
+++ 
b/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/DefaultSecurityConstraintTest.java
@@ -0,0 +1,108 @@
+/**
+ * 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.camel.component.netty.http;
+
+import junit.framework.TestCase;
+
+public class DefaultSecurityConstraintTest extends TestCase {
+
+    public void testDefault() {
+        DefaultSecurityConstraint matcher = new DefaultSecurityConstraint();
+
+        assertNotNull(matcher.restricted("/"));
+        assertNotNull(matcher.restricted("/foo"));
+    }
+
+    public void testFoo() {
+        DefaultSecurityConstraint matcher = new DefaultSecurityConstraint();
+        matcher.addInclusion("/foo");
+
+        assertNull(matcher.restricted("/"));
+        assertNotNull(matcher.restricted("/foo"));
+        assertNull(matcher.restricted("/foobar"));
+        assertNull(matcher.restricted("/foo/bar"));
+    }
+
+    public void testFooWildcard() {
+        DefaultSecurityConstraint matcher = new DefaultSecurityConstraint();
+        matcher.addInclusion("/foo*");
+
+        assertNull(matcher.restricted("/"));
+        assertNotNull(matcher.restricted("/foo"));
+        assertNotNull(matcher.restricted("/foobar"));
+        assertNotNull(matcher.restricted("/foo/bar"));
+    }
+
+    public void testFooBar() {
+        DefaultSecurityConstraint matcher = new DefaultSecurityConstraint();
+        matcher.addInclusion("/foo");
+        matcher.addInclusion("/bar");
+
+        assertNull(matcher.restricted("/"));
+        assertNotNull(matcher.restricted("/foo"));
+        assertNull(matcher.restricted("/foobar"));
+        assertNull(matcher.restricted("/foo/bar"));
+
+        assertNotNull(matcher.restricted("/bar"));
+        assertNull(matcher.restricted("/barbar"));
+        assertNull(matcher.restricted("/bar/bar"));
+    }
+
+    public void testFooBarWildcard() {
+        DefaultSecurityConstraint matcher = new DefaultSecurityConstraint();
+        matcher.addInclusion("/foo*");
+        matcher.addInclusion("/bar*");
+
+        assertNull(matcher.restricted("/"));
+        assertNotNull(matcher.restricted("/foo"));
+        assertNotNull(matcher.restricted("/foobar"));
+        assertNotNull(matcher.restricted("/foo/bar"));
+
+        assertNotNull(matcher.restricted("/bar"));
+        assertNotNull(matcher.restricted("/barbar"));
+        assertNotNull(matcher.restricted("/bar/bar"));
+    }
+
+    public void testFooExclusion() {
+        DefaultSecurityConstraint matcher = new DefaultSecurityConstraint();
+        matcher.addInclusion("/foo/*");
+        matcher.addExclusion("/foo/public/*");
+
+        assertNull(matcher.restricted("/"));
+        assertNotNull(matcher.restricted("/foo"));
+        assertNotNull(matcher.restricted("/foo/bar"));
+        assertNull(matcher.restricted("/foo/public"));
+        assertNull(matcher.restricted("/foo/public/open"));
+    }
+
+    public void testDefaultExclusion() {
+        // everything is restricted unless its from the public
+        DefaultSecurityConstraint matcher = new DefaultSecurityConstraint();
+        matcher.addExclusion("/public/*");
+        matcher.addExclusion("/index");
+        matcher.addExclusion("/index.html");
+
+        assertNotNull(matcher.restricted("/"));
+        assertNotNull(matcher.restricted("/foo"));
+        assertNotNull(matcher.restricted("/foo/bar"));
+        assertNull(matcher.restricted("/public"));
+        assertNull(matcher.restricted("/public/open"));
+        assertNull(matcher.restricted("/index"));
+        assertNull(matcher.restricted("/index.html"));
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/8042c338/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpBasicAuthConstraintMapperTest.java
----------------------------------------------------------------------
diff --git 
a/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpBasicAuthConstraintMapperTest.java
 
b/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpBasicAuthConstraintMapperTest.java
index 3724db7..890be6c 100644
--- 
a/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpBasicAuthConstraintMapperTest.java
+++ 
b/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpBasicAuthConstraintMapperTest.java
@@ -45,10 +45,10 @@ public class NettyHttpBasicAuthConstraintMapperTest extends 
BaseNettyTest {
         auth.setName("karaf");
         security.setSecurityAuthenticator(auth);
 
-        ConstraintMappingContextPathMatcher matcher = new 
ConstraintMappingContextPathMatcher();
+        DefaultSecurityConstraint matcher = new DefaultSecurityConstraint();
         matcher.addInclusion("/foo/*");
         matcher.addExclusion("/foo/public/*");
-        security.setConstraintMapping(matcher);
+        security.setSecurityConstraint(matcher);
 
         jndi.bind("mySecurityConfig", security);
 

http://git-wip-us.apache.org/repos/asf/camel/blob/8042c338/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpBasicAuthCustomSecurityAuthenticatorTest.java
----------------------------------------------------------------------
diff --git 
a/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpBasicAuthCustomSecurityAuthenticatorTest.java
 
b/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpBasicAuthCustomSecurityAuthenticatorTest.java
index aa9a795..e52ccc4 100644
--- 
a/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpBasicAuthCustomSecurityAuthenticatorTest.java
+++ 
b/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpBasicAuthCustomSecurityAuthenticatorTest.java
@@ -76,6 +76,11 @@ public class 
NettyHttpBasicAuthCustomSecurityAuthenticatorTest extends BaseNetty
         }
 
         @Override
+        public void setRoleClassNames(String names) {
+            // noop
+        }
+
+        @Override
         public Subject login(HttpPrincipal principal) throws LoginException {
             if (!principal.getPassword().equalsIgnoreCase("secret")) {
                 throw new LoginException("Login denied");
@@ -88,6 +93,11 @@ public class 
NettyHttpBasicAuthCustomSecurityAuthenticatorTest extends BaseNetty
         public void logout(Subject subject) throws LoginException {
             // noop
         }
+
+        @Override
+        public String getUserRoles(Subject subject) {
+            return null;
+        }
     }
 
 }

http://git-wip-us.apache.org/repos/asf/camel/blob/8042c338/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpSimpleBasicAuthConstraintMapperTest.java
----------------------------------------------------------------------
diff --git 
a/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpSimpleBasicAuthConstraintMapperTest.java
 
b/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpSimpleBasicAuthConstraintMapperTest.java
index 9ecfc72..c68ba0d 100644
--- 
a/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpSimpleBasicAuthConstraintMapperTest.java
+++ 
b/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpSimpleBasicAuthConstraintMapperTest.java
@@ -39,7 +39,7 @@ public class NettyHttpSimpleBasicAuthConstraintMapperTest 
extends BaseNettyTest
     protected JndiRegistry createRegistry() throws Exception {
         JndiRegistry jndi = super.createRegistry();
 
-        ConstraintMappingContextPathMatcher matcher = new 
ConstraintMappingContextPathMatcher();
+        DefaultSecurityConstraint matcher = new DefaultSecurityConstraint();
         matcher.addInclusion("/foo/*");
         matcher.addExclusion("/foo/public/*");
 
@@ -78,7 +78,7 @@ public class NettyHttpSimpleBasicAuthConstraintMapperTest 
extends BaseNettyTest
             @Override
             public void configure() throws Exception {
                 
from("netty-http:http://0.0.0.0:{{port}}/foo?matchOnUriPrefix=true";
-                        + 
"&securityConfiguration.realm=karaf&securityConfiguration.constraintMapping=#myConstraint")
+                        + 
"&securityConfiguration.realm=karaf&securityConfiguration.securityConstraint=#myConstraint")
                     .to("mock:input")
                     .transform().constant("Bye World");
             }

Reply via email to