summaryrefslogtreecommitdiff
path: root/qpid/java/broker/src/main
diff options
context:
space:
mode:
authorKeith Wall <kwall@apache.org>2012-09-10 15:37:45 +0000
committerKeith Wall <kwall@apache.org>2012-09-10 15:37:45 +0000
commitb0a4911fa51737570a1e9767f7fd37f50f06b3bd (patch)
treed3183ccd29662cd13926e529aa3f3d0f6db24ef3 /qpid/java/broker/src/main
parent3957c7f5aab759d2a9b2f10b38c116f0472b32fa (diff)
downloadqpid-python-b0a4911fa51737570a1e9767f7fd37f50f06b3bd.tar.gz
QPID-4292: add ACL rule to authorise access to the web management UI
* added object name MANAGEMENT to represent both JMX and Web Management layers * Change both JMX/Web entry points to permission access with an access management check * Updated examples and docbook * Made Principals serialised to avoid container warnings when Qpid principals are placed within a HttpSession. Work of Robbie Gemmell <robbie@apache.org> and myself. git-svn-id: https://svn.apache.org/repos/asf/qpid/trunk@1382947 13f79535-47bb-0310-9956-ffa450edef68
Diffstat (limited to 'qpid/java/broker/src/main')
-rwxr-xr-xqpid/java/broker/src/main/java/org/apache/qpid/server/security/SecurityManager.java12
-rw-r--r--qpid/java/broker/src/main/java/org/apache/qpid/server/security/access/ObjectType.java1
-rw-r--r--qpid/java/broker/src/main/java/org/apache/qpid/server/security/auth/AuthenticatedPrincipal.java3
-rw-r--r--qpid/java/broker/src/main/java/org/apache/qpid/server/security/auth/UsernamePrincipal.java3
-rw-r--r--qpid/java/broker/src/main/java/org/apache/qpid/server/security/auth/rmi/RMIPasswordAuthenticator.java76
-rw-r--r--qpid/java/broker/src/main/java/org/apache/qpid/server/security/group/GroupPrincipal.java3
6 files changed, 64 insertions, 34 deletions
diff --git a/qpid/java/broker/src/main/java/org/apache/qpid/server/security/SecurityManager.java b/qpid/java/broker/src/main/java/org/apache/qpid/server/security/SecurityManager.java
index ce0ea2faea..1e377be1d2 100755
--- a/qpid/java/broker/src/main/java/org/apache/qpid/server/security/SecurityManager.java
+++ b/qpid/java/broker/src/main/java/org/apache/qpid/server/security/SecurityManager.java
@@ -29,6 +29,7 @@ import org.apache.qpid.server.exchange.Exchange;
import org.apache.qpid.server.plugins.PluginManager;
import org.apache.qpid.server.queue.AMQQueue;
import org.apache.qpid.server.security.access.ObjectProperties;
+import org.apache.qpid.server.security.access.ObjectType;
import org.apache.qpid.server.security.access.Operation;
import static org.apache.qpid.server.security.access.ObjectType.EXCHANGE;
@@ -359,6 +360,17 @@ public class SecurityManager
});
}
+ public boolean accessManagement()
+ {
+ return checkAllPlugins(new AccessCheck()
+ {
+ Result allowed(SecurityPlugin plugin)
+ {
+ return plugin.access(ObjectType.MANAGEMENT, null);
+ }
+ });
+ }
+
public boolean accessVirtualhost(final String vhostname, final SocketAddress remoteAddress)
{
return checkAllPlugins(new AccessCheck()
diff --git a/qpid/java/broker/src/main/java/org/apache/qpid/server/security/access/ObjectType.java b/qpid/java/broker/src/main/java/org/apache/qpid/server/security/access/ObjectType.java
index 043d4909d5..8bc4b9d278 100644
--- a/qpid/java/broker/src/main/java/org/apache/qpid/server/security/access/ObjectType.java
+++ b/qpid/java/broker/src/main/java/org/apache/qpid/server/security/access/ObjectType.java
@@ -41,6 +41,7 @@ public enum ObjectType
{
ALL(Operation.ALL),
VIRTUALHOST(Operation.ALL, ACCESS),
+ MANAGEMENT(Operation.ALL, ACCESS),
QUEUE(Operation.ALL, CREATE, DELETE, PURGE, CONSUME),
EXCHANGE(Operation.ALL, ACCESS, CREATE, DELETE, BIND, UNBIND, PUBLISH),
LINK, // Not allowed in the Java broker
diff --git a/qpid/java/broker/src/main/java/org/apache/qpid/server/security/auth/AuthenticatedPrincipal.java b/qpid/java/broker/src/main/java/org/apache/qpid/server/security/auth/AuthenticatedPrincipal.java
index 96360e83e4..fb31132514 100644
--- a/qpid/java/broker/src/main/java/org/apache/qpid/server/security/auth/AuthenticatedPrincipal.java
+++ b/qpid/java/broker/src/main/java/org/apache/qpid/server/security/auth/AuthenticatedPrincipal.java
@@ -18,6 +18,7 @@
*/
package org.apache.qpid.server.security.auth;
+import java.io.Serializable;
import java.security.Principal;
import java.util.Set;
@@ -30,7 +31,7 @@ import org.apache.qpid.server.security.auth.UsernamePrincipal;
* by calling {@link Subject#getPrincipals(Class)}, passing in {@link AuthenticatedPrincipal}.class,
* e.g. when logging.
*/
-public final class AuthenticatedPrincipal implements Principal
+public final class AuthenticatedPrincipal implements Principal, Serializable
{
private final Principal _wrappedPrincipal;
diff --git a/qpid/java/broker/src/main/java/org/apache/qpid/server/security/auth/UsernamePrincipal.java b/qpid/java/broker/src/main/java/org/apache/qpid/server/security/auth/UsernamePrincipal.java
index cc414f801a..5b3c1d59cf 100644
--- a/qpid/java/broker/src/main/java/org/apache/qpid/server/security/auth/UsernamePrincipal.java
+++ b/qpid/java/broker/src/main/java/org/apache/qpid/server/security/auth/UsernamePrincipal.java
@@ -20,10 +20,11 @@
*/
package org.apache.qpid.server.security.auth;
+import java.io.Serializable;
import java.security.Principal;
/** A principal that is just a wrapper for a simple username. */
-public class UsernamePrincipal implements Principal
+public class UsernamePrincipal implements Principal, Serializable
{
private final String _name;
diff --git a/qpid/java/broker/src/main/java/org/apache/qpid/server/security/auth/rmi/RMIPasswordAuthenticator.java b/qpid/java/broker/src/main/java/org/apache/qpid/server/security/auth/rmi/RMIPasswordAuthenticator.java
index 808447b7ff..9f5d87bf62 100644
--- a/qpid/java/broker/src/main/java/org/apache/qpid/server/security/auth/rmi/RMIPasswordAuthenticator.java
+++ b/qpid/java/broker/src/main/java/org/apache/qpid/server/security/auth/rmi/RMIPasswordAuthenticator.java
@@ -22,7 +22,8 @@ package org.apache.qpid.server.security.auth.rmi;
import java.net.SocketAddress;
-import org.apache.qpid.server.registry.ApplicationRegistry;
+import org.apache.qpid.server.registry.IApplicationRegistry;
+import org.apache.qpid.server.security.SecurityManager;
import org.apache.qpid.server.security.SubjectCreator;
import org.apache.qpid.server.security.auth.AuthenticationResult.AuthenticationStatus;
import org.apache.qpid.server.security.auth.SubjectAuthenticationResult;
@@ -37,23 +38,33 @@ public class RMIPasswordAuthenticator implements JMXAuthenticator
static final String SHOULD_HAVE_2_ELEMENTS = "User details should have 2 elements, username, password";
static final String SHOULD_BE_NON_NULL = "Supplied username and password should be non-null";
static final String INVALID_CREDENTIALS = "Invalid user details supplied";
+ static final String USER_NOT_AUTHORISED_FOR_MANAGEMENT = "User not authorised for management";
static final String CREDENTIALS_REQUIRED = "User details are required. " +
- "Please ensure you are using an up to date management console to connect.";
+ "Please ensure you are using an up to date management console to connect.";
- private SubjectCreator _subjectCreator = null;
- private SocketAddress _socketAddress;
+ private final IApplicationRegistry _appRegistry;
+ private final SocketAddress _socketAddress;
- public RMIPasswordAuthenticator(SocketAddress socketAddress)
+ public RMIPasswordAuthenticator(IApplicationRegistry appRegistry, SocketAddress socketAddress)
{
+ _appRegistry = appRegistry;
_socketAddress = socketAddress;
}
- public void setSubjectCreator(final SubjectCreator subjectCreator)
+ public Subject authenticate(Object credentials) throws SecurityException
{
- _subjectCreator = subjectCreator;
+ validateCredentials(credentials);
+
+ final String[] userCredentials = (String[]) credentials;
+ final String username = (String) userCredentials[0];
+ final String password = (String) userCredentials[1];
+
+ final Subject authenticatedSubject = doAuthentication(username, password);
+ doManagementAuthorisation(authenticatedSubject);
+ return authenticatedSubject;
}
- public Subject authenticate(Object credentials) throws SecurityException
+ private void validateCredentials(Object credentials)
{
// Verify that credential's are of type String[].
if (!(credentials instanceof String[]))
@@ -69,41 +80,27 @@ public class RMIPasswordAuthenticator implements JMXAuthenticator
}
// Verify that required number of credentials.
- final String[] userCredentials = (String[]) credentials;
- if (userCredentials.length != 2)
+ if (((String[])credentials).length != 2)
{
throw new SecurityException(SHOULD_HAVE_2_ELEMENTS);
}
+ }
- final String username = (String) userCredentials[0];
- final String password = (String) userCredentials[1];
-
+ private Subject doAuthentication(final String username, final String password)
+ {
// Verify that all required credentials are actually present.
if (username == null || password == null)
{
throw new SecurityException(SHOULD_BE_NON_NULL);
}
- // Verify that an SubjectCreator has been set.
- if (_subjectCreator == null)
+ SubjectCreator subjectCreator = _appRegistry.getSubjectCreator(_socketAddress);
+ if (subjectCreator == null)
{
- try
- {
- if(ApplicationRegistry.getInstance().getSubjectCreator(_socketAddress) != null)
- {
- _subjectCreator = ApplicationRegistry.getInstance().getSubjectCreator(_socketAddress);
- }
- else
- {
- throw new SecurityException(UNABLE_TO_LOOKUP);
- }
- }
- catch(IllegalStateException e)
- {
- throw new SecurityException(UNABLE_TO_LOOKUP);
- }
+ throw new SecurityException("Can't get subject creator for " + _socketAddress);
}
- final SubjectAuthenticationResult result = _subjectCreator.authenticate(username, password);
+
+ final SubjectAuthenticationResult result = subjectCreator.authenticate(username, password);
if (AuthenticationStatus.ERROR.equals(result.getStatus()))
{
@@ -119,4 +116,21 @@ public class RMIPasswordAuthenticator implements JMXAuthenticator
}
}
+ private void doManagementAuthorisation(Subject authenticatedSubject)
+ {
+ SecurityManager.setThreadSubject(authenticatedSubject);
+ try
+ {
+ if (!_appRegistry.getSecurityManager().accessManagement())
+ {
+ throw new SecurityException(USER_NOT_AUTHORISED_FOR_MANAGEMENT);
+ }
+ }
+ finally
+ {
+ SecurityManager.setThreadSubject(null);
+ }
+ }
+
+
} \ No newline at end of file
diff --git a/qpid/java/broker/src/main/java/org/apache/qpid/server/security/group/GroupPrincipal.java b/qpid/java/broker/src/main/java/org/apache/qpid/server/security/group/GroupPrincipal.java
index ccb446b719..a9590bb964 100644
--- a/qpid/java/broker/src/main/java/org/apache/qpid/server/security/group/GroupPrincipal.java
+++ b/qpid/java/broker/src/main/java/org/apache/qpid/server/security/group/GroupPrincipal.java
@@ -20,6 +20,7 @@
*/
package org.apache.qpid.server.security.group;
+import java.io.Serializable;
import java.security.Principal;
import java.security.acl.Group;
import java.util.Enumeration;
@@ -30,7 +31,7 @@ import java.util.Enumeration;
* methods etc throw {@link UnsupportedOperationException}.
*
*/
-public class GroupPrincipal implements Group
+public class GroupPrincipal implements Group, Serializable
{
/** Name of the group */
private final String _groupName;