Skip to content

Commit 7989b95

Browse files
authored
Add internal and anonymous authentication types (#36331)
This change builds upon the work done in #35970 and adds appropriate types for anonymous and internal authentication to the `AuthenticationType` enum.
1 parent b3bbf4e commit 7989b95

File tree

7 files changed

+73
-27
lines changed

7 files changed

+73
-27
lines changed

x-pack/plugin/core/src/main/java/org/elasticsearch/xpack/core/security/SecurityContext.java

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -13,9 +13,11 @@
1313
import org.elasticsearch.common.util.concurrent.ThreadContext.StoredContext;
1414
import org.elasticsearch.node.Node;
1515
import org.elasticsearch.xpack.core.security.authc.Authentication;
16+
import org.elasticsearch.xpack.core.security.authc.Authentication.AuthenticationType;
1617
import org.elasticsearch.xpack.core.security.user.User;
1718

1819
import java.io.IOException;
20+
import java.util.Collections;
1921
import java.util.Objects;
2022
import java.util.function.Consumer;
2123

@@ -71,7 +73,8 @@ public void setUser(User user, Version version) {
7173
} else {
7274
lookedUpBy = null;
7375
}
74-
setAuthentication(new Authentication(user, authenticatedBy, lookedUpBy, version));
76+
setAuthentication(
77+
new Authentication(user, authenticatedBy, lookedUpBy, version, AuthenticationType.INTERNAL, Collections.emptyMap()));
7578
}
7679

7780
/** Writes the authentication to the thread context */
@@ -89,7 +92,7 @@ private void setAuthentication(Authentication authentication) {
8992
*/
9093
public void executeAsUser(User user, Consumer<StoredContext> consumer, Version version) {
9194
final StoredContext original = threadContext.newStoredContext(true);
92-
try (ThreadContext.StoredContext ctx = threadContext.stashContext()) {
95+
try (ThreadContext.StoredContext ignore = threadContext.stashContext()) {
9396
setUser(user, version);
9497
consumer.accept(original);
9598
}
@@ -102,9 +105,9 @@ public void executeAsUser(User user, Consumer<StoredContext> consumer, Version v
102105
public void executeAfterRewritingAuthentication(Consumer<StoredContext> consumer, Version version) {
103106
final StoredContext original = threadContext.newStoredContext(true);
104107
final Authentication authentication = Objects.requireNonNull(userSettings.getAuthentication());
105-
try (ThreadContext.StoredContext ctx = threadContext.stashContext()) {
108+
try (ThreadContext.StoredContext ignore = threadContext.stashContext()) {
106109
setAuthentication(new Authentication(authentication.getUser(), authentication.getAuthenticatedBy(),
107-
authentication.getLookedUpBy(), version));
110+
authentication.getLookedUpBy(), version, authentication.getAuthenticationType(), authentication.getMetadata()));
108111
consumer.accept(original);
109112
}
110113
}

x-pack/plugin/core/src/main/java/org/elasticsearch/xpack/core/security/authc/Authentication.java

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -274,7 +274,9 @@ public int hashCode() {
274274
public enum AuthenticationType {
275275
REALM,
276276
API_KEY,
277-
TOKEN
277+
TOKEN,
278+
ANONYMOUS,
279+
INTERNAL
278280
}
279281
}
280282

x-pack/plugin/security/src/main/java/org/elasticsearch/xpack/security/authc/AuthenticationService.java

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@
2424
import org.elasticsearch.transport.TransportMessage;
2525
import org.elasticsearch.xpack.core.common.IteratingActionListener;
2626
import org.elasticsearch.xpack.core.security.authc.Authentication;
27+
import org.elasticsearch.xpack.core.security.authc.Authentication.AuthenticationType;
2728
import org.elasticsearch.xpack.core.security.authc.Authentication.RealmRef;
2829
import org.elasticsearch.xpack.core.security.authc.AuthenticationFailureHandler;
2930
import org.elasticsearch.xpack.core.security.authc.AuthenticationResult;
@@ -40,6 +41,7 @@
4041
import org.elasticsearch.xpack.security.audit.AuditUtil;
4142
import org.elasticsearch.xpack.security.authc.support.RealmUserLookup;
4243

44+
import java.util.Collections;
4345
import java.util.LinkedHashMap;
4446
import java.util.List;
4547
import java.util.Map;
@@ -360,10 +362,12 @@ void handleNullToken() {
360362
final Authentication authentication;
361363
if (fallbackUser != null) {
362364
RealmRef authenticatedBy = new RealmRef("__fallback", "__fallback", nodeName);
363-
authentication = new Authentication(fallbackUser, authenticatedBy, null);
365+
authentication = new Authentication(fallbackUser, authenticatedBy, null, Version.CURRENT, AuthenticationType.INTERNAL,
366+
Collections.emptyMap());
364367
} else if (isAnonymousUserEnabled) {
365368
RealmRef authenticatedBy = new RealmRef("__anonymous", "__anonymous", nodeName);
366-
authentication = new Authentication(anonymousUser, authenticatedBy, null);
369+
authentication = new Authentication(anonymousUser, authenticatedBy, null, Version.CURRENT, AuthenticationType.ANONYMOUS,
370+
Collections.emptyMap());
367371
} else {
368372
authentication = null;
369373
}

x-pack/plugin/security/src/main/java/org/elasticsearch/xpack/security/authc/TokenService.java

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -73,6 +73,7 @@
7373
import org.elasticsearch.xpack.core.XPackSettings;
7474
import org.elasticsearch.xpack.core.security.ScrollHelper;
7575
import org.elasticsearch.xpack.core.security.authc.Authentication;
76+
import org.elasticsearch.xpack.core.security.authc.Authentication.AuthenticationType;
7677
import org.elasticsearch.xpack.core.security.authc.KeyAndTimestamp;
7778
import org.elasticsearch.xpack.core.security.authc.TokenMetaData;
7879
import org.elasticsearch.xpack.security.support.SecurityIndexManager;
@@ -230,10 +231,9 @@ public void createUserToken(Authentication authentication, Authentication origin
230231
final Instant created = clock.instant();
231232
final Instant expiration = getExpirationTime(created);
232233
final Version version = clusterService.state().nodes().getMinNodeVersion();
233-
final Authentication matchingVersionAuth = version.equals(authentication.getVersion()) ? authentication :
234-
new Authentication(authentication.getUser(), authentication.getAuthenticatedBy(), authentication.getLookedUpBy(),
235-
version);
236-
final UserToken userToken = new UserToken(version, matchingVersionAuth, expiration, metadata);
234+
final Authentication tokenAuth = new Authentication(authentication.getUser(), authentication.getAuthenticatedBy(),
235+
authentication.getLookedUpBy(), version, AuthenticationType.TOKEN, authentication.getMetadata());
236+
final UserToken userToken = new UserToken(version, tokenAuth, expiration, metadata);
237237
final String refreshToken = includeRefreshToken ? UUIDs.randomBase64UUID() : null;
238238

239239
try (XContentBuilder builder = XContentFactory.jsonBuilder()) {

x-pack/plugin/security/src/test/java/org/elasticsearch/xpack/security/SecurityContextTests.java

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
import org.elasticsearch.test.VersionUtils;
1414
import org.elasticsearch.xpack.core.security.SecurityContext;
1515
import org.elasticsearch.xpack.core.security.authc.Authentication;
16+
import org.elasticsearch.xpack.core.security.authc.Authentication.AuthenticationType;
1617
import org.elasticsearch.xpack.core.security.authc.Authentication.RealmRef;
1718
import org.elasticsearch.xpack.core.security.user.SystemUser;
1819
import org.elasticsearch.xpack.core.security.user.User;
@@ -56,6 +57,7 @@ public void testSetUser() {
5657
assertNull(securityContext.getUser());
5758
securityContext.setUser(user, Version.CURRENT);
5859
assertEquals(user, securityContext.getUser());
60+
assertEquals(AuthenticationType.INTERNAL, securityContext.getAuthentication().getAuthenticationType());
5961

6062
IllegalStateException e = expectThrows(IllegalStateException.class,
6163
() -> securityContext.setUser(randomFrom(user, SystemUser.INSTANCE), Version.CURRENT));
@@ -76,11 +78,15 @@ public void testExecuteAsUser() throws IOException {
7678
final AtomicReference<StoredContext> contextAtomicReference = new AtomicReference<>();
7779
securityContext.executeAsUser(executionUser, (originalCtx) -> {
7880
assertEquals(executionUser, securityContext.getUser());
81+
assertEquals(AuthenticationType.INTERNAL, securityContext.getAuthentication().getAuthenticationType());
7982
contextAtomicReference.set(originalCtx);
8083
}, Version.CURRENT);
8184

8285
final User userAfterExecution = securityContext.getUser();
8386
assertEquals(original, userAfterExecution);
87+
if (original != null) {
88+
assertEquals(AuthenticationType.REALM, securityContext.getAuthentication().getAuthenticationType());
89+
}
8490
StoredContext originalContext = contextAtomicReference.get();
8591
assertNotNull(originalContext);
8692
originalContext.restore();
@@ -100,6 +106,7 @@ public void testExecuteAfterRewritingAuthentication() throws IOException {
100106
assertEquals(original.getAuthenticatedBy(), authentication.getAuthenticatedBy());
101107
assertEquals(original.getLookedUpBy(), authentication.getLookedUpBy());
102108
assertEquals(VersionUtils.getPreviousVersion(), authentication.getVersion());
109+
assertEquals(original.getAuthenticationType(), securityContext.getAuthentication().getAuthenticationType());
103110
contextAtomicReference.set(originalCtx);
104111
}, VersionUtils.getPreviousVersion());
105112

x-pack/plugin/security/src/test/java/org/elasticsearch/xpack/security/authc/AuthenticationServiceTests.java

Lines changed: 18 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,7 @@
5757
import org.elasticsearch.xpack.core.XPackField;
5858
import org.elasticsearch.xpack.core.XPackSettings;
5959
import org.elasticsearch.xpack.core.security.authc.Authentication;
60+
import org.elasticsearch.xpack.core.security.authc.Authentication.AuthenticationType;
6061
import org.elasticsearch.xpack.core.security.authc.Authentication.RealmRef;
6162
import org.elasticsearch.xpack.core.security.authc.AuthenticationField;
6263
import org.elasticsearch.xpack.core.security.authc.AuthenticationResult;
@@ -270,6 +271,7 @@ public void testAuthenticateBothSupportSecondSucceeds() throws Exception {
270271
assertThat(result.getUser(), is(user));
271272
assertThat(result.getLookedUpBy(), is(nullValue()));
272273
assertThat(result.getAuthenticatedBy(), is(notNullValue())); // TODO implement equals
274+
assertThat(result.getAuthenticationType(), is(AuthenticationType.REALM));
273275
assertThreadContextContainsAuthentication(result);
274276
setCompletedToTrue(completed);
275277
}, this::logAndFail));
@@ -289,6 +291,7 @@ public void testAuthenticateFirstNotSupportingSecondSucceeds() throws Exception
289291
service.authenticate("_action", message, (User)null, ActionListener.wrap(result -> {
290292
assertThat(result, notNullValue());
291293
assertThat(result.getUser(), is(user));
294+
assertThat(result.getAuthenticationType(), is(AuthenticationType.REALM));
292295
assertThreadContextContainsAuthentication(result);
293296
setCompletedToTrue(completed);
294297
}, this::logAndFail));
@@ -306,6 +309,7 @@ public void testAuthenticateCached() throws Exception {
306309

307310
assertThat(result, notNullValue());
308311
assertThat(result, is(authentication));
312+
assertThat(result.getAuthenticationType(), is(AuthenticationType.REALM));
309313
verifyZeroInteractions(auditTrail);
310314
verifyZeroInteractions(firstRealm);
311315
verifyZeroInteractions(secondRealm);
@@ -342,6 +346,7 @@ public void authenticationInContextAndHeader() throws Exception {
342346

343347
assertThat(result, notNullValue());
344348
assertThat(result.getUser(), is(user));
349+
assertThat(result.getAuthenticationType(), is(AuthenticationType.REALM));
345350

346351
String userStr = threadContext.getHeader(AuthenticationField.AUTHENTICATION_KEY);
347352
assertThat(userStr, notNullValue());
@@ -387,6 +392,7 @@ public void testAuthenticateTransportFallback() throws Exception {
387392
Authentication result = authenticateBlocking("_action", message, user1);
388393
assertThat(result, notNullValue());
389394
assertThat(result.getUser(), sameInstance(user1));
395+
assertThat(result.getAuthenticationType(), is(AuthenticationType.INTERNAL));
390396
assertThreadContextContainsAuthentication(result);
391397
}
392398

@@ -432,6 +438,7 @@ public void testAuthenticateTransportSuccess() throws Exception {
432438
assertThat(result, notNullValue());
433439
assertThat(result.getUser(), sameInstance(user));
434440
assertThreadContextContainsAuthentication(result);
441+
assertThat(result.getAuthenticationType(), is(AuthenticationType.REALM));
435442
setCompletedToTrue(completed);
436443
}, this::logAndFail));
437444

@@ -450,6 +457,7 @@ public void testAuthenticateRestSuccess() throws Exception {
450457
service.authenticate(restRequest, ActionListener.wrap(authentication -> {
451458
assertThat(authentication, notNullValue());
452459
assertThat(authentication.getUser(), sameInstance(user1));
460+
assertThat(authentication.getAuthenticationType(), is(AuthenticationType.REALM));
453461
assertThreadContextContainsAuthentication(authentication);
454462
setCompletedToTrue(completed);
455463
}, this::logAndFail));
@@ -459,7 +467,7 @@ public void testAuthenticateRestSuccess() throws Exception {
459467
assertTrue(completed.get());
460468
}
461469

462-
public void testAutheticateTransportContextAndHeader() throws Exception {
470+
public void testAuthenticateTransportContextAndHeader() throws Exception {
463471
User user1 = new User("username", "r1", "r2");
464472
when(firstRealm.token(threadContext)).thenReturn(token);
465473
when(firstRealm.supports(token)).thenReturn(true);
@@ -469,9 +477,9 @@ public void testAutheticateTransportContextAndHeader() throws Exception {
469477
final SetOnce<String> authHeaderRef = new SetOnce<>();
470478
try (ThreadContext.StoredContext ignore = threadContext.stashContext()) {
471479
service.authenticate("_action", message, SystemUser.INSTANCE, ActionListener.wrap(authentication -> {
472-
473480
assertThat(authentication, notNullValue());
474481
assertThat(authentication.getUser(), sameInstance(user1));
482+
assertThat(authentication.getAuthenticationType(), is(AuthenticationType.REALM));
475483
assertThreadContextContainsAuthentication(authentication);
476484
authRef.set(authentication);
477485
authHeaderRef.set(threadContext.getHeader(AuthenticationField.AUTHENTICATION_KEY));
@@ -530,6 +538,7 @@ public void testAutheticateTransportContextAndHeader() throws Exception {
530538
service.authenticate("_action", new InternalMessage(), SystemUser.INSTANCE, ActionListener.wrap(result -> {
531539
assertThat(result, notNullValue());
532540
assertThat(result.getUser(), equalTo(user1));
541+
assertThat(result.getAuthenticationType(), is(AuthenticationType.REALM));
533542
setCompletedToTrue(completed);
534543
}, this::logAndFail));
535544
assertTrue(completed.get());
@@ -570,6 +579,7 @@ public void testAnonymousUserRest() throws Exception {
570579

571580
assertThat(result, notNullValue());
572581
assertThat(result.getUser(), sameInstance((Object) anonymousUser));
582+
assertThat(result.getAuthenticationType(), is(AuthenticationType.ANONYMOUS));
573583
assertThreadContextContainsAuthentication(result);
574584
String reqId = expectAuditRequestId();
575585
verify(auditTrail).authenticationSuccess(reqId, "__anonymous", new AnonymousUser(settings), request);
@@ -588,6 +598,7 @@ public void testAnonymousUserTransportNoDefaultUser() throws Exception {
588598
Authentication result = authenticateBlocking("_action", message, null);
589599
assertThat(result, notNullValue());
590600
assertThat(result.getUser(), sameInstance(anonymousUser));
601+
assertThat(result.getAuthenticationType(), is(AuthenticationType.ANONYMOUS));
591602
assertThreadContextContainsAuthentication(result);
592603
}
593604

@@ -604,6 +615,7 @@ public void testAnonymousUserTransportWithDefaultUser() throws Exception {
604615
Authentication result = authenticateBlocking("_action", message, SystemUser.INSTANCE);
605616
assertThat(result, notNullValue());
606617
assertThat(result.getUser(), sameInstance(SystemUser.INSTANCE));
618+
assertThat(result.getAuthenticationType(), is(AuthenticationType.INTERNAL));
607619
assertThreadContextContainsAuthentication(result);
608620
}
609621

@@ -790,6 +802,7 @@ public void testRunAsLookupSameRealm() throws Exception {
790802
final AtomicBoolean completed = new AtomicBoolean(false);
791803
ActionListener<Authentication> listener = ActionListener.wrap(result -> {
792804
assertThat(result, notNullValue());
805+
assertThat(result.getAuthenticationType(), is(AuthenticationType.REALM));
793806
User authenticated = result.getUser();
794807

795808
assertThat(authenticated.principal(), is("looked up user"));
@@ -835,6 +848,7 @@ public void testRunAsLookupDifferentRealm() throws Exception {
835848
final AtomicBoolean completed = new AtomicBoolean(false);
836849
ActionListener<Authentication> listener = ActionListener.wrap(result -> {
837850
assertThat(result, notNullValue());
851+
assertThat(result.getAuthenticationType(), is(AuthenticationType.REALM));
838852
User authenticated = result.getUser();
839853

840854
assertThat(SystemUser.is(authenticated), is(false));
@@ -958,7 +972,7 @@ public void testAuthenticateWithToken() throws Exception {
958972
assertThat(result.getUser(), is(user));
959973
assertThat(result.getLookedUpBy(), is(nullValue()));
960974
assertThat(result.getAuthenticatedBy(), is(notNullValue()));
961-
assertEquals(expected, result);
975+
assertThat(result.getAuthenticationType(), is(AuthenticationType.TOKEN));
962976
setCompletedToTrue(completed);
963977
}, this::logAndFail));
964978
}
@@ -1115,6 +1129,7 @@ public void testApiKeyAuth() {
11151129
threadContext.putHeader("Authorization", headerValue);
11161130
final Authentication authentication = authenticateBlocking("_action", message, null);
11171131
assertThat(authentication.getUser().principal(), is("johndoe"));
1132+
assertThat(authentication.getAuthenticationType(), is(AuthenticationType.API_KEY));
11181133
}
11191134
}
11201135

0 commit comments

Comments
 (0)