|
29 | 29 |
|
30 | 30 | import com.github.benmanes.caffeine.cache.Cache; |
31 | 31 | import com.github.benmanes.caffeine.cache.Caffeine; |
| 32 | +import org.apache.activemq.artemis.api.core.ActiveMQSecurityException; |
32 | 33 | import org.apache.activemq.artemis.api.core.Pair; |
33 | 34 | import org.apache.activemq.artemis.api.core.SimpleString; |
34 | 35 | import org.apache.activemq.artemis.api.core.management.CoreNotificationType; |
|
63 | 64 | import org.slf4j.Logger; |
64 | 65 | import org.slf4j.LoggerFactory; |
65 | 66 |
|
| 67 | +import static org.apache.activemq.artemis.api.config.ActiveMQDefaultConfiguration.getDefaultClusterPassword; |
| 68 | +import static org.apache.activemq.artemis.api.config.ActiveMQDefaultConfiguration.getDefaultClusterUser; |
66 | 69 | import static org.apache.activemq.artemis.utils.CertificateUtil.CERT_SUBJECT_DN_UNAVAILABLE; |
67 | 70 |
|
68 | 71 | /** |
@@ -113,7 +116,7 @@ public SecurityStoreImpl(final HierarchicalRepository<Set<Role>> securityReposit |
113 | 116 | final String managementClusterPassword, |
114 | 117 | final NotificationService notificationService, |
115 | 118 | final long authenticationCacheSize, |
116 | | - final long authorizationCacheSize) throws NoSuchAlgorithmException { |
| 119 | + final long authorizationCacheSize) { |
117 | 120 | this.securityRepository = securityRepository; |
118 | 121 | this.securityManager = securityManager; |
119 | 122 | this.securityEnabled = securityEnabled; |
@@ -178,24 +181,10 @@ public String authenticate(final String user, |
178 | 181 | RemotingConnection connection, |
179 | 182 | String securityDomain) throws Exception { |
180 | 183 | if (securityEnabled) { |
181 | | - |
182 | | - if (managementClusterUser.equals(user)) { |
183 | | - logger.trace("Authenticating cluster admin user"); |
184 | | - |
185 | | - /* |
186 | | - * The special user cluster user is used for creating sessions that replicate management |
187 | | - * operation between nodes |
188 | | - */ |
189 | | - if (!managementClusterPassword.equals(password)) { |
190 | | - AUTHENTICATION_FAILURE_COUNT_UPDATER.incrementAndGet(this); |
191 | | - throw ActiveMQMessageBundle.BUNDLE.unableToValidateClusterUser(user); |
192 | | - } else { |
193 | | - AUTHENTICATION_SUCCESS_COUNT_UPDATER.incrementAndGet(this); |
194 | | - return managementClusterUser; |
195 | | - } |
| 184 | + String validatedUser = handleClusterAuthentication(user, password, connection); |
| 185 | + if (validatedUser != null) { |
| 186 | + return validatedUser; |
196 | 187 | } |
197 | | - |
198 | | - String validatedUser = null; |
199 | 188 | boolean userIsValid = false; |
200 | 189 | boolean check = true; |
201 | 190 |
|
@@ -305,10 +294,12 @@ public boolean hasPermission(final SimpleString address, |
305 | 294 | return true; |
306 | 295 | } |
307 | 296 |
|
308 | | - // bypass permission checks for management cluster user |
309 | 297 | String user = session.getUsername(); |
310 | | - if (managementClusterUser.equals(user) && session.getPassword().equals(managementClusterPassword)) { |
| 298 | + ClusterCredentialsCheckResult checkResult = checkClusterCredentials(user, session.getPassword()); |
| 299 | + if (checkResult == ClusterCredentialsCheckResult.VALID) { |
311 | 300 | return true; |
| 301 | + } else if (checkResult == ClusterCredentialsCheckResult.INVALID) { |
| 302 | + return false; |
312 | 303 | } |
313 | 304 |
|
314 | 305 | // Special case: detect authentication failure for ActiveMQSecurityManager5 |
@@ -384,6 +375,38 @@ public boolean hasPermission(final SimpleString address, |
384 | 375 | } |
385 | 376 | } |
386 | 377 |
|
| 378 | + private String handleClusterAuthentication(String user, String password, RemotingConnection connection) throws ActiveMQSecurityException { |
| 379 | + ClusterCredentialsCheckResult checkResult = checkClusterCredentials(user, password); |
| 380 | + |
| 381 | + if (checkResult == ClusterCredentialsCheckResult.VALID) { |
| 382 | + AUTHENTICATION_SUCCESS_COUNT_UPDATER.incrementAndGet(this); |
| 383 | + return user; |
| 384 | + } else if (checkResult == ClusterCredentialsCheckResult.INVALID) { |
| 385 | + AUTHENTICATION_FAILURE_COUNT_UPDATER.incrementAndGet(this); |
| 386 | + throw ActiveMQMessageBundle.BUNDLE.unableToValidateUser(connection == null ? "null" : connection.getRemoteAddress(), user, null); |
| 387 | + } else { |
| 388 | + return null; |
| 389 | + } |
| 390 | + } |
| 391 | + |
| 392 | + private ClusterCredentialsCheckResult checkClusterCredentials(String user, String password) { |
| 393 | + if ((getDefaultClusterUser().equals(user) && getDefaultClusterPassword().equals(password)) || |
| 394 | + (managementClusterUser.equals(user) && !managementClusterPassword.equals(password))) { |
| 395 | + // reject default cluster credentials |
| 396 | + // reject also if username is right, but password is wrong |
| 397 | + return ClusterCredentialsCheckResult.INVALID; |
| 398 | + } else if (managementClusterUser.equals(user) && managementClusterPassword.equals(password)) { |
| 399 | + // accept if both user & password are right |
| 400 | + return ClusterCredentialsCheckResult.VALID; |
| 401 | + } else { |
| 402 | + return ClusterCredentialsCheckResult.IGNORE; |
| 403 | + } |
| 404 | + } |
| 405 | + |
| 406 | + enum ClusterCredentialsCheckResult { |
| 407 | + VALID, INVALID, IGNORE |
| 408 | + } |
| 409 | + |
387 | 410 | @Override |
388 | 411 | public void check(final SimpleString address, |
389 | 412 | final SimpleString queue, |
|
0 commit comments