Skip to content

Commit 883b312

Browse files
authored
User Profile - Use only realmType for file and native realms (#84205)
When locating existing profile document for the given authentication, use only realm type to search for file and native realms. This is because there can only ever be a single file or native realm and it does not matter what name it takes. Relates: #83570
1 parent 270d22f commit 883b312

File tree

2 files changed

+53
-8
lines changed

2 files changed

+53
-8
lines changed

x-pack/plugin/security/src/internalClusterTest/java/org/elasticsearch/xpack/security/profile/ProfileDomainSingleNodeTests.java

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,8 @@
2020
import org.elasticsearch.xpack.core.security.authc.RealmConfig;
2121
import org.elasticsearch.xpack.core.security.authc.RealmDomain;
2222
import org.elasticsearch.xpack.core.security.authc.Subject;
23+
import org.elasticsearch.xpack.core.security.authc.esnative.NativeRealmSettings;
24+
import org.elasticsearch.xpack.core.security.authc.file.FileRealmSettings;
2325
import org.elasticsearch.xpack.core.security.user.User;
2426

2527
import java.time.Instant;
@@ -212,6 +214,41 @@ public void testGetProfileByAuthenticationDomainless() {
212214
assertThat(future3.actionGet(), nullValue());
213215
}
214216

217+
public void testGetProfileByAuthenticationWillNotCheckRealmNameForFileOrNativeRealm() {
218+
// File and native realms are under the same domain, activate the profile from either the realm
219+
final Profile profile1;
220+
if (randomBoolean()) {
221+
profile1 = doActivateProfile(RAC_USER_NAME, TEST_PASSWORD_SECURE_STRING);
222+
} else {
223+
profile1 = doActivateProfile(RAC_USER_NAME, NATIVE_RAC_USER_PASSWORD);
224+
}
225+
final ProfileService profileService = node().injector().getInstance(ProfileService.class);
226+
227+
final String realmName = randomAlphaOfLengthBetween(3, 8);
228+
final String realmType = randomBoolean() ? FileRealmSettings.TYPE : NativeRealmSettings.TYPE;
229+
final RealmDomain realmDomain = new RealmDomain(
230+
randomAlphaOfLengthBetween(3, 8),
231+
Set.of(
232+
new RealmConfig.RealmIdentifier(realmType, realmName),
233+
new RealmConfig.RealmIdentifier(
234+
FileRealmSettings.TYPE.equals(realmType) ? NativeRealmSettings.TYPE : FileRealmSettings.TYPE,
235+
randomAlphaOfLengthBetween(3, 8)
236+
)
237+
)
238+
);
239+
final Authentication.RealmRef authenticatedBy = new Authentication.RealmRef(
240+
realmName,
241+
realmType,
242+
randomAlphaOfLengthBetween(3, 8),
243+
realmDomain
244+
);
245+
final Authentication authentication1 = Authentication.newRealmAuthentication(new User(RAC_USER_NAME), authenticatedBy);
246+
247+
final PlainActionFuture<Profile> future1 = new PlainActionFuture<>();
248+
profileService.activateProfile(authentication1, future1);
249+
assertThat(future1.actionGet().uid(), equalTo(profile1.uid()));
250+
}
251+
215252
private String indexDocument() {
216253
final String uid = randomAlphaOfLength(20);
217254
final String source = ProfileServiceTests.SAMPLE_PROFILE_DOCUMENT_TEMPLATE.formatted(uid, Instant.now().toEpochMilli());

x-pack/plugin/security/src/main/java/org/elasticsearch/xpack/security/profile/ProfileService.java

Lines changed: 16 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,8 @@
5454
import org.elasticsearch.xpack.core.security.authc.Authentication;
5555
import org.elasticsearch.xpack.core.security.authc.AuthenticationContext;
5656
import org.elasticsearch.xpack.core.security.authc.Subject;
57+
import org.elasticsearch.xpack.core.security.authc.esnative.NativeRealmSettings;
58+
import org.elasticsearch.xpack.core.security.authc.file.FileRealmSettings;
5759
import org.elasticsearch.xpack.core.security.user.User;
5860
import org.elasticsearch.xpack.security.support.SecurityIndexManager;
5961

@@ -98,7 +100,6 @@ public void getProfile(String uid, @Nullable Set<String> dataKeys, ActionListene
98100
}
99101

100102
// TODO: with request when we take request body for profile activation
101-
102103
/**
103104
* Create a new profile or update an existing profile for the user of the given Authentication.
104105
* @param authentication This is the object from which the profile will be created or updated.
@@ -259,8 +260,10 @@ void getVersionedDocument(Subject subject, ActionListener<VersionedDocument> lis
259260
final BoolQueryBuilder boolQuery = QueryBuilders.boolQuery()
260261
.filter(QueryBuilders.termQuery("user_profile.user.username", subject.getUser().principal()));
261262
if (subject.getRealm().getDomain() == null) {
262-
boolQuery.filter(QueryBuilders.termQuery("user_profile.user.realm.name", subject.getRealm().getName()))
263-
.filter(QueryBuilders.termQuery("user_profile.user.realm.type", subject.getRealm().getType()));
263+
boolQuery.filter(QueryBuilders.termQuery("user_profile.user.realm.type", subject.getRealm().getType()));
264+
if (false == isFileOrNativeRealm(subject.getRealm().getType())) {
265+
boolQuery.filter(QueryBuilders.termQuery("user_profile.user.realm.name", subject.getRealm().getName()));
266+
}
264267
} else {
265268
logger.debug(
266269
() -> new ParameterizedMessage(
@@ -271,11 +274,12 @@ void getVersionedDocument(Subject subject, ActionListener<VersionedDocument> lis
271274
)
272275
);
273276
subject.getRealm().getDomain().realms().forEach(realmIdentifier -> {
274-
boolQuery.should(
275-
QueryBuilders.boolQuery()
276-
.filter(QueryBuilders.termQuery("user_profile.user.realm.name", realmIdentifier.getName()))
277-
.filter(QueryBuilders.termQuery("user_profile.user.realm.type", realmIdentifier.getType()))
278-
);
277+
final BoolQueryBuilder perRealmQuery = QueryBuilders.boolQuery()
278+
.filter(QueryBuilders.termQuery("user_profile.user.realm.type", realmIdentifier.getType()));
279+
if (false == isFileOrNativeRealm(realmIdentifier.getType())) {
280+
perRealmQuery.filter(QueryBuilders.termQuery("user_profile.user.realm.name", realmIdentifier.getName()));
281+
}
282+
boolQuery.should(perRealmQuery);
279283
});
280284
boolQuery.minimumShouldMatch(1);
281285
}
@@ -489,6 +493,10 @@ private ProfileDocument updateWithSubject(ProfileDocument doc, Subject subject)
489493
);
490494
}
491495

496+
private boolean isFileOrNativeRealm(String realmType) {
497+
return FileRealmSettings.TYPE.equals(realmType) || NativeRealmSettings.TYPE.equals(realmType);
498+
}
499+
492500
// Package private for testing
493501
record VersionedDocument(ProfileDocument doc, long primaryTerm, long seqNo) {
494502

0 commit comments

Comments
 (0)