Merge branch 'master' into fix/client-cookie
Original commit: elastic/x-pack-elasticsearch@a9920d5626
This commit is contained in:
commit
00fba58c56
|
@ -5,6 +5,8 @@ dependencies {
|
||||||
testCompile "org.elasticsearch.test:framework:${version}"
|
testCompile "org.elasticsearch.test:framework:${version}"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
compactProfile = 'full'
|
||||||
|
|
||||||
dependencyLicenses.enabled = false
|
dependencyLicenses.enabled = false
|
||||||
|
|
||||||
jar {
|
jar {
|
||||||
|
|
|
@ -6,8 +6,6 @@
|
||||||
package org.elasticsearch.license.core;
|
package org.elasticsearch.license.core;
|
||||||
|
|
||||||
|
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
|
|
||||||
import javax.crypto.BadPaddingException;
|
import javax.crypto.BadPaddingException;
|
||||||
import javax.crypto.Cipher;
|
import javax.crypto.Cipher;
|
||||||
import javax.crypto.IllegalBlockSizeException;
|
import javax.crypto.IllegalBlockSizeException;
|
||||||
|
@ -27,6 +25,7 @@ import java.security.SecureRandom;
|
||||||
import java.security.spec.InvalidKeySpecException;
|
import java.security.spec.InvalidKeySpecException;
|
||||||
import java.security.spec.PKCS8EncodedKeySpec;
|
import java.security.spec.PKCS8EncodedKeySpec;
|
||||||
import java.security.spec.X509EncodedKeySpec;
|
import java.security.spec.X509EncodedKeySpec;
|
||||||
|
import java.util.Base64;
|
||||||
|
|
||||||
public class CryptUtils {
|
public class CryptUtils {
|
||||||
private static final int minimumPadding = 20;
|
private static final int minimumPadding = 20;
|
||||||
|
@ -251,6 +250,6 @@ public class CryptUtils {
|
||||||
private static char[] hashPassPhrase(String passPhrase) throws NoSuchAlgorithmException {
|
private static char[] hashPassPhrase(String passPhrase) throws NoSuchAlgorithmException {
|
||||||
final byte[] passBytes = passPhrase.getBytes(StandardCharsets.UTF_8);
|
final byte[] passBytes = passPhrase.getBytes(StandardCharsets.UTF_8);
|
||||||
final byte[] digest = MessageDigest.getInstance(passHashAlgorithm).digest(passBytes);
|
final byte[] digest = MessageDigest.getInstance(passHashAlgorithm).digest(passBytes);
|
||||||
return new String(Base64.encodeBytesToBytes(digest), StandardCharsets.UTF_8).toCharArray();
|
return Base64.getEncoder().encodeToString(digest).toCharArray();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -8,7 +8,6 @@ package org.elasticsearch.license.core;
|
||||||
import org.apache.lucene.util.CollectionUtil;
|
import org.apache.lucene.util.CollectionUtil;
|
||||||
import org.elasticsearch.ElasticsearchException;
|
import org.elasticsearch.ElasticsearchException;
|
||||||
import org.elasticsearch.ElasticsearchParseException;
|
import org.elasticsearch.ElasticsearchParseException;
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.common.io.stream.StreamInput;
|
import org.elasticsearch.common.io.stream.StreamInput;
|
||||||
import org.elasticsearch.common.io.stream.StreamOutput;
|
import org.elasticsearch.common.io.stream.StreamOutput;
|
||||||
import org.elasticsearch.common.xcontent.ToXContent;
|
import org.elasticsearch.common.xcontent.ToXContent;
|
||||||
|
@ -20,6 +19,7 @@ import java.io.IOException;
|
||||||
import java.nio.ByteBuffer;
|
import java.nio.ByteBuffer;
|
||||||
import java.nio.charset.StandardCharsets;
|
import java.nio.charset.StandardCharsets;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
import java.util.Base64;
|
||||||
import java.util.Comparator;
|
import java.util.Comparator;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Locale;
|
import java.util.Locale;
|
||||||
|
@ -388,7 +388,7 @@ public class License implements ToXContent {
|
||||||
}
|
}
|
||||||
// not a license spec
|
// not a license spec
|
||||||
if (builder.signature != null) {
|
if (builder.signature != null) {
|
||||||
byte[] signatureBytes = Base64.decode(builder.signature);
|
byte[] signatureBytes = Base64.getDecoder().decode(builder.signature);
|
||||||
ByteBuffer byteBuffer = ByteBuffer.wrap(signatureBytes);
|
ByteBuffer byteBuffer = ByteBuffer.wrap(signatureBytes);
|
||||||
int version = byteBuffer.getInt();
|
int version = byteBuffer.getInt();
|
||||||
// we take the absolute version, because negative versions
|
// we take the absolute version, because negative versions
|
||||||
|
@ -415,10 +415,10 @@ public class License implements ToXContent {
|
||||||
*/
|
*/
|
||||||
public static boolean isAutoGeneratedLicense(String signature) {
|
public static boolean isAutoGeneratedLicense(String signature) {
|
||||||
try {
|
try {
|
||||||
byte[] signatureBytes = Base64.decode(signature);
|
byte[] signatureBytes = Base64.getDecoder().decode(signature);
|
||||||
ByteBuffer byteBuffer = ByteBuffer.wrap(signatureBytes);
|
ByteBuffer byteBuffer = ByteBuffer.wrap(signatureBytes);
|
||||||
return byteBuffer.getInt() < 0;
|
return byteBuffer.getInt() < 0;
|
||||||
} catch (IOException e) {
|
} catch (IllegalArgumentException e) {
|
||||||
throw new IllegalStateException(e);
|
throw new IllegalStateException(e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,7 +5,6 @@
|
||||||
*/
|
*/
|
||||||
package org.elasticsearch.license.core;
|
package org.elasticsearch.license.core;
|
||||||
|
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.common.xcontent.ToXContent;
|
import org.elasticsearch.common.xcontent.ToXContent;
|
||||||
import org.elasticsearch.common.xcontent.XContentBuilder;
|
import org.elasticsearch.common.xcontent.XContentBuilder;
|
||||||
import org.elasticsearch.common.xcontent.XContentFactory;
|
import org.elasticsearch.common.xcontent.XContentFactory;
|
||||||
|
@ -18,6 +17,7 @@ import java.security.NoSuchAlgorithmException;
|
||||||
import java.security.Signature;
|
import java.security.Signature;
|
||||||
import java.security.SignatureException;
|
import java.security.SignatureException;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
import java.util.Base64;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -35,7 +35,7 @@ public class LicenseVerifier {
|
||||||
byte[] signedContent = null;
|
byte[] signedContent = null;
|
||||||
byte[] signatureHash = null;
|
byte[] signatureHash = null;
|
||||||
try {
|
try {
|
||||||
byte[] signatureBytes = Base64.decode(license.signature());
|
byte[] signatureBytes = Base64.getDecoder().decode(license.signature());
|
||||||
ByteBuffer byteBuffer = ByteBuffer.wrap(signatureBytes);
|
ByteBuffer byteBuffer = ByteBuffer.wrap(signatureBytes);
|
||||||
int version = byteBuffer.getInt();
|
int version = byteBuffer.getInt();
|
||||||
int magicLen = byteBuffer.getInt();
|
int magicLen = byteBuffer.getInt();
|
||||||
|
@ -53,7 +53,7 @@ public class LicenseVerifier {
|
||||||
rsa.initVerify(CryptUtils.readEncryptedPublicKey(encryptedPublicKeyData));
|
rsa.initVerify(CryptUtils.readEncryptedPublicKey(encryptedPublicKeyData));
|
||||||
rsa.update(contentBuilder.bytes().toBytes());
|
rsa.update(contentBuilder.bytes().toBytes());
|
||||||
return rsa.verify(signedContent)
|
return rsa.verify(signedContent)
|
||||||
&& Arrays.equals(Base64.encodeBytesToBytes(encryptedPublicKeyData), signatureHash);
|
&& Arrays.equals(Base64.getEncoder().encode(encryptedPublicKeyData), signatureHash);
|
||||||
} catch (IOException | NoSuchAlgorithmException | SignatureException | InvalidKeyException e) {
|
} catch (IOException | NoSuchAlgorithmException | SignatureException | InvalidKeyException e) {
|
||||||
throw new IllegalStateException(e);
|
throw new IllegalStateException(e);
|
||||||
} finally {
|
} finally {
|
||||||
|
|
|
@ -5,7 +5,6 @@
|
||||||
*/
|
*/
|
||||||
package org.elasticsearch.license.licensor;
|
package org.elasticsearch.license.licensor;
|
||||||
|
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.common.xcontent.ToXContent;
|
import org.elasticsearch.common.xcontent.ToXContent;
|
||||||
import org.elasticsearch.common.xcontent.XContentBuilder;
|
import org.elasticsearch.common.xcontent.XContentBuilder;
|
||||||
import org.elasticsearch.common.xcontent.XContentFactory;
|
import org.elasticsearch.common.xcontent.XContentFactory;
|
||||||
|
@ -22,6 +21,7 @@ import java.security.NoSuchAlgorithmException;
|
||||||
import java.security.SecureRandom;
|
import java.security.SecureRandom;
|
||||||
import java.security.Signature;
|
import java.security.Signature;
|
||||||
import java.security.SignatureException;
|
import java.security.SignatureException;
|
||||||
|
import java.util.Base64;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -63,7 +63,7 @@ public class LicenseSigner {
|
||||||
final byte[] magic = new byte[MAGIC_LENGTH];
|
final byte[] magic = new byte[MAGIC_LENGTH];
|
||||||
SecureRandom random = new SecureRandom();
|
SecureRandom random = new SecureRandom();
|
||||||
random.nextBytes(magic);
|
random.nextBytes(magic);
|
||||||
final byte[] hash = Base64.encodeBytesToBytes(Files.readAllBytes(publicKeyPath));
|
final byte[] hash = Base64.getEncoder().encode(Files.readAllBytes(publicKeyPath));
|
||||||
assert hash != null;
|
assert hash != null;
|
||||||
byte[] bytes = new byte[4 + 4 + MAGIC_LENGTH + 4 + hash.length + 4 + signedContent.length];
|
byte[] bytes = new byte[4 + 4 + MAGIC_LENGTH + 4 + hash.length + 4 + signedContent.length];
|
||||||
ByteBuffer byteBuffer = ByteBuffer.wrap(bytes);
|
ByteBuffer byteBuffer = ByteBuffer.wrap(bytes);
|
||||||
|
@ -76,7 +76,7 @@ public class LicenseSigner {
|
||||||
.put(signedContent);
|
.put(signedContent);
|
||||||
|
|
||||||
return License.builder()
|
return License.builder()
|
||||||
.fromLicenseSpec(licenseSpec, Base64.encodeBytes(bytes))
|
.fromLicenseSpec(licenseSpec, Base64.getEncoder().encodeToString(bytes))
|
||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -10,7 +10,6 @@ import org.elasticsearch.action.search.SearchRequest;
|
||||||
import org.elasticsearch.action.search.SearchResponse;
|
import org.elasticsearch.action.search.SearchResponse;
|
||||||
import org.elasticsearch.action.search.SearchType;
|
import org.elasticsearch.action.search.SearchType;
|
||||||
import org.elasticsearch.client.Requests;
|
import org.elasticsearch.client.Requests;
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.common.bytes.BytesArray;
|
import org.elasticsearch.common.bytes.BytesArray;
|
||||||
import org.elasticsearch.common.bytes.BytesReference;
|
import org.elasticsearch.common.bytes.BytesReference;
|
||||||
import org.elasticsearch.common.io.Streams;
|
import org.elasticsearch.common.io.Streams;
|
||||||
|
@ -60,6 +59,7 @@ import java.nio.charset.StandardCharsets;
|
||||||
import java.nio.file.Files;
|
import java.nio.file.Files;
|
||||||
import java.nio.file.Path;
|
import java.nio.file.Path;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
import java.util.Base64;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
@ -214,7 +214,7 @@ public class SearchTransformIT extends ESIntegTestCase {
|
||||||
assertThat(map.get("query"), instanceOf(String.class));
|
assertThat(map.get("query"), instanceOf(String.class));
|
||||||
|
|
||||||
String queryAsBase64 = (String) map.get("query");
|
String queryAsBase64 = (String) map.get("query");
|
||||||
String decodedQuery = new String(Base64.decode(queryAsBase64), StandardCharsets.UTF_8);
|
String decodedQuery = new String(Base64.getDecoder().decode(queryAsBase64), StandardCharsets.UTF_8);
|
||||||
assertThat(decodedQuery, containsString("_unknown_query_"));
|
assertThat(decodedQuery, containsString("_unknown_query_"));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -140,12 +140,12 @@ def smoke_test_release(release, files, expected_hash):
|
||||||
|
|
||||||
# put the supplied license to ensure that system was built with
|
# put the supplied license to ensure that system was built with
|
||||||
license = read_fully(os.path.join(os.path.dirname(__file__), 'license.json'))
|
license = read_fully(os.path.join(os.path.dirname(__file__), 'license.json'))
|
||||||
conn.request('PUT', '/_license?acknowledge=true', license, headers=headers)
|
conn.request('PUT', '/_xpack/license?acknowledge=true', license, headers=headers)
|
||||||
res = conn.getresponse()
|
res = conn.getresponse()
|
||||||
# reading the result, so we can execute the next request on the same connection
|
# reading the result, so we can execute the next request on the same connection
|
||||||
license_resp = json.loads(res.read().decode('utf-8'))
|
license_resp = json.loads(res.read().decode('utf-8'))
|
||||||
if res.status != 200:
|
if res.status != 200:
|
||||||
raise RuntimeError('Could not PUT _license, got status %s' % res.status)
|
raise RuntimeError('Could not PUT _xpack/license, got status %s' % res.status)
|
||||||
if license_resp['license_status'] != 'valid':
|
if license_resp['license_status'] != 'valid':
|
||||||
raise RuntimeError('Expected license to be valid, but was %s' % license_resp['license_status'])
|
raise RuntimeError('Expected license to be valid, but was %s' % license_resp['license_status'])
|
||||||
|
|
||||||
|
|
|
@ -35,6 +35,10 @@ dependencies {
|
||||||
compile 'com.googlecode.owasp-java-html-sanitizer:owasp-java-html-sanitizer:r239'
|
compile 'com.googlecode.owasp-java-html-sanitizer:owasp-java-html-sanitizer:r239'
|
||||||
compile 'com.google.guava:guava:16.0.1' // needed by watcher for the html sanitizer and shield tests for jimfs
|
compile 'com.google.guava:guava:16.0.1' // needed by watcher for the html sanitizer and shield tests for jimfs
|
||||||
compile 'com.sun.mail:javax.mail:1.5.3'
|
compile 'com.sun.mail:javax.mail:1.5.3'
|
||||||
|
// HACK: java 9 removed javax.activation from the default modules, so instead of trying to add modules, which would have
|
||||||
|
// to be conditionalized for java 8/9, we pull in the classes directly
|
||||||
|
compile 'javax.activation:activation:1.1'
|
||||||
|
|
||||||
testCompile 'org.subethamail:subethasmtp:3.1.7'
|
testCompile 'org.subethamail:subethasmtp:3.1.7'
|
||||||
// needed for subethasmtp, has @GuardedBy annotation
|
// needed for subethasmtp, has @GuardedBy annotation
|
||||||
testCompile 'com.google.code.findbugs:jsr305:3.0.1'
|
testCompile 'com.google.code.findbugs:jsr305:3.0.1'
|
||||||
|
@ -169,6 +173,42 @@ thirdPartyAudit.excludes = [
|
||||||
'com.google.common.cache.Striped64$Cell',
|
'com.google.common.cache.Striped64$Cell',
|
||||||
'com.google.common.primitives.UnsignedBytes$LexicographicalComparatorHolder$UnsafeComparator',
|
'com.google.common.primitives.UnsignedBytes$LexicographicalComparatorHolder$UnsafeComparator',
|
||||||
'com.google.common.primitives.UnsignedBytes$LexicographicalComparatorHolder$UnsafeComparator$1',
|
'com.google.common.primitives.UnsignedBytes$LexicographicalComparatorHolder$UnsafeComparator$1',
|
||||||
|
|
||||||
|
// pulled in as external dependency to work on java 9
|
||||||
|
'com.sun.activation.registries.LineTokenizer',
|
||||||
|
'com.sun.activation.registries.LogSupport',
|
||||||
|
'com.sun.activation.registries.MailcapFile',
|
||||||
|
'com.sun.activation.registries.MailcapParseException',
|
||||||
|
'com.sun.activation.registries.MailcapTokenizer',
|
||||||
|
'com.sun.activation.registries.MimeTypeEntry',
|
||||||
|
'com.sun.activation.registries.MimeTypeFile',
|
||||||
|
'javax.activation.ActivationDataFlavor',
|
||||||
|
'javax.activation.CommandInfo',
|
||||||
|
'javax.activation.CommandMap',
|
||||||
|
'javax.activation.CommandObject',
|
||||||
|
'javax.activation.DataContentHandler',
|
||||||
|
'javax.activation.DataContentHandlerFactory',
|
||||||
|
'javax.activation.DataHandler$1',
|
||||||
|
'javax.activation.DataHandler',
|
||||||
|
'javax.activation.DataHandlerDataSource',
|
||||||
|
'javax.activation.DataSource',
|
||||||
|
'javax.activation.DataSourceDataContentHandler',
|
||||||
|
'javax.activation.FileDataSource',
|
||||||
|
'javax.activation.FileTypeMap',
|
||||||
|
'javax.activation.MailcapCommandMap',
|
||||||
|
'javax.activation.MimeType',
|
||||||
|
'javax.activation.MimeTypeParameterList',
|
||||||
|
'javax.activation.MimeTypeParseException',
|
||||||
|
'javax.activation.MimetypesFileTypeMap',
|
||||||
|
'javax.activation.ObjectDataContentHandler',
|
||||||
|
'javax.activation.SecuritySupport$1',
|
||||||
|
'javax.activation.SecuritySupport$2',
|
||||||
|
'javax.activation.SecuritySupport$3',
|
||||||
|
'javax.activation.SecuritySupport$4',
|
||||||
|
'javax.activation.SecuritySupport$5',
|
||||||
|
'javax.activation.SecuritySupport',
|
||||||
|
'javax.activation.URLDataSource',
|
||||||
|
'javax.activation.UnsupportedDataTypeException'
|
||||||
]
|
]
|
||||||
|
|
||||||
// someone figure out what the x-plugins logic should be
|
// someone figure out what the x-plugins logic should be
|
||||||
|
|
|
@ -9,7 +9,6 @@ import org.apache.lucene.util.CollectionUtil;
|
||||||
import org.elasticsearch.Version;
|
import org.elasticsearch.Version;
|
||||||
import org.elasticsearch.cluster.AbstractDiffable;
|
import org.elasticsearch.cluster.AbstractDiffable;
|
||||||
import org.elasticsearch.cluster.metadata.MetaData;
|
import org.elasticsearch.cluster.metadata.MetaData;
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.common.io.stream.StreamInput;
|
import org.elasticsearch.common.io.stream.StreamInput;
|
||||||
import org.elasticsearch.common.io.stream.StreamOutput;
|
import org.elasticsearch.common.io.stream.StreamOutput;
|
||||||
import org.elasticsearch.common.xcontent.ToXContent;
|
import org.elasticsearch.common.xcontent.ToXContent;
|
||||||
|
@ -21,6 +20,7 @@ import org.elasticsearch.license.core.License;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
import java.util.Base64;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.EnumSet;
|
import java.util.EnumSet;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
@ -114,7 +114,7 @@ public class LicensesMetaData extends AbstractDiffable<MetaData.Custom> implemen
|
||||||
while (parser.nextToken() != XContentParser.Token.END_ARRAY) {
|
while (parser.nextToken() != XContentParser.Token.END_ARRAY) {
|
||||||
if (parser.currentToken().isValue()) {
|
if (parser.currentToken().isValue()) {
|
||||||
// trial license
|
// trial license
|
||||||
byte[] data = decrypt(Base64.decode(parser.text()));
|
byte[] data = decrypt(Base64.getDecoder().decode(parser.text()));
|
||||||
try (XContentParser trialLicenseParser =
|
try (XContentParser trialLicenseParser =
|
||||||
XContentFactory.xContent(XContentType.JSON).createParser(data)) {
|
XContentFactory.xContent(XContentType.JSON).createParser(data)) {
|
||||||
trialLicenseParser.nextToken();
|
trialLicenseParser.nextToken();
|
||||||
|
@ -186,7 +186,7 @@ public class LicensesMetaData extends AbstractDiffable<MetaData.Custom> implemen
|
||||||
XContentBuilder contentBuilder = XContentFactory.contentBuilder(XContentType.JSON);
|
XContentBuilder contentBuilder = XContentFactory.contentBuilder(XContentType.JSON);
|
||||||
license.toXContent(contentBuilder,
|
license.toXContent(contentBuilder,
|
||||||
new ToXContent.MapParams(Collections.singletonMap(License.LICENSE_SPEC_VIEW_MODE, "true")));
|
new ToXContent.MapParams(Collections.singletonMap(License.LICENSE_SPEC_VIEW_MODE, "true")));
|
||||||
streamOutput.writeString(Base64.encodeBytes(encrypt(contentBuilder.bytes().toBytes())));
|
streamOutput.writeString(Base64.getEncoder().encodeToString(encrypt(contentBuilder.bytes().toBytes())));
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
if (license == LICENSE_TOMBSTONE) {
|
if (license == LICENSE_TOMBSTONE) {
|
||||||
|
@ -209,7 +209,7 @@ public class LicensesMetaData extends AbstractDiffable<MetaData.Custom> implemen
|
||||||
}
|
}
|
||||||
int numTrialLicenses = streamInput.readVInt();
|
int numTrialLicenses = streamInput.readVInt();
|
||||||
for (int i = 0; i < numTrialLicenses; i++) {
|
for (int i = 0; i < numTrialLicenses; i++) {
|
||||||
byte[] data = decrypt(Base64.decode(streamInput.readString()));
|
byte[] data = decrypt(Base64.getDecoder().decode(streamInput.readString()));
|
||||||
try (XContentParser trialLicenseParser = XContentFactory.xContent(XContentType.JSON).createParser(data)) {
|
try (XContentParser trialLicenseParser = XContentFactory.xContent(XContentType.JSON).createParser(data)) {
|
||||||
trialLicenseParser.nextToken();
|
trialLicenseParser.nextToken();
|
||||||
License pre20TrialLicense = License.fromXContent(trialLicenseParser);
|
License pre20TrialLicense = License.fromXContent(trialLicenseParser);
|
||||||
|
|
|
@ -149,7 +149,7 @@ public class LicensesService extends AbstractLifecycleComponent<LicensesService>
|
||||||
}
|
}
|
||||||
|
|
||||||
private void populateExpirationCallbacks() {
|
private void populateExpirationCallbacks() {
|
||||||
expirationCallbacks.add(new ExpirationCallback.Pre(days(7), days(30), days(1)) {
|
expirationCallbacks.add(new ExpirationCallback.Pre(days(7), days(25), days(1)) {
|
||||||
@Override
|
@Override
|
||||||
public void on(License license) {
|
public void on(License license) {
|
||||||
String general = LoggerMessageFormat.format(null, "\n" +
|
String general = LoggerMessageFormat.format(null, "\n" +
|
||||||
|
@ -174,9 +174,9 @@ public class LicensesService extends AbstractLifecycleComponent<LicensesService>
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
logger.error("{}", builder);
|
logger.warn("{}", builder);
|
||||||
} else {
|
} else {
|
||||||
logger.error("{}", general);
|
logger.warn("{}", general);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -206,9 +206,9 @@ public class LicensesService extends AbstractLifecycleComponent<LicensesService>
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
logger.error("{}", builder.toString());
|
logger.warn("{}", builder.toString());
|
||||||
} else {
|
} else {
|
||||||
logger.error("{}", general);
|
logger.warn("{}", general);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -238,9 +238,9 @@ public class LicensesService extends AbstractLifecycleComponent<LicensesService>
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
logger.error("{}", builder.toString());
|
logger.warn("{}", builder.toString());
|
||||||
} else {
|
} else {
|
||||||
logger.error("{}", general);
|
logger.warn("{}", general);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,7 +5,6 @@
|
||||||
*/
|
*/
|
||||||
package org.elasticsearch.license.plugin.core;
|
package org.elasticsearch.license.plugin.core;
|
||||||
|
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.common.xcontent.ToXContent;
|
import org.elasticsearch.common.xcontent.ToXContent;
|
||||||
import org.elasticsearch.common.xcontent.XContentBuilder;
|
import org.elasticsearch.common.xcontent.XContentBuilder;
|
||||||
import org.elasticsearch.common.xcontent.XContentFactory;
|
import org.elasticsearch.common.xcontent.XContentFactory;
|
||||||
|
@ -15,6 +14,7 @@ import org.elasticsearch.license.core.License;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.nio.ByteBuffer;
|
import java.nio.ByteBuffer;
|
||||||
|
import java.util.Base64;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
|
||||||
import static org.elasticsearch.license.core.CryptUtils.decrypt;
|
import static org.elasticsearch.license.core.CryptUtils.decrypt;
|
||||||
|
@ -39,7 +39,7 @@ public class TrialLicense {
|
||||||
byteBuffer.putInt(-License.VERSION_CURRENT)
|
byteBuffer.putInt(-License.VERSION_CURRENT)
|
||||||
.putInt(encrypt.length)
|
.putInt(encrypt.length)
|
||||||
.put(encrypt);
|
.put(encrypt);
|
||||||
signature = Base64.encodeBytes(bytes);
|
signature = Base64.getEncoder().encodeToString(bytes);
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
throw new IllegalStateException(e);
|
throw new IllegalStateException(e);
|
||||||
}
|
}
|
||||||
|
@ -48,7 +48,7 @@ public class TrialLicense {
|
||||||
|
|
||||||
public static boolean verify(final License license) {
|
public static boolean verify(final License license) {
|
||||||
try {
|
try {
|
||||||
byte[] signatureBytes = Base64.decode(license.signature());
|
byte[] signatureBytes = Base64.getDecoder().decode(license.signature());
|
||||||
ByteBuffer byteBuffer = ByteBuffer.wrap(signatureBytes);
|
ByteBuffer byteBuffer = ByteBuffer.wrap(signatureBytes);
|
||||||
int version = byteBuffer.getInt();
|
int version = byteBuffer.getInt();
|
||||||
int contentLen = byteBuffer.getInt();
|
int contentLen = byteBuffer.getInt();
|
||||||
|
|
|
@ -23,7 +23,7 @@ public class RestDeleteLicenseAction extends BaseRestHandler {
|
||||||
@Inject
|
@Inject
|
||||||
public RestDeleteLicenseAction(Settings settings, RestController controller, Client client) {
|
public RestDeleteLicenseAction(Settings settings, RestController controller, Client client) {
|
||||||
super(settings, client);
|
super(settings, client);
|
||||||
controller.registerHandler(DELETE, "/_license", this);
|
controller.registerHandler(DELETE, "/_xpack/license", this);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -34,7 +34,7 @@ public class RestGetLicenseAction extends BaseRestHandler {
|
||||||
@Inject
|
@Inject
|
||||||
public RestGetLicenseAction(Settings settings, RestController controller, Client client) {
|
public RestGetLicenseAction(Settings settings, RestController controller, Client client) {
|
||||||
super(settings, client);
|
super(settings, client);
|
||||||
controller.registerHandler(GET, "/_license", this);
|
controller.registerHandler(GET, "/_xpack/license", this);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -30,8 +30,8 @@ public class RestPutLicenseAction extends BaseRestHandler {
|
||||||
@Inject
|
@Inject
|
||||||
public RestPutLicenseAction(Settings settings, RestController controller, Client client) {
|
public RestPutLicenseAction(Settings settings, RestController controller, Client client) {
|
||||||
super(settings, client);
|
super(settings, client);
|
||||||
controller.registerHandler(PUT, "/_license", this);
|
controller.registerHandler(PUT, "/_xpack/license", this);
|
||||||
controller.registerHandler(POST, "/_license", this);
|
controller.registerHandler(POST, "/_xpack/license", this);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -5,7 +5,6 @@
|
||||||
*/
|
*/
|
||||||
package org.elasticsearch.license.plugin;
|
package org.elasticsearch.license.plugin;
|
||||||
|
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.common.unit.TimeValue;
|
import org.elasticsearch.common.unit.TimeValue;
|
||||||
import org.elasticsearch.common.xcontent.ToXContent;
|
import org.elasticsearch.common.xcontent.ToXContent;
|
||||||
import org.elasticsearch.common.xcontent.XContentBuilder;
|
import org.elasticsearch.common.xcontent.XContentBuilder;
|
||||||
|
@ -17,6 +16,7 @@ import org.elasticsearch.test.ESTestCase;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.nio.ByteBuffer;
|
import java.nio.ByteBuffer;
|
||||||
|
import java.util.Base64;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
|
@ -102,7 +102,7 @@ public class TrialLicenseTests extends ESTestCase {
|
||||||
byteBuffer.putInt(-spec.version())
|
byteBuffer.putInt(-spec.version())
|
||||||
.putInt(encrypt.length)
|
.putInt(encrypt.length)
|
||||||
.put(encrypt);
|
.put(encrypt);
|
||||||
signature = Base64.encodeBytes(bytes);
|
signature = Base64.getEncoder().encodeToString(bytes);
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
throw new IllegalStateException(e);
|
throw new IllegalStateException(e);
|
||||||
}
|
}
|
||||||
|
|
|
@ -9,7 +9,6 @@ import org.elasticsearch.Version;
|
||||||
import org.elasticsearch.cluster.metadata.MetaData;
|
import org.elasticsearch.cluster.metadata.MetaData;
|
||||||
import org.elasticsearch.cluster.metadata.RepositoriesMetaData;
|
import org.elasticsearch.cluster.metadata.RepositoriesMetaData;
|
||||||
import org.elasticsearch.cluster.metadata.RepositoryMetaData;
|
import org.elasticsearch.cluster.metadata.RepositoryMetaData;
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.common.io.stream.ByteBufferStreamInput;
|
import org.elasticsearch.common.io.stream.ByteBufferStreamInput;
|
||||||
import org.elasticsearch.common.io.stream.BytesStreamOutput;
|
import org.elasticsearch.common.io.stream.BytesStreamOutput;
|
||||||
import org.elasticsearch.common.settings.Settings;
|
import org.elasticsearch.common.settings.Settings;
|
||||||
|
@ -26,6 +25,7 @@ import org.elasticsearch.license.plugin.TestUtils;
|
||||||
import org.elasticsearch.test.ESTestCase;
|
import org.elasticsearch.test.ESTestCase;
|
||||||
|
|
||||||
import java.nio.ByteBuffer;
|
import java.nio.ByteBuffer;
|
||||||
|
import java.util.Base64;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
|
@ -113,7 +113,7 @@ public class LicensesMetaDataSerializationTests extends ESTestCase {
|
||||||
builder.startArray("trial_licenses");
|
builder.startArray("trial_licenses");
|
||||||
XContentBuilder contentBuilder = XContentFactory.contentBuilder(XContentType.JSON);
|
XContentBuilder contentBuilder = XContentFactory.contentBuilder(XContentType.JSON);
|
||||||
trialLicense.toXContent(contentBuilder, new ToXContent.MapParams(Collections.singletonMap(License.LICENSE_SPEC_VIEW_MODE, "true")));
|
trialLicense.toXContent(contentBuilder, new ToXContent.MapParams(Collections.singletonMap(License.LICENSE_SPEC_VIEW_MODE, "true")));
|
||||||
builder.value(Base64.encodeBytes(encrypt(contentBuilder.bytes().toBytes())));
|
builder.value(Base64.getEncoder().encodeToString(encrypt(contentBuilder.bytes().toBytes())));
|
||||||
builder.endArray();
|
builder.endArray();
|
||||||
builder.startArray("signed_licenses");
|
builder.startArray("signed_licenses");
|
||||||
builder.endArray();
|
builder.endArray();
|
||||||
|
@ -143,7 +143,7 @@ public class LicensesMetaDataSerializationTests extends ESTestCase {
|
||||||
builder.startArray("trial_licenses");
|
builder.startArray("trial_licenses");
|
||||||
contentBuilder = XContentFactory.contentBuilder(XContentType.JSON);
|
contentBuilder = XContentFactory.contentBuilder(XContentType.JSON);
|
||||||
trialLicense.toXContent(contentBuilder, new ToXContent.MapParams(Collections.singletonMap(License.LICENSE_SPEC_VIEW_MODE, "true")));
|
trialLicense.toXContent(contentBuilder, new ToXContent.MapParams(Collections.singletonMap(License.LICENSE_SPEC_VIEW_MODE, "true")));
|
||||||
builder.value(Base64.encodeBytes(encrypt(contentBuilder.bytes().toBytes())));
|
builder.value(Base64.getEncoder().encodeToString(encrypt(contentBuilder.bytes().toBytes())));
|
||||||
builder.endArray();
|
builder.endArray();
|
||||||
builder.startArray("signed_licenses");
|
builder.startArray("signed_licenses");
|
||||||
signedLicense.toXContent(builder, ToXContent.EMPTY_PARAMS);
|
signedLicense.toXContent(builder, ToXContent.EMPTY_PARAMS);
|
||||||
|
@ -162,7 +162,7 @@ public class LicensesMetaDataSerializationTests extends ESTestCase {
|
||||||
builder.startArray("trial_licenses");
|
builder.startArray("trial_licenses");
|
||||||
contentBuilder = XContentFactory.contentBuilder(XContentType.JSON);
|
contentBuilder = XContentFactory.contentBuilder(XContentType.JSON);
|
||||||
trialLicense.toXContent(contentBuilder, new ToXContent.MapParams(Collections.singletonMap(License.LICENSE_SPEC_VIEW_MODE, "true")));
|
trialLicense.toXContent(contentBuilder, new ToXContent.MapParams(Collections.singletonMap(License.LICENSE_SPEC_VIEW_MODE, "true")));
|
||||||
builder.value(Base64.encodeBytes(encrypt(contentBuilder.bytes().toBytes())));
|
builder.value(Base64.getEncoder().encodeToString(encrypt(contentBuilder.bytes().toBytes())));
|
||||||
builder.endArray();
|
builder.endArray();
|
||||||
builder.startArray("signed_licenses");
|
builder.startArray("signed_licenses");
|
||||||
signedLicense.toXContent(builder, ToXContent.EMPTY_PARAMS);
|
signedLicense.toXContent(builder, ToXContent.EMPTY_PARAMS);
|
||||||
|
@ -190,7 +190,7 @@ public class LicensesMetaDataSerializationTests extends ESTestCase {
|
||||||
output.writeVInt(1);
|
output.writeVInt(1);
|
||||||
XContentBuilder contentBuilder = XContentFactory.contentBuilder(XContentType.JSON);
|
XContentBuilder contentBuilder = XContentFactory.contentBuilder(XContentType.JSON);
|
||||||
trialLicense.toXContent(contentBuilder, new ToXContent.MapParams(Collections.singletonMap(License.LICENSE_SPEC_VIEW_MODE, "true")));
|
trialLicense.toXContent(contentBuilder, new ToXContent.MapParams(Collections.singletonMap(License.LICENSE_SPEC_VIEW_MODE, "true")));
|
||||||
output.writeString(Base64.encodeBytes(encrypt(contentBuilder.bytes().toBytes())));
|
output.writeString(Base64.getEncoder().encodeToString(encrypt(contentBuilder.bytes().toBytes())));
|
||||||
byte[] bytes = output.bytes().toBytes();
|
byte[] bytes = output.bytes().toBytes();
|
||||||
ByteBufferStreamInput input = new ByteBufferStreamInput(ByteBuffer.wrap(bytes));
|
ByteBufferStreamInput input = new ByteBufferStreamInput(ByteBuffer.wrap(bytes));
|
||||||
|
|
||||||
|
|
|
@ -3,8 +3,8 @@
|
||||||
"documentation": "https://www.elastic.co/guide/en/shield/current/license-management.html",
|
"documentation": "https://www.elastic.co/guide/en/shield/current/license-management.html",
|
||||||
"methods": ["DELETE"],
|
"methods": ["DELETE"],
|
||||||
"url": {
|
"url": {
|
||||||
"path": "/_license",
|
"path": "/_xpack/license",
|
||||||
"paths": ["/_license"],
|
"paths": ["/_xpack/license"],
|
||||||
"parts" : {}
|
"parts" : {}
|
||||||
},
|
},
|
||||||
"body": null
|
"body": null
|
||||||
|
|
|
@ -3,8 +3,8 @@
|
||||||
"documentation": "https://www.elastic.co/guide/en/shield/current/license-management.html",
|
"documentation": "https://www.elastic.co/guide/en/shield/current/license-management.html",
|
||||||
"methods": ["GET"],
|
"methods": ["GET"],
|
||||||
"url": {
|
"url": {
|
||||||
"path": "/_license",
|
"path": "/_xpack/license",
|
||||||
"paths": ["/_license"],
|
"paths": ["/_xpack/license"],
|
||||||
"parts" : {
|
"parts" : {
|
||||||
},
|
},
|
||||||
"params": {
|
"params": {
|
||||||
|
|
|
@ -3,8 +3,8 @@
|
||||||
"documentation": "https://www.elastic.co/guide/en/shield/current/license-management.html",
|
"documentation": "https://www.elastic.co/guide/en/shield/current/license-management.html",
|
||||||
"methods": ["PUT", "POST"],
|
"methods": ["PUT", "POST"],
|
||||||
"url": {
|
"url": {
|
||||||
"path": "/_license",
|
"path": "/_xpack/license",
|
||||||
"paths": ["/_license"],
|
"paths": ["/_xpack/license"],
|
||||||
"parts" : {
|
"parts" : {
|
||||||
},
|
},
|
||||||
"params": {
|
"params": {
|
||||||
|
|
|
@ -9,7 +9,6 @@ import org.elasticsearch.ElasticsearchException;
|
||||||
import org.elasticsearch.ExceptionsHelper;
|
import org.elasticsearch.ExceptionsHelper;
|
||||||
import org.elasticsearch.SpecialPermission;
|
import org.elasticsearch.SpecialPermission;
|
||||||
import org.elasticsearch.Version;
|
import org.elasticsearch.Version;
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.common.Nullable;
|
import org.elasticsearch.common.Nullable;
|
||||||
import org.elasticsearch.common.Strings;
|
import org.elasticsearch.common.Strings;
|
||||||
import org.elasticsearch.common.inject.Inject;
|
import org.elasticsearch.common.inject.Inject;
|
||||||
|
@ -53,6 +52,7 @@ import java.security.AccessController;
|
||||||
import java.security.KeyStore;
|
import java.security.KeyStore;
|
||||||
import java.security.PrivilegedAction;
|
import java.security.PrivilegedAction;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
import java.util.Base64;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
@ -683,7 +683,7 @@ public class HttpExporter extends Exporter {
|
||||||
|
|
||||||
void apply(HttpURLConnection connection) throws UnsupportedEncodingException {
|
void apply(HttpURLConnection connection) throws UnsupportedEncodingException {
|
||||||
String userInfo = username + ":" + (password != null ? new String(password) : "");
|
String userInfo = username + ":" + (password != null ? new String(password) : "");
|
||||||
String basicAuth = "Basic " + Base64.encodeBytes(userInfo.getBytes("ISO-8859-1"));
|
String basicAuth = "Basic " + Base64.getEncoder().encodeToString(userInfo.getBytes("ISO-8859-1"));
|
||||||
connection.setRequestProperty("Authorization", basicAuth);
|
connection.setRequestProperty("Authorization", basicAuth);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -161,7 +161,7 @@ public abstract class AbstractCollectorTestCase extends MarvelIntegTestCase {
|
||||||
public void run() {
|
public void run() {
|
||||||
for (String nodeId : internalCluster().getNodeNames()) {
|
for (String nodeId : internalCluster().getNodeNames()) {
|
||||||
try {
|
try {
|
||||||
assertTrue(waitForNoBlocksOnNode(nodeId));
|
waitForNoBlocksOnNode(nodeId);
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
fail("failed to wait for no blocks on node [" + nodeId + "]: " + e.getMessage());
|
fail("failed to wait for no blocks on node [" + nodeId + "]: " + e.getMessage());
|
||||||
}
|
}
|
||||||
|
@ -170,13 +170,12 @@ public abstract class AbstractCollectorTestCase extends MarvelIntegTestCase {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean waitForNoBlocksOnNode(final String nodeId) throws Exception {
|
public void waitForNoBlocksOnNode(final String nodeId) throws Exception {
|
||||||
return assertBusy(() -> {
|
assertBusy(() -> {
|
||||||
ClusterBlocks clusterBlocks =
|
ClusterBlocks clusterBlocks =
|
||||||
client(nodeId).admin().cluster().prepareState().setLocal(true).execute().actionGet().getState().blocks();
|
client(nodeId).admin().cluster().prepareState().setLocal(true).execute().actionGet().getState().blocks();
|
||||||
assertTrue(clusterBlocks.global().isEmpty());
|
assertTrue(clusterBlocks.global().isEmpty());
|
||||||
assertTrue(clusterBlocks.indices().values().isEmpty());
|
assertTrue(clusterBlocks.indices().values().isEmpty());
|
||||||
return true;
|
|
||||||
}, 30L, TimeUnit.SECONDS);
|
}, 30L, TimeUnit.SECONDS);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -121,7 +121,8 @@ public abstract class AbstractExporterTemplateTestCase extends MarvelIntegTestCa
|
||||||
assertNotNull(exporters);
|
assertNotNull(exporters);
|
||||||
|
|
||||||
// Wait for exporting bulks to be ready to export
|
// Wait for exporting bulks to be ready to export
|
||||||
assertBusy(() -> assertThat(exporters.openBulk(), notNullValue()));
|
Runnable busy = () -> assertThat(exporters.openBulk(), notNullValue());
|
||||||
|
assertBusy(busy);
|
||||||
exporters.export(collector.collect());
|
exporters.export(collector.collect());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -93,7 +93,8 @@ public class HttpExporterTemplateTests extends AbstractExporterTemplateTestCase
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void awaitIndexExists(String index) throws Exception {
|
protected void awaitIndexExists(String index) throws Exception {
|
||||||
assertBusy(() -> assertThat("could not find index " + index, dispatcher.hasIndex(index), is(true)), 10, TimeUnit.SECONDS);
|
Runnable busy = () -> assertThat("could not find index " + index, dispatcher.hasIndex(index), is(true));
|
||||||
|
assertBusy(busy, 10, TimeUnit.SECONDS);
|
||||||
}
|
}
|
||||||
|
|
||||||
class MockServerDispatcher extends Dispatcher {
|
class MockServerDispatcher extends Dispatcher {
|
||||||
|
|
|
@ -7,7 +7,6 @@ package org.elasticsearch.shield.authc;
|
||||||
|
|
||||||
import org.elasticsearch.ElasticsearchSecurityException;
|
import org.elasticsearch.ElasticsearchSecurityException;
|
||||||
import org.elasticsearch.Version;
|
import org.elasticsearch.Version;
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.common.Strings;
|
import org.elasticsearch.common.Strings;
|
||||||
import org.elasticsearch.common.component.AbstractComponent;
|
import org.elasticsearch.common.component.AbstractComponent;
|
||||||
import org.elasticsearch.common.inject.Inject;
|
import org.elasticsearch.common.inject.Inject;
|
||||||
|
@ -29,6 +28,7 @@ import org.elasticsearch.threadpool.ThreadPool;
|
||||||
import org.elasticsearch.transport.TransportMessage;
|
import org.elasticsearch.transport.TransportMessage;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
import java.util.Base64;
|
||||||
|
|
||||||
import static org.elasticsearch.shield.Security.setting;
|
import static org.elasticsearch.shield.Security.setting;
|
||||||
import static org.elasticsearch.shield.support.Exceptions.authenticationError;
|
import static org.elasticsearch.shield.support.Exceptions.authenticationError;
|
||||||
|
@ -157,7 +157,7 @@ public class InternalAuthenticationService extends AbstractComponent implements
|
||||||
|
|
||||||
static User decodeUser(String text) {
|
static User decodeUser(String text) {
|
||||||
try {
|
try {
|
||||||
byte[] bytes = Base64.decode(text);
|
byte[] bytes = Base64.getDecoder().decode(text);
|
||||||
StreamInput input = StreamInput.wrap(bytes);
|
StreamInput input = StreamInput.wrap(bytes);
|
||||||
Version version = Version.readVersion(input);
|
Version version = Version.readVersion(input);
|
||||||
input.setVersion(version);
|
input.setVersion(version);
|
||||||
|
@ -173,7 +173,7 @@ public class InternalAuthenticationService extends AbstractComponent implements
|
||||||
Version.writeVersion(Version.CURRENT, output);
|
Version.writeVersion(Version.CURRENT, output);
|
||||||
User.writeTo(user, output);
|
User.writeTo(user, output);
|
||||||
byte[] bytes = output.bytes().toBytes();
|
byte[] bytes = output.bytes().toBytes();
|
||||||
return Base64.encodeBytes(bytes);
|
return Base64.getEncoder().encodeToString(bytes);
|
||||||
} catch (IOException ioe) {
|
} catch (IOException ioe) {
|
||||||
if (logger != null) {
|
if (logger != null) {
|
||||||
logger.error("could not encode authenticated user in message header... falling back to token headers", ioe);
|
logger.error("could not encode authenticated user in message header... falling back to token headers", ioe);
|
||||||
|
|
|
@ -18,7 +18,7 @@ import org.elasticsearch.shield.support.Exceptions;
|
||||||
import org.elasticsearch.shield.user.AnonymousUser;
|
import org.elasticsearch.shield.user.AnonymousUser;
|
||||||
import org.elasticsearch.shield.user.KibanaUser;
|
import org.elasticsearch.shield.user.KibanaUser;
|
||||||
import org.elasticsearch.shield.user.User;
|
import org.elasticsearch.shield.user.User;
|
||||||
import org.elasticsearch.shield.user.XPackUser;
|
import org.elasticsearch.shield.user.ElasticUser;
|
||||||
|
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
|
@ -86,7 +86,7 @@ public class ReservedRealm extends CachingUsernamePasswordRealm {
|
||||||
public static boolean isReserved(String username) {
|
public static boolean isReserved(String username) {
|
||||||
assert username != null;
|
assert username != null;
|
||||||
switch (username) {
|
switch (username) {
|
||||||
case XPackUser.NAME:
|
case ElasticUser.NAME:
|
||||||
case KibanaUser.NAME:
|
case KibanaUser.NAME:
|
||||||
return true;
|
return true;
|
||||||
default:
|
default:
|
||||||
|
@ -97,8 +97,8 @@ public class ReservedRealm extends CachingUsernamePasswordRealm {
|
||||||
public static User getUser(String username) {
|
public static User getUser(String username) {
|
||||||
assert username != null;
|
assert username != null;
|
||||||
switch (username) {
|
switch (username) {
|
||||||
case XPackUser.NAME:
|
case ElasticUser.NAME:
|
||||||
return XPackUser.INSTANCE;
|
return ElasticUser.INSTANCE;
|
||||||
case KibanaUser.NAME:
|
case KibanaUser.NAME:
|
||||||
return KibanaUser.INSTANCE;
|
return KibanaUser.INSTANCE;
|
||||||
default:
|
default:
|
||||||
|
@ -111,9 +111,9 @@ public class ReservedRealm extends CachingUsernamePasswordRealm {
|
||||||
|
|
||||||
public static Collection<User> users() {
|
public static Collection<User> users() {
|
||||||
if (AnonymousUser.enabled()) {
|
if (AnonymousUser.enabled()) {
|
||||||
return Arrays.asList(XPackUser.INSTANCE, KibanaUser.INSTANCE, AnonymousUser.INSTANCE);
|
return Arrays.asList(ElasticUser.INSTANCE, KibanaUser.INSTANCE, AnonymousUser.INSTANCE);
|
||||||
}
|
}
|
||||||
return Arrays.asList(XPackUser.INSTANCE, KibanaUser.INSTANCE);
|
return Arrays.asList(ElasticUser.INSTANCE, KibanaUser.INSTANCE);
|
||||||
}
|
}
|
||||||
|
|
||||||
private char[] getPasswordHash(final String username) {
|
private char[] getPasswordHash(final String username) {
|
||||||
|
|
|
@ -5,13 +5,12 @@
|
||||||
*/
|
*/
|
||||||
package org.elasticsearch.shield.authc.support;
|
package org.elasticsearch.shield.authc.support;
|
||||||
|
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.common.Randomness;
|
import org.elasticsearch.common.Randomness;
|
||||||
import org.elasticsearch.common.hash.MessageDigests;
|
import org.elasticsearch.common.hash.MessageDigests;
|
||||||
|
|
||||||
import java.nio.charset.StandardCharsets;
|
import java.nio.charset.StandardCharsets;
|
||||||
import java.security.MessageDigest;
|
import java.security.MessageDigest;
|
||||||
import java.security.NoSuchAlgorithmException;
|
import java.util.Base64;
|
||||||
import java.util.Locale;
|
import java.util.Locale;
|
||||||
import java.util.Random;
|
import java.util.Random;
|
||||||
|
|
||||||
|
@ -145,7 +144,7 @@ public enum Hasher {
|
||||||
byte[] textBytes = CharArrays.toUtf8Bytes(text.internalChars());
|
byte[] textBytes = CharArrays.toUtf8Bytes(text.internalChars());
|
||||||
MessageDigest md = MessageDigests.sha1();
|
MessageDigest md = MessageDigests.sha1();
|
||||||
md.update(textBytes);
|
md.update(textBytes);
|
||||||
String hash = Base64.encodeBytes(md.digest());
|
String hash = Base64.getEncoder().encodeToString(md.digest());
|
||||||
return (SHA1_PREFIX + hash).toCharArray();
|
return (SHA1_PREFIX + hash).toCharArray();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -158,7 +157,7 @@ public enum Hasher {
|
||||||
byte[] textBytes = CharArrays.toUtf8Bytes(text.internalChars());
|
byte[] textBytes = CharArrays.toUtf8Bytes(text.internalChars());
|
||||||
MessageDigest md = MessageDigests.sha1();
|
MessageDigest md = MessageDigests.sha1();
|
||||||
md.update(textBytes);
|
md.update(textBytes);
|
||||||
String passwd64 = Base64.encodeBytes(md.digest());
|
String passwd64 = Base64.getEncoder().encodeToString(md.digest());
|
||||||
String hashNoPrefix = hashStr.substring(SHA1_PREFIX.length());
|
String hashNoPrefix = hashStr.substring(SHA1_PREFIX.length());
|
||||||
return SecuredString.constantTimeEquals(hashNoPrefix, passwd64);
|
return SecuredString.constantTimeEquals(hashNoPrefix, passwd64);
|
||||||
}
|
}
|
||||||
|
@ -169,7 +168,7 @@ public enum Hasher {
|
||||||
public char[] hash(SecuredString text) {
|
public char[] hash(SecuredString text) {
|
||||||
MessageDigest md = MessageDigests.md5();
|
MessageDigest md = MessageDigests.md5();
|
||||||
md.update(CharArrays.toUtf8Bytes(text.internalChars()));
|
md.update(CharArrays.toUtf8Bytes(text.internalChars()));
|
||||||
String hash = Base64.encodeBytes(md.digest());
|
String hash = Base64.getEncoder().encodeToString(md.digest());
|
||||||
return (MD5_PREFIX + hash).toCharArray();
|
return (MD5_PREFIX + hash).toCharArray();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -182,7 +181,7 @@ public enum Hasher {
|
||||||
hashStr = hashStr.substring(MD5_PREFIX.length());
|
hashStr = hashStr.substring(MD5_PREFIX.length());
|
||||||
MessageDigest md = MessageDigests.md5();
|
MessageDigest md = MessageDigests.md5();
|
||||||
md.update(CharArrays.toUtf8Bytes(text.internalChars()));
|
md.update(CharArrays.toUtf8Bytes(text.internalChars()));
|
||||||
String computedHashStr = Base64.encodeBytes(md.digest());
|
String computedHashStr = Base64.getEncoder().encodeToString(md.digest());
|
||||||
return SecuredString.constantTimeEquals(hashStr, computedHashStr);
|
return SecuredString.constantTimeEquals(hashStr, computedHashStr);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
@ -194,7 +193,7 @@ public enum Hasher {
|
||||||
md.update(CharArrays.toUtf8Bytes(text.internalChars()));
|
md.update(CharArrays.toUtf8Bytes(text.internalChars()));
|
||||||
char[] salt = SaltProvider.salt(8);
|
char[] salt = SaltProvider.salt(8);
|
||||||
md.update(CharArrays.toUtf8Bytes(salt));
|
md.update(CharArrays.toUtf8Bytes(salt));
|
||||||
String hash = Base64.encodeBytes(md.digest());
|
String hash = Base64.getEncoder().encodeToString(md.digest());
|
||||||
char[] result = new char[SSHA256_PREFIX.length() + salt.length + hash.length()];
|
char[] result = new char[SSHA256_PREFIX.length() + salt.length + hash.length()];
|
||||||
System.arraycopy(SSHA256_PREFIX.toCharArray(), 0, result, 0, SSHA256_PREFIX.length());
|
System.arraycopy(SSHA256_PREFIX.toCharArray(), 0, result, 0, SSHA256_PREFIX.length());
|
||||||
System.arraycopy(salt, 0, result, SSHA256_PREFIX.length(), salt.length);
|
System.arraycopy(salt, 0, result, SSHA256_PREFIX.length(), salt.length);
|
||||||
|
@ -213,7 +212,7 @@ public enum Hasher {
|
||||||
MessageDigest md = MessageDigests.sha256();
|
MessageDigest md = MessageDigests.sha256();
|
||||||
md.update(CharArrays.toUtf8Bytes(text.internalChars()));
|
md.update(CharArrays.toUtf8Bytes(text.internalChars()));
|
||||||
md.update(new String(saltAndHash, 0, 8).getBytes(StandardCharsets.UTF_8));
|
md.update(new String(saltAndHash, 0, 8).getBytes(StandardCharsets.UTF_8));
|
||||||
String computedHash = Base64.encodeBytes(md.digest());
|
String computedHash = Base64.getEncoder().encodeToString(md.digest());
|
||||||
return SecuredString.constantTimeEquals(computedHash, new String(saltAndHash, 8, saltAndHash.length - 8));
|
return SecuredString.constantTimeEquals(computedHash, new String(saltAndHash, 8, saltAndHash.length - 8));
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
|
@ -5,13 +5,12 @@
|
||||||
*/
|
*/
|
||||||
package org.elasticsearch.shield.authc.support;
|
package org.elasticsearch.shield.authc.support;
|
||||||
|
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.common.util.concurrent.ThreadContext;
|
import org.elasticsearch.common.util.concurrent.ThreadContext;
|
||||||
import org.elasticsearch.shield.authc.AuthenticationToken;
|
import org.elasticsearch.shield.authc.AuthenticationToken;
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.nio.CharBuffer;
|
import java.nio.CharBuffer;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
import java.util.Base64;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
|
|
||||||
import static org.elasticsearch.shield.support.Exceptions.authenticationError;
|
import static org.elasticsearch.shield.support.Exceptions.authenticationError;
|
||||||
|
@ -85,8 +84,8 @@ public class UsernamePasswordToken implements AuthenticationToken {
|
||||||
|
|
||||||
char[] userpasswd;
|
char[] userpasswd;
|
||||||
try {
|
try {
|
||||||
userpasswd = CharArrays.utf8BytesToChars(Base64.decode(headerValue.substring(BASIC_AUTH_PREFIX.length()).trim()));
|
userpasswd = CharArrays.utf8BytesToChars(Base64.getDecoder().decode(headerValue.substring(BASIC_AUTH_PREFIX.length()).trim()));
|
||||||
} catch (IllegalArgumentException | IOException e) {
|
} catch (IllegalArgumentException e) {
|
||||||
throw authenticationError("invalid basic authentication header encoding", e);
|
throw authenticationError("invalid basic authentication header encoding", e);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -109,7 +108,7 @@ public class UsernamePasswordToken implements AuthenticationToken {
|
||||||
chars.put(username).put(':').put(passwd.internalChars());
|
chars.put(username).put(':').put(passwd.internalChars());
|
||||||
|
|
||||||
//TODO we still have passwords in Strings in headers
|
//TODO we still have passwords in Strings in headers
|
||||||
String basicToken = Base64.encodeBytes(CharArrays.toUtf8Bytes(chars.array()));
|
String basicToken = Base64.getEncoder().encodeToString(CharArrays.toUtf8Bytes(chars.array()));
|
||||||
return "Basic " + basicToken;
|
return "Basic " + basicToken;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -17,7 +17,7 @@ public class KibanaRole extends Role {
|
||||||
|
|
||||||
private static final String[] CLUSTER_PRIVILEGES = new String[] { "monitor", MonitoringBulkAction.NAME};
|
private static final String[] CLUSTER_PRIVILEGES = new String[] { "monitor", MonitoringBulkAction.NAME};
|
||||||
private static final RoleDescriptor.IndicesPrivileges[] INDICES_PRIVILEGES = new RoleDescriptor.IndicesPrivileges[] {
|
private static final RoleDescriptor.IndicesPrivileges[] INDICES_PRIVILEGES = new RoleDescriptor.IndicesPrivileges[] {
|
||||||
RoleDescriptor.IndicesPrivileges.builder().indices(".kibana").privileges("all").build() };
|
RoleDescriptor.IndicesPrivileges.builder().indices(".kibana*", ".reporting-*").privileges("all").build() };
|
||||||
|
|
||||||
public static final String NAME = "kibana";
|
public static final String NAME = "kibana";
|
||||||
public static final RoleDescriptor DESCRIPTOR = new RoleDescriptor(NAME, CLUSTER_PRIVILEGES, INDICES_PRIVILEGES, null);
|
public static final RoleDescriptor DESCRIPTOR = new RoleDescriptor(NAME, CLUSTER_PRIVILEGES, INDICES_PRIVILEGES, null);
|
||||||
|
|
|
@ -6,7 +6,6 @@
|
||||||
package org.elasticsearch.shield.crypto;
|
package org.elasticsearch.shield.crypto;
|
||||||
|
|
||||||
import org.elasticsearch.ElasticsearchException;
|
import org.elasticsearch.ElasticsearchException;
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.common.Nullable;
|
import org.elasticsearch.common.Nullable;
|
||||||
import org.elasticsearch.common.component.AbstractLifecycleComponent;
|
import org.elasticsearch.common.component.AbstractLifecycleComponent;
|
||||||
import org.elasticsearch.common.inject.Inject;
|
import org.elasticsearch.common.inject.Inject;
|
||||||
|
@ -39,6 +38,7 @@ import java.security.MessageDigest;
|
||||||
import java.security.NoSuchAlgorithmException;
|
import java.security.NoSuchAlgorithmException;
|
||||||
import java.security.SecureRandom;
|
import java.security.SecureRandom;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
import java.util.Base64;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
|
@ -138,11 +138,7 @@ public class InternalCryptoService extends AbstractLifecycleComponent<InternalCr
|
||||||
keyFile = resolveSystemKey(settings, env);
|
keyFile = resolveSystemKey(settings, env);
|
||||||
systemKey = readSystemKey(keyFile);
|
systemKey = readSystemKey(keyFile);
|
||||||
randomKey = generateSecretKey(RANDOM_KEY_SIZE);
|
randomKey = generateSecretKey(RANDOM_KEY_SIZE);
|
||||||
try {
|
randomKeyBase64 = Base64.getUrlEncoder().encodeToString(randomKey.getEncoded());
|
||||||
randomKeyBase64 = Base64.encodeBytes(randomKey.getEncoded(), 0, randomKey.getEncoded().length, Base64.URL_SAFE);
|
|
||||||
} catch (IOException e) {
|
|
||||||
throw new ElasticsearchException("failed to encode key data as base64", e);
|
|
||||||
}
|
|
||||||
|
|
||||||
signingKey = createSigningKey(systemKey, randomKey);
|
signingKey = createSigningKey(systemKey, randomKey);
|
||||||
|
|
||||||
|
@ -256,17 +252,17 @@ public class InternalCryptoService extends AbstractLifecycleComponent<InternalCr
|
||||||
} else {
|
} else {
|
||||||
byte[] randomKeyBytes;
|
byte[] randomKeyBytes;
|
||||||
try {
|
try {
|
||||||
randomKeyBytes = Base64.decode(base64RandomKey, Base64.URL_SAFE);
|
randomKeyBytes = Base64.getUrlDecoder().decode(base64RandomKey);
|
||||||
if (randomKeyBytes.length * 8 != RANDOM_KEY_SIZE) {
|
} catch (IllegalArgumentException e) {
|
||||||
logger.debug("incorrect random key data length. received [{}] bytes", randomKeyBytes.length);
|
|
||||||
throw new IllegalArgumentException("tampered signed text");
|
|
||||||
}
|
|
||||||
SecretKey randomKey = new SecretKeySpec(randomKeyBytes, KEY_ALGO);
|
|
||||||
signingKey = createSigningKey(systemKey, randomKey);
|
|
||||||
} catch (IOException e) {
|
|
||||||
logger.error("error occurred while decoding key data", e);
|
logger.error("error occurred while decoding key data", e);
|
||||||
throw new IllegalStateException("error while verifying the signed text");
|
throw new IllegalStateException("error while verifying the signed text");
|
||||||
}
|
}
|
||||||
|
if (randomKeyBytes.length * 8 != RANDOM_KEY_SIZE) {
|
||||||
|
logger.debug("incorrect random key data length. received [{}] bytes", randomKeyBytes.length);
|
||||||
|
throw new IllegalArgumentException("tampered signed text");
|
||||||
|
}
|
||||||
|
SecretKey randomKey = new SecretKeySpec(randomKeyBytes, KEY_ALGO);
|
||||||
|
signingKey = createSigningKey(systemKey, randomKey);
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
@ -297,7 +293,7 @@ public class InternalCryptoService extends AbstractLifecycleComponent<InternalCr
|
||||||
}
|
}
|
||||||
|
|
||||||
byte[] charBytes = CharArrays.toUtf8Bytes(chars);
|
byte[] charBytes = CharArrays.toUtf8Bytes(chars);
|
||||||
String base64 = Base64.encodeBytes(encryptInternal(charBytes, key));
|
String base64 = Base64.getEncoder().encodeToString(encryptInternal(charBytes, key));
|
||||||
return ENCRYPTED_TEXT_PREFIX.concat(base64).toCharArray();
|
return ENCRYPTED_TEXT_PREFIX.concat(base64).toCharArray();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -335,8 +331,8 @@ public class InternalCryptoService extends AbstractLifecycleComponent<InternalCr
|
||||||
String encrypted = new String(chars, ENCRYPTED_TEXT_PREFIX.length(), chars.length - ENCRYPTED_TEXT_PREFIX.length());
|
String encrypted = new String(chars, ENCRYPTED_TEXT_PREFIX.length(), chars.length - ENCRYPTED_TEXT_PREFIX.length());
|
||||||
byte[] bytes;
|
byte[] bytes;
|
||||||
try {
|
try {
|
||||||
bytes = Base64.decode(encrypted);
|
bytes = Base64.getDecoder().decode(encrypted);
|
||||||
} catch (IOException e) {
|
} catch (IllegalArgumentException e) {
|
||||||
throw new ElasticsearchException("unable to decode encrypted data", e);
|
throw new ElasticsearchException("unable to decode encrypted data", e);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -430,7 +426,7 @@ public class InternalCryptoService extends AbstractLifecycleComponent<InternalCr
|
||||||
private static String signInternal(String text, SecretKey key) throws IOException {
|
private static String signInternal(String text, SecretKey key) throws IOException {
|
||||||
Mac mac = createMac(key);
|
Mac mac = createMac(key);
|
||||||
byte[] sig = mac.doFinal(text.getBytes(StandardCharsets.UTF_8));
|
byte[] sig = mac.doFinal(text.getBytes(StandardCharsets.UTF_8));
|
||||||
return Base64.encodeBytes(sig, 0, sig.length, Base64.URL_SAFE);
|
return Base64.getUrlEncoder().encodeToString(sig);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -25,7 +25,7 @@ import static org.elasticsearch.shield.Security.setting;
|
||||||
*/
|
*/
|
||||||
public class AnonymousUser extends ReservedUser {
|
public class AnonymousUser extends ReservedUser {
|
||||||
|
|
||||||
public static final String DEFAULT_ANONYMOUS_USERNAME = "_es_anonymous_user";
|
public static final String DEFAULT_ANONYMOUS_USERNAME = "_anonymous";
|
||||||
public static final Setting<String> USERNAME_SETTING =
|
public static final Setting<String> USERNAME_SETTING =
|
||||||
new Setting<>(setting("authc.anonymous.username"), DEFAULT_ANONYMOUS_USERNAME, s -> s, Property.NodeScope);
|
new Setting<>(setting("authc.anonymous.username"), DEFAULT_ANONYMOUS_USERNAME, s -> s, Property.NodeScope);
|
||||||
public static final Setting<List<String>> ROLES_SETTING =
|
public static final Setting<List<String>> ROLES_SETTING =
|
||||||
|
|
|
@ -0,0 +1,42 @@
|
||||||
|
/*
|
||||||
|
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||||
|
* or more contributor license agreements. Licensed under the Elastic License;
|
||||||
|
* you may not use this file except in compliance with the Elastic License.
|
||||||
|
*/
|
||||||
|
package org.elasticsearch.shield.user;
|
||||||
|
|
||||||
|
import org.elasticsearch.shield.authz.permission.SuperuserRole;
|
||||||
|
import org.elasticsearch.shield.user.User.ReservedUser;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The reserved {@code elastic} superuser. As full permission/access to the cluster/indices and can
|
||||||
|
* run as any other user.
|
||||||
|
*/
|
||||||
|
public class ElasticUser extends ReservedUser {
|
||||||
|
|
||||||
|
public static final String NAME = "elastic";
|
||||||
|
public static final String ROLE_NAME = SuperuserRole.NAME;
|
||||||
|
public static final ElasticUser INSTANCE = new ElasticUser();
|
||||||
|
|
||||||
|
private ElasticUser() {
|
||||||
|
super(NAME, ROLE_NAME);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean equals(Object o) {
|
||||||
|
return INSTANCE == o;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int hashCode() {
|
||||||
|
return System.identityHashCode(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static boolean is(User user) {
|
||||||
|
return INSTANCE.equals(user);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static boolean is(String principal) {
|
||||||
|
return NAME.equals(principal);
|
||||||
|
}
|
||||||
|
}
|
|
@ -16,8 +16,8 @@ import java.util.function.Predicate;
|
||||||
*/
|
*/
|
||||||
public class SystemUser extends User {
|
public class SystemUser extends User {
|
||||||
|
|
||||||
public static final String NAME = "__es_system_user";
|
public static final String NAME = "_system";
|
||||||
public static final String ROLE_NAME = "__es_system_role";
|
public static final String ROLE_NAME = "_system";
|
||||||
|
|
||||||
public static final User INSTANCE = new SystemUser();
|
public static final User INSTANCE = new SystemUser();
|
||||||
|
|
||||||
|
@ -41,6 +41,10 @@ public class SystemUser extends User {
|
||||||
return INSTANCE.equals(user);
|
return INSTANCE.equals(user);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static boolean is(String principal) {
|
||||||
|
return NAME.equals(principal);
|
||||||
|
}
|
||||||
|
|
||||||
public static boolean isAuthorized(String action) {
|
public static boolean isAuthorized(String action) {
|
||||||
return PREDICATE.test(action);
|
return PREDICATE.test(action);
|
||||||
}
|
}
|
||||||
|
|
|
@ -187,12 +187,14 @@ public class User implements ToXContent {
|
||||||
public static User readFrom(StreamInput input) throws IOException {
|
public static User readFrom(StreamInput input) throws IOException {
|
||||||
if (input.readBoolean()) {
|
if (input.readBoolean()) {
|
||||||
String name = input.readString();
|
String name = input.readString();
|
||||||
if (SystemUser.NAME.equals(name)) {
|
if (SystemUser.is(name)) {
|
||||||
return SystemUser.INSTANCE;
|
return SystemUser.INSTANCE;
|
||||||
|
} else if (XPackUser.is(name)) {
|
||||||
|
return XPackUser.INSTANCE;
|
||||||
}
|
}
|
||||||
User user = ReservedRealm.getUser(name);
|
User user = ReservedRealm.getUser(name);
|
||||||
if (user == null) {
|
if (user == null) {
|
||||||
throw new IllegalStateException("invalid internal user");
|
throw new IllegalStateException("invalid reserved user");
|
||||||
}
|
}
|
||||||
return user;
|
return user;
|
||||||
}
|
}
|
||||||
|
@ -217,6 +219,9 @@ public class User implements ToXContent {
|
||||||
if (SystemUser.is(user)) {
|
if (SystemUser.is(user)) {
|
||||||
output.writeBoolean(true);
|
output.writeBoolean(true);
|
||||||
output.writeString(SystemUser.NAME);
|
output.writeString(SystemUser.NAME);
|
||||||
|
} else if (XPackUser.is(user)) {
|
||||||
|
output.writeBoolean(true);
|
||||||
|
output.writeString(XPackUser.NAME);
|
||||||
} else if (ReservedRealm.isReserved(user.principal())) {
|
} else if (ReservedRealm.isReserved(user.principal())) {
|
||||||
output.writeBoolean(true);
|
output.writeBoolean(true);
|
||||||
output.writeString(user.principal());
|
output.writeString(user.principal());
|
||||||
|
|
|
@ -12,9 +12,9 @@ import org.elasticsearch.shield.user.User.ReservedUser;
|
||||||
* XPack internal user that manages xpack. Has all cluster/indices permissions for watcher,
|
* XPack internal user that manages xpack. Has all cluster/indices permissions for watcher,
|
||||||
* shield and monitoring to operate.
|
* shield and monitoring to operate.
|
||||||
*/
|
*/
|
||||||
public class XPackUser extends ReservedUser {
|
public class XPackUser extends User {
|
||||||
|
|
||||||
public static final String NAME = "elastic";
|
public static final String NAME = "_xpack";
|
||||||
public static final String ROLE_NAME = SuperuserRole.NAME;
|
public static final String ROLE_NAME = SuperuserRole.NAME;
|
||||||
public static final XPackUser INSTANCE = new XPackUser();
|
public static final XPackUser INSTANCE = new XPackUser();
|
||||||
|
|
||||||
|
|
|
@ -9,8 +9,6 @@ import org.apache.lucene.search.join.ScoreMode;
|
||||||
import org.elasticsearch.ElasticsearchSecurityException;
|
import org.elasticsearch.ElasticsearchSecurityException;
|
||||||
import org.elasticsearch.action.get.GetResponse;
|
import org.elasticsearch.action.get.GetResponse;
|
||||||
import org.elasticsearch.action.get.MultiGetResponse;
|
import org.elasticsearch.action.get.MultiGetResponse;
|
||||||
import org.elasticsearch.action.percolate.PercolateResponse;
|
|
||||||
import org.elasticsearch.action.percolate.PercolateSourceBuilder;
|
|
||||||
import org.elasticsearch.action.search.SearchResponse;
|
import org.elasticsearch.action.search.SearchResponse;
|
||||||
import org.elasticsearch.action.termvectors.MultiTermVectorsResponse;
|
import org.elasticsearch.action.termvectors.MultiTermVectorsResponse;
|
||||||
import org.elasticsearch.action.termvectors.TermVectorsRequest;
|
import org.elasticsearch.action.termvectors.TermVectorsRequest;
|
||||||
|
@ -605,86 +603,6 @@ public class DocumentLevelSecurityTests extends ShieldIntegTestCase {
|
||||||
assertThat(searchResponse.getHits().getAt(1).id(), equalTo("c2"));
|
assertThat(searchResponse.getHits().getAt(1).id(), equalTo("c2"));
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testPercolateApi() {
|
|
||||||
assertAcked(client().admin().indices().prepareCreate("test")
|
|
||||||
.addMapping("query", "query", "type=percolator", "field1", "type=text", "field2", "type=text", "field3", "type=text")
|
|
||||||
);
|
|
||||||
client().prepareIndex("test", "query", "1")
|
|
||||||
.setSource("{\"query\" : { \"match_all\" : {} }, \"field1\" : \"value1\"}")
|
|
||||||
.setRefresh(true)
|
|
||||||
.get();
|
|
||||||
|
|
||||||
// Percolator without a query just evaluates all percolator queries that are loaded, so we have a match:
|
|
||||||
PercolateResponse response = client()
|
|
||||||
.filterWithHeader(Collections.singletonMap(BASIC_AUTH_HEADER, basicAuthHeaderValue("user1", USERS_PASSWD)))
|
|
||||||
.preparePercolate()
|
|
||||||
.setDocumentType("query")
|
|
||||||
.setPercolateDoc(new PercolateSourceBuilder.DocBuilder().setDoc("{}"))
|
|
||||||
.get();
|
|
||||||
assertThat(response.getCount(), equalTo(1L));
|
|
||||||
assertThat(response.getMatches()[0].getId().string(), equalTo("1"));
|
|
||||||
|
|
||||||
response = client()
|
|
||||||
.filterWithHeader(Collections.singletonMap(BASIC_AUTH_HEADER, basicAuthHeaderValue("user2", USERS_PASSWD)))
|
|
||||||
.preparePercolate()
|
|
||||||
.setDocumentType("query")
|
|
||||||
.setPercolateDoc(new PercolateSourceBuilder.DocBuilder().setDoc("{}"))
|
|
||||||
.get();
|
|
||||||
assertThat(response.getCount(), equalTo(0L));
|
|
||||||
|
|
||||||
response = client()
|
|
||||||
.filterWithHeader(Collections.singletonMap(BASIC_AUTH_HEADER, basicAuthHeaderValue("user3", USERS_PASSWD)))
|
|
||||||
.preparePercolate()
|
|
||||||
.setDocumentType("query")
|
|
||||||
.setPercolateDoc(new PercolateSourceBuilder.DocBuilder().setDoc("{}"))
|
|
||||||
.get();
|
|
||||||
assertThat(response.getCount(), equalTo(1L));
|
|
||||||
assertThat(response.getMatches()[0].getId().string(), equalTo("1"));
|
|
||||||
|
|
||||||
// Percolator with a query on a document that the current user can see. Percolator will have one query to evaluate, so there is a
|
|
||||||
// match:
|
|
||||||
response = client().filterWithHeader(Collections.singletonMap(BASIC_AUTH_HEADER, basicAuthHeaderValue("user1", USERS_PASSWD)))
|
|
||||||
.preparePercolate()
|
|
||||||
.setDocumentType("query")
|
|
||||||
.setPercolateQuery(termQuery("field1", "value1"))
|
|
||||||
.setPercolateDoc(new PercolateSourceBuilder.DocBuilder().setDoc("{}"))
|
|
||||||
.get();
|
|
||||||
assertThat(response.getCount(), equalTo(1L));
|
|
||||||
assertThat(response.getMatches()[0].getId().string(), equalTo("1"));
|
|
||||||
|
|
||||||
// Percolator with a query on a document that the current user can't see. Percolator will not have queries to evaluate, so there
|
|
||||||
// is no match:
|
|
||||||
response = client().filterWithHeader(Collections.singletonMap(BASIC_AUTH_HEADER, basicAuthHeaderValue("user2", USERS_PASSWD)))
|
|
||||||
.preparePercolate()
|
|
||||||
.setDocumentType("query")
|
|
||||||
.setPercolateQuery(termQuery("field1", "value1"))
|
|
||||||
.setPercolateDoc(new PercolateSourceBuilder.DocBuilder().setDoc("{}"))
|
|
||||||
.get();
|
|
||||||
assertThat(response.getCount(), equalTo(0L));
|
|
||||||
|
|
||||||
response = client().filterWithHeader(Collections.singletonMap(BASIC_AUTH_HEADER, basicAuthHeaderValue("user3", USERS_PASSWD)))
|
|
||||||
.preparePercolate()
|
|
||||||
.setDocumentType("query")
|
|
||||||
.setPercolateQuery(termQuery("field1", "value1"))
|
|
||||||
.setPercolateDoc(new PercolateSourceBuilder.DocBuilder().setDoc("{}"))
|
|
||||||
.get();
|
|
||||||
assertThat(response.getCount(), equalTo(1L));
|
|
||||||
assertThat(response.getMatches()[0].getId().string(), equalTo("1"));
|
|
||||||
|
|
||||||
assertAcked(client().admin().indices().prepareClose("test"));
|
|
||||||
assertAcked(client().admin().indices().prepareOpen("test"));
|
|
||||||
ensureGreen("test");
|
|
||||||
|
|
||||||
// Ensure that the query loading that happens at startup has permissions to load the percolator queries:
|
|
||||||
response = client().filterWithHeader(Collections.singletonMap(BASIC_AUTH_HEADER, basicAuthHeaderValue("user1", USERS_PASSWD)))
|
|
||||||
.preparePercolate()
|
|
||||||
.setDocumentType("query")
|
|
||||||
.setPercolateDoc(new PercolateSourceBuilder.DocBuilder().setDoc("{}"))
|
|
||||||
.get();
|
|
||||||
assertThat(response.getCount(), equalTo(1L));
|
|
||||||
assertThat(response.getMatches()[0].getId().string(), equalTo("1"));
|
|
||||||
}
|
|
||||||
|
|
||||||
public void testScroll() throws Exception {
|
public void testScroll() throws Exception {
|
||||||
assertAcked(client().admin().indices().prepareCreate("test")
|
assertAcked(client().admin().indices().prepareCreate("test")
|
||||||
.setSettings(Settings.builder().put(IndicesRequestCache.INDEX_CACHE_REQUEST_ENABLED_SETTING.getKey(), true))
|
.setSettings(Settings.builder().put(IndicesRequestCache.INDEX_CACHE_REQUEST_ENABLED_SETTING.getKey(), true))
|
||||||
|
|
|
@ -10,8 +10,6 @@ import org.elasticsearch.ElasticsearchSecurityException;
|
||||||
import org.elasticsearch.action.fieldstats.FieldStatsResponse;
|
import org.elasticsearch.action.fieldstats.FieldStatsResponse;
|
||||||
import org.elasticsearch.action.get.GetResponse;
|
import org.elasticsearch.action.get.GetResponse;
|
||||||
import org.elasticsearch.action.get.MultiGetResponse;
|
import org.elasticsearch.action.get.MultiGetResponse;
|
||||||
import org.elasticsearch.action.percolate.PercolateResponse;
|
|
||||||
import org.elasticsearch.action.percolate.PercolateSourceBuilder;
|
|
||||||
import org.elasticsearch.action.search.SearchResponse;
|
import org.elasticsearch.action.search.SearchResponse;
|
||||||
import org.elasticsearch.action.termvectors.MultiTermVectorsResponse;
|
import org.elasticsearch.action.termvectors.MultiTermVectorsResponse;
|
||||||
import org.elasticsearch.action.termvectors.TermVectorsRequest;
|
import org.elasticsearch.action.termvectors.TermVectorsRequest;
|
||||||
|
@ -1122,49 +1120,6 @@ public class FieldLevelSecurityTests extends ShieldIntegTestCase {
|
||||||
assertThat(response.getResponses()[0].getResponse().getFields().terms("field2").size(), equalTo(1L));
|
assertThat(response.getResponses()[0].getResponse().getFields().terms("field2").size(), equalTo(1L));
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testPercolateApi() {
|
|
||||||
assertAcked(client().admin().indices().prepareCreate("test")
|
|
||||||
.addMapping("query", "query", "type=percolator", "field1", "type=text", "field2", "type=text")
|
|
||||||
);
|
|
||||||
client().prepareIndex("test", "query", "1")
|
|
||||||
.setSource("{\"query\" : { \"match_all\" : {} }, \"field1\" : \"value1\"}")
|
|
||||||
.setRefresh(true)
|
|
||||||
.get();
|
|
||||||
|
|
||||||
// Percolator without a query just evaluates all percolator queries that are loaded, so we have a match:
|
|
||||||
PercolateResponse response = client()
|
|
||||||
.filterWithHeader(Collections.singletonMap(BASIC_AUTH_HEADER, basicAuthHeaderValue("user2", USERS_PASSWD)))
|
|
||||||
.preparePercolate()
|
|
||||||
.setDocumentType("query")
|
|
||||||
.setPercolateDoc(new PercolateSourceBuilder.DocBuilder().setDoc("{}"))
|
|
||||||
.get();
|
|
||||||
assertThat(response.getCount(), equalTo(1L));
|
|
||||||
assertThat(response.getMatches()[0].getId().string(), equalTo("1"));
|
|
||||||
|
|
||||||
// Percolator with a query on a field that the current user can't see. Percolator will not have queries to evaluate, so there is
|
|
||||||
// no match:
|
|
||||||
response = client().filterWithHeader(Collections.singletonMap(BASIC_AUTH_HEADER, basicAuthHeaderValue("user2", USERS_PASSWD)))
|
|
||||||
.preparePercolate()
|
|
||||||
.setDocumentType("query")
|
|
||||||
.setPercolateQuery(termQuery("field1", "value1"))
|
|
||||||
.setPercolateDoc(new PercolateSourceBuilder.DocBuilder().setDoc("{}"))
|
|
||||||
.get();
|
|
||||||
assertThat(response.getCount(), equalTo(0L));
|
|
||||||
|
|
||||||
assertAcked(client().admin().indices().prepareClose("test"));
|
|
||||||
assertAcked(client().admin().indices().prepareOpen("test"));
|
|
||||||
ensureGreen("test");
|
|
||||||
|
|
||||||
// Ensure that the query loading that happens at startup has permissions to load the percolator queries:
|
|
||||||
response = client().filterWithHeader(Collections.singletonMap(BASIC_AUTH_HEADER, basicAuthHeaderValue("user2", USERS_PASSWD)))
|
|
||||||
.preparePercolate()
|
|
||||||
.setDocumentType("query")
|
|
||||||
.setPercolateDoc(new PercolateSourceBuilder.DocBuilder().setDoc("{}"))
|
|
||||||
.get();
|
|
||||||
assertThat(response.getCount(), equalTo(1L));
|
|
||||||
assertThat(response.getMatches()[0].getId().string(), equalTo("1"));
|
|
||||||
}
|
|
||||||
|
|
||||||
public void testParentChild() {
|
public void testParentChild() {
|
||||||
assertAcked(prepareCreate("test")
|
assertAcked(prepareCreate("test")
|
||||||
.addMapping("parent")
|
.addMapping("parent")
|
||||||
|
|
|
@ -11,10 +11,10 @@ import org.elasticsearch.action.support.ActionFilters;
|
||||||
import org.elasticsearch.cluster.metadata.IndexNameExpressionResolver;
|
import org.elasticsearch.cluster.metadata.IndexNameExpressionResolver;
|
||||||
import org.elasticsearch.common.settings.Settings;
|
import org.elasticsearch.common.settings.Settings;
|
||||||
import org.elasticsearch.shield.SecurityContext;
|
import org.elasticsearch.shield.SecurityContext;
|
||||||
|
import org.elasticsearch.shield.user.ElasticUser;
|
||||||
import org.elasticsearch.shield.user.KibanaUser;
|
import org.elasticsearch.shield.user.KibanaUser;
|
||||||
import org.elasticsearch.shield.user.SystemUser;
|
import org.elasticsearch.shield.user.SystemUser;
|
||||||
import org.elasticsearch.shield.user.User;
|
import org.elasticsearch.shield.user.User;
|
||||||
import org.elasticsearch.shield.user.XPackUser;
|
|
||||||
import org.elasticsearch.test.ESTestCase;
|
import org.elasticsearch.test.ESTestCase;
|
||||||
import org.elasticsearch.threadpool.ThreadPool;
|
import org.elasticsearch.threadpool.ThreadPool;
|
||||||
import org.elasticsearch.transport.TransportService;
|
import org.elasticsearch.transport.TransportService;
|
||||||
|
@ -83,7 +83,7 @@ public class TransportAuthenticateActionTests extends ESTestCase {
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testValidUser() {
|
public void testValidUser() {
|
||||||
final User user = randomFrom(XPackUser.INSTANCE, KibanaUser.INSTANCE, new User("joe"));
|
final User user = randomFrom(ElasticUser.INSTANCE, KibanaUser.INSTANCE, new User("joe"));
|
||||||
SecurityContext securityContext = mock(SecurityContext.class);
|
SecurityContext securityContext = mock(SecurityContext.class);
|
||||||
when(securityContext.getUser()).thenReturn(user);
|
when(securityContext.getUser()).thenReturn(user);
|
||||||
TransportAuthenticateAction action = new TransportAuthenticateAction(Settings.EMPTY, mock(ThreadPool.class),
|
TransportAuthenticateAction action = new TransportAuthenticateAction(Settings.EMPTY, mock(ThreadPool.class),
|
||||||
|
|
|
@ -14,10 +14,10 @@ import org.elasticsearch.shield.authc.esnative.NativeUsersStore;
|
||||||
import org.elasticsearch.shield.authc.support.Hasher;
|
import org.elasticsearch.shield.authc.support.Hasher;
|
||||||
import org.elasticsearch.shield.authc.support.SecuredString;
|
import org.elasticsearch.shield.authc.support.SecuredString;
|
||||||
import org.elasticsearch.shield.user.AnonymousUser;
|
import org.elasticsearch.shield.user.AnonymousUser;
|
||||||
|
import org.elasticsearch.shield.user.ElasticUser;
|
||||||
import org.elasticsearch.shield.user.KibanaUser;
|
import org.elasticsearch.shield.user.KibanaUser;
|
||||||
import org.elasticsearch.shield.user.SystemUser;
|
import org.elasticsearch.shield.user.SystemUser;
|
||||||
import org.elasticsearch.shield.user.User;
|
import org.elasticsearch.shield.user.User;
|
||||||
import org.elasticsearch.shield.user.XPackUser;
|
|
||||||
import org.elasticsearch.test.ESTestCase;
|
import org.elasticsearch.test.ESTestCase;
|
||||||
import org.elasticsearch.threadpool.ThreadPool;
|
import org.elasticsearch.threadpool.ThreadPool;
|
||||||
import org.elasticsearch.transport.TransportService;
|
import org.elasticsearch.transport.TransportService;
|
||||||
|
@ -109,7 +109,7 @@ public class TransportChangePasswordActionTests extends ESTestCase {
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testValidUser() {
|
public void testValidUser() {
|
||||||
final User user = randomFrom(XPackUser.INSTANCE, KibanaUser.INSTANCE, new User("joe"));
|
final User user = randomFrom(ElasticUser.INSTANCE, KibanaUser.INSTANCE, new User("joe"));
|
||||||
NativeUsersStore usersStore = mock(NativeUsersStore.class);
|
NativeUsersStore usersStore = mock(NativeUsersStore.class);
|
||||||
ChangePasswordRequest request = new ChangePasswordRequest();
|
ChangePasswordRequest request = new ChangePasswordRequest();
|
||||||
request.username(user.principal());
|
request.username(user.principal());
|
||||||
|
@ -147,7 +147,7 @@ public class TransportChangePasswordActionTests extends ESTestCase {
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testException() {
|
public void testException() {
|
||||||
final User user = randomFrom(XPackUser.INSTANCE, KibanaUser.INSTANCE, new User("joe"));
|
final User user = randomFrom(ElasticUser.INSTANCE, KibanaUser.INSTANCE, new User("joe"));
|
||||||
NativeUsersStore usersStore = mock(NativeUsersStore.class);
|
NativeUsersStore usersStore = mock(NativeUsersStore.class);
|
||||||
ChangePasswordRequest request = new ChangePasswordRequest();
|
ChangePasswordRequest request = new ChangePasswordRequest();
|
||||||
request.username(user.principal());
|
request.username(user.principal());
|
||||||
|
|
|
@ -8,7 +8,6 @@ package org.elasticsearch.shield.authc;
|
||||||
import org.elasticsearch.ElasticsearchException;
|
import org.elasticsearch.ElasticsearchException;
|
||||||
import org.elasticsearch.ElasticsearchSecurityException;
|
import org.elasticsearch.ElasticsearchSecurityException;
|
||||||
import org.elasticsearch.Version;
|
import org.elasticsearch.Version;
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.common.io.stream.BytesStreamOutput;
|
import org.elasticsearch.common.io.stream.BytesStreamOutput;
|
||||||
import org.elasticsearch.common.io.stream.StreamInput;
|
import org.elasticsearch.common.io.stream.StreamInput;
|
||||||
import org.elasticsearch.common.settings.Settings;
|
import org.elasticsearch.common.settings.Settings;
|
||||||
|
@ -37,6 +36,7 @@ import org.junit.Rule;
|
||||||
import org.junit.rules.ExpectedException;
|
import org.junit.rules.ExpectedException;
|
||||||
|
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
import java.util.Base64;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
|
||||||
import static org.elasticsearch.shield.support.Exceptions.authenticationError;
|
import static org.elasticsearch.shield.support.Exceptions.authenticationError;
|
||||||
|
@ -751,7 +751,7 @@ public class InternalAuthenticationServiceTests extends ESTestCase {
|
||||||
User user = new User("username", "r1", "r2", "r3");
|
User user = new User("username", "r1", "r2", "r3");
|
||||||
String text = InternalAuthenticationService.encodeUser(user, null);
|
String text = InternalAuthenticationService.encodeUser(user, null);
|
||||||
|
|
||||||
StreamInput input = StreamInput.wrap(Base64.decode(text));
|
StreamInput input = StreamInput.wrap(Base64.getDecoder().decode(text));
|
||||||
Version version = Version.readVersion(input);
|
Version version = Version.readVersion(input);
|
||||||
assertThat(version, is(Version.CURRENT));
|
assertThat(version, is(Version.CURRENT));
|
||||||
}
|
}
|
||||||
|
|
|
@ -16,25 +16,25 @@ import org.elasticsearch.common.bytes.BytesArray;
|
||||||
import org.elasticsearch.common.settings.Settings;
|
import org.elasticsearch.common.settings.Settings;
|
||||||
import org.elasticsearch.rest.RestStatus;
|
import org.elasticsearch.rest.RestStatus;
|
||||||
import org.elasticsearch.shield.ShieldTemplateService;
|
import org.elasticsearch.shield.ShieldTemplateService;
|
||||||
|
import org.elasticsearch.shield.action.role.DeleteRoleResponse;
|
||||||
|
import org.elasticsearch.shield.action.role.GetRolesResponse;
|
||||||
import org.elasticsearch.shield.action.user.AuthenticateAction;
|
import org.elasticsearch.shield.action.user.AuthenticateAction;
|
||||||
import org.elasticsearch.shield.action.user.AuthenticateRequest;
|
import org.elasticsearch.shield.action.user.AuthenticateRequest;
|
||||||
import org.elasticsearch.shield.action.user.AuthenticateResponse;
|
import org.elasticsearch.shield.action.user.AuthenticateResponse;
|
||||||
import org.elasticsearch.shield.action.user.ChangePasswordResponse;
|
import org.elasticsearch.shield.action.user.ChangePasswordResponse;
|
||||||
import org.elasticsearch.shield.authz.permission.KibanaRole;
|
|
||||||
import org.elasticsearch.shield.authz.permission.SuperuserRole;
|
|
||||||
import org.elasticsearch.shield.user.AnonymousUser;
|
|
||||||
import org.elasticsearch.shield.user.KibanaUser;
|
|
||||||
import org.elasticsearch.shield.user.SystemUser;
|
|
||||||
import org.elasticsearch.shield.user.User;
|
|
||||||
import org.elasticsearch.shield.action.role.DeleteRoleResponse;
|
|
||||||
import org.elasticsearch.shield.action.role.GetRolesResponse;
|
|
||||||
import org.elasticsearch.shield.action.user.DeleteUserResponse;
|
import org.elasticsearch.shield.action.user.DeleteUserResponse;
|
||||||
import org.elasticsearch.shield.action.user.GetUsersResponse;
|
import org.elasticsearch.shield.action.user.GetUsersResponse;
|
||||||
import org.elasticsearch.shield.authc.support.SecuredString;
|
import org.elasticsearch.shield.authc.support.SecuredString;
|
||||||
import org.elasticsearch.shield.authz.RoleDescriptor;
|
import org.elasticsearch.shield.authz.RoleDescriptor;
|
||||||
|
import org.elasticsearch.shield.authz.permission.KibanaRole;
|
||||||
import org.elasticsearch.shield.authz.permission.Role;
|
import org.elasticsearch.shield.authz.permission.Role;
|
||||||
|
import org.elasticsearch.shield.authz.permission.SuperuserRole;
|
||||||
import org.elasticsearch.shield.client.SecurityClient;
|
import org.elasticsearch.shield.client.SecurityClient;
|
||||||
import org.elasticsearch.shield.user.XPackUser;
|
import org.elasticsearch.shield.user.AnonymousUser;
|
||||||
|
import org.elasticsearch.shield.user.ElasticUser;
|
||||||
|
import org.elasticsearch.shield.user.KibanaUser;
|
||||||
|
import org.elasticsearch.shield.user.SystemUser;
|
||||||
|
import org.elasticsearch.shield.user.User;
|
||||||
import org.elasticsearch.test.NativeRealmIntegTestCase;
|
import org.elasticsearch.test.NativeRealmIntegTestCase;
|
||||||
import org.elasticsearch.test.ShieldSettingsSource;
|
import org.elasticsearch.test.ShieldSettingsSource;
|
||||||
import org.junit.BeforeClass;
|
import org.junit.BeforeClass;
|
||||||
|
@ -457,7 +457,7 @@ public class NativeRealmIntegTests extends NativeRealmIntegTestCase {
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testOperationsOnReservedUsers() throws Exception {
|
public void testOperationsOnReservedUsers() throws Exception {
|
||||||
final String username = randomFrom(XPackUser.NAME, KibanaUser.NAME);
|
final String username = randomFrom(ElasticUser.NAME, KibanaUser.NAME);
|
||||||
IllegalArgumentException exception = expectThrows(IllegalArgumentException.class,
|
IllegalArgumentException exception = expectThrows(IllegalArgumentException.class,
|
||||||
() -> securityClient().preparePutUser(username, randomBoolean() ? "changeme".toCharArray() : null, "admin").get());
|
() -> securityClient().preparePutUser(username, randomBoolean() ? "changeme".toCharArray() : null, "admin").get());
|
||||||
assertThat(exception.getMessage(), containsString("user [" + username + "] is reserved"));
|
assertThat(exception.getMessage(), containsString("user [" + username + "] is reserved"));
|
||||||
|
|
|
@ -7,8 +7,8 @@ package org.elasticsearch.shield.authc.esnative;
|
||||||
|
|
||||||
import org.elasticsearch.ElasticsearchSecurityException;
|
import org.elasticsearch.ElasticsearchSecurityException;
|
||||||
import org.elasticsearch.action.admin.cluster.health.ClusterHealthResponse;
|
import org.elasticsearch.action.admin.cluster.health.ClusterHealthResponse;
|
||||||
|
import org.elasticsearch.shield.user.ElasticUser;
|
||||||
import org.elasticsearch.shield.user.KibanaUser;
|
import org.elasticsearch.shield.user.KibanaUser;
|
||||||
import org.elasticsearch.shield.user.XPackUser;
|
|
||||||
import org.elasticsearch.shield.action.user.ChangePasswordResponse;
|
import org.elasticsearch.shield.action.user.ChangePasswordResponse;
|
||||||
import org.elasticsearch.shield.authc.support.SecuredString;
|
import org.elasticsearch.shield.authc.support.SecuredString;
|
||||||
import org.elasticsearch.test.NativeRealmIntegTestCase;
|
import org.elasticsearch.test.NativeRealmIntegTestCase;
|
||||||
|
@ -29,7 +29,7 @@ public class ReservedRealmIntegTests extends NativeRealmIntegTestCase {
|
||||||
private static final SecuredString DEFAULT_PASSWORD = new SecuredString("changeme".toCharArray());
|
private static final SecuredString DEFAULT_PASSWORD = new SecuredString("changeme".toCharArray());
|
||||||
|
|
||||||
public void testAuthenticate() {
|
public void testAuthenticate() {
|
||||||
for (String username : Arrays.asList(XPackUser.NAME, KibanaUser.NAME)) {
|
for (String username : Arrays.asList(ElasticUser.NAME, KibanaUser.NAME)) {
|
||||||
ClusterHealthResponse response = client()
|
ClusterHealthResponse response = client()
|
||||||
.filterWithHeader(singletonMap("Authorization", basicAuthHeaderValue(username, DEFAULT_PASSWORD)))
|
.filterWithHeader(singletonMap("Authorization", basicAuthHeaderValue(username, DEFAULT_PASSWORD)))
|
||||||
.admin()
|
.admin()
|
||||||
|
@ -42,7 +42,7 @@ public class ReservedRealmIntegTests extends NativeRealmIntegTestCase {
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testChangingPassword() {
|
public void testChangingPassword() {
|
||||||
String username = randomFrom(XPackUser.NAME, KibanaUser.NAME);
|
String username = randomFrom(ElasticUser.NAME, KibanaUser.NAME);
|
||||||
final char[] newPassword = "supersecretvalue".toCharArray();
|
final char[] newPassword = "supersecretvalue".toCharArray();
|
||||||
|
|
||||||
if (randomBoolean()) {
|
if (randomBoolean()) {
|
||||||
|
|
|
@ -13,9 +13,9 @@ import org.elasticsearch.shield.authc.support.Hasher;
|
||||||
import org.elasticsearch.shield.authc.support.SecuredString;
|
import org.elasticsearch.shield.authc.support.SecuredString;
|
||||||
import org.elasticsearch.shield.authc.support.UsernamePasswordToken;
|
import org.elasticsearch.shield.authc.support.UsernamePasswordToken;
|
||||||
import org.elasticsearch.shield.user.AnonymousUser;
|
import org.elasticsearch.shield.user.AnonymousUser;
|
||||||
|
import org.elasticsearch.shield.user.ElasticUser;
|
||||||
import org.elasticsearch.shield.user.KibanaUser;
|
import org.elasticsearch.shield.user.KibanaUser;
|
||||||
import org.elasticsearch.shield.user.User;
|
import org.elasticsearch.shield.user.User;
|
||||||
import org.elasticsearch.shield.user.XPackUser;
|
|
||||||
import org.elasticsearch.test.ESTestCase;
|
import org.elasticsearch.test.ESTestCase;
|
||||||
import org.junit.Before;
|
import org.junit.Before;
|
||||||
|
|
||||||
|
@ -49,7 +49,7 @@ public class ReservedRealmTests extends ESTestCase {
|
||||||
public void testUserStoreNotStarted() {
|
public void testUserStoreNotStarted() {
|
||||||
when(usersStore.started()).thenReturn(false);
|
when(usersStore.started()).thenReturn(false);
|
||||||
final ReservedRealm reservedRealm = new ReservedRealm(mock(Environment.class), Settings.EMPTY, usersStore);
|
final ReservedRealm reservedRealm = new ReservedRealm(mock(Environment.class), Settings.EMPTY, usersStore);
|
||||||
final String principal = randomFrom(XPackUser.NAME, KibanaUser.NAME);
|
final String principal = randomFrom(ElasticUser.NAME, KibanaUser.NAME);
|
||||||
|
|
||||||
ElasticsearchSecurityException expected = expectThrows(ElasticsearchSecurityException.class,
|
ElasticsearchSecurityException expected = expectThrows(ElasticsearchSecurityException.class,
|
||||||
() -> reservedRealm.doAuthenticate(new UsernamePasswordToken(principal, DEFAULT_PASSWORD)));
|
() -> reservedRealm.doAuthenticate(new UsernamePasswordToken(principal, DEFAULT_PASSWORD)));
|
||||||
|
@ -65,7 +65,7 @@ public class ReservedRealmTests extends ESTestCase {
|
||||||
when(usersStore.shieldIndexExists()).thenReturn(true);
|
when(usersStore.shieldIndexExists()).thenReturn(true);
|
||||||
}
|
}
|
||||||
final ReservedRealm reservedRealm = new ReservedRealm(mock(Environment.class), Settings.EMPTY, usersStore);
|
final ReservedRealm reservedRealm = new ReservedRealm(mock(Environment.class), Settings.EMPTY, usersStore);
|
||||||
final User expected = randomFrom((User) XPackUser.INSTANCE, (User) KibanaUser.INSTANCE);
|
final User expected = randomFrom((User) ElasticUser.INSTANCE, KibanaUser.INSTANCE);
|
||||||
final String principal = expected.principal();
|
final String principal = expected.principal();
|
||||||
|
|
||||||
final User authenticated = reservedRealm.doAuthenticate(new UsernamePasswordToken(principal, DEFAULT_PASSWORD));
|
final User authenticated = reservedRealm.doAuthenticate(new UsernamePasswordToken(principal, DEFAULT_PASSWORD));
|
||||||
|
@ -81,7 +81,7 @@ public class ReservedRealmTests extends ESTestCase {
|
||||||
|
|
||||||
public void testAuthenticationWithStoredPassword() throws Throwable {
|
public void testAuthenticationWithStoredPassword() throws Throwable {
|
||||||
final ReservedRealm reservedRealm = new ReservedRealm(mock(Environment.class), Settings.EMPTY, usersStore);
|
final ReservedRealm reservedRealm = new ReservedRealm(mock(Environment.class), Settings.EMPTY, usersStore);
|
||||||
final User expectedUser = randomFrom((User) XPackUser.INSTANCE, (User) KibanaUser.INSTANCE);
|
final User expectedUser = randomFrom((User) ElasticUser.INSTANCE, KibanaUser.INSTANCE);
|
||||||
final String principal = expectedUser.principal();
|
final String principal = expectedUser.principal();
|
||||||
final SecuredString newPassword = new SecuredString("foobar".toCharArray());
|
final SecuredString newPassword = new SecuredString("foobar".toCharArray());
|
||||||
when(usersStore.shieldIndexExists()).thenReturn(true);
|
when(usersStore.shieldIndexExists()).thenReturn(true);
|
||||||
|
@ -107,7 +107,7 @@ public class ReservedRealmTests extends ESTestCase {
|
||||||
|
|
||||||
public void testLookup() {
|
public void testLookup() {
|
||||||
final ReservedRealm reservedRealm = new ReservedRealm(mock(Environment.class), Settings.EMPTY, usersStore);
|
final ReservedRealm reservedRealm = new ReservedRealm(mock(Environment.class), Settings.EMPTY, usersStore);
|
||||||
final User expectedUser = randomFrom((User) XPackUser.INSTANCE, (User) KibanaUser.INSTANCE);
|
final User expectedUser = randomFrom((User) ElasticUser.INSTANCE, KibanaUser.INSTANCE);
|
||||||
final String principal = expectedUser.principal();
|
final String principal = expectedUser.principal();
|
||||||
|
|
||||||
final User user = reservedRealm.doLookupUser(principal);
|
final User user = reservedRealm.doLookupUser(principal);
|
||||||
|
@ -120,7 +120,7 @@ public class ReservedRealmTests extends ESTestCase {
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testHelperMethods() {
|
public void testHelperMethods() {
|
||||||
final User expectedUser = randomFrom((User) XPackUser.INSTANCE, KibanaUser.INSTANCE);
|
final User expectedUser = randomFrom((User) ElasticUser.INSTANCE, KibanaUser.INSTANCE);
|
||||||
final String principal = expectedUser.principal();
|
final String principal = expectedUser.principal();
|
||||||
assertThat(ReservedRealm.isReserved(principal), is(true));
|
assertThat(ReservedRealm.isReserved(principal), is(true));
|
||||||
assertThat(ReservedRealm.getUser(principal), sameInstance(expectedUser));
|
assertThat(ReservedRealm.getUser(principal), sameInstance(expectedUser));
|
||||||
|
@ -129,19 +129,20 @@ public class ReservedRealmTests extends ESTestCase {
|
||||||
assertThat(ReservedRealm.isReserved(notExpected), is(false));
|
assertThat(ReservedRealm.isReserved(notExpected), is(false));
|
||||||
assertThat(ReservedRealm.getUser(notExpected), nullValue());
|
assertThat(ReservedRealm.getUser(notExpected), nullValue());
|
||||||
|
|
||||||
assertThat(ReservedRealm.users(), containsInAnyOrder((User) XPackUser.INSTANCE, KibanaUser.INSTANCE));
|
assertThat(ReservedRealm.users(), containsInAnyOrder((User) ElasticUser.INSTANCE, KibanaUser.INSTANCE));
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testFailedAuthentication() {
|
public void testFailedAuthentication() {
|
||||||
final ReservedRealm reservedRealm = new ReservedRealm(mock(Environment.class), Settings.EMPTY, usersStore);
|
final ReservedRealm reservedRealm = new ReservedRealm(mock(Environment.class), Settings.EMPTY, usersStore);
|
||||||
// maybe cache a successful auth
|
// maybe cache a successful auth
|
||||||
if (randomBoolean()) {
|
if (randomBoolean()) {
|
||||||
User user = reservedRealm.authenticate(new UsernamePasswordToken(XPackUser.NAME, new SecuredString("changeme".toCharArray())));
|
User user = reservedRealm.authenticate(
|
||||||
assertThat(user, sameInstance(XPackUser.INSTANCE));
|
new UsernamePasswordToken(ElasticUser.NAME, new SecuredString("changeme".toCharArray())));
|
||||||
|
assertThat(user, sameInstance(ElasticUser.INSTANCE));
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
reservedRealm.authenticate(new UsernamePasswordToken(XPackUser.NAME, new SecuredString("foobar".toCharArray())));
|
reservedRealm.authenticate(new UsernamePasswordToken(ElasticUser.NAME, new SecuredString("foobar".toCharArray())));
|
||||||
fail("authentication should throw an exception otherwise we may allow others to impersonate reserved users...");
|
fail("authentication should throw an exception otherwise we may allow others to impersonate reserved users...");
|
||||||
} catch (ElasticsearchSecurityException e) {
|
} catch (ElasticsearchSecurityException e) {
|
||||||
assertThat(e.getMessage(), containsString("failed to authenticate"));
|
assertThat(e.getMessage(), containsString("failed to authenticate"));
|
||||||
|
|
|
@ -92,6 +92,7 @@ public class UsersToolTests extends CommandTestCase {
|
||||||
public static void closeJimfs() throws IOException {
|
public static void closeJimfs() throws IOException {
|
||||||
if (jimfs != null) {
|
if (jimfs != null) {
|
||||||
jimfs.close();
|
jimfs.close();
|
||||||
|
jimfs = null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -119,7 +119,7 @@ public class OpenLdapTests extends ESTestCase {
|
||||||
|
|
||||||
Map<String, Object> stats = realm.usageStats();
|
Map<String, Object> stats = realm.usageStats();
|
||||||
assertThat(stats, is(notNullValue()));
|
assertThat(stats, is(notNullValue()));
|
||||||
assertThat(stats, hasEntry("size", "small"));
|
assertThat(stats, hasEntry("size", "tiny"));
|
||||||
assertThat(stats, hasEntry("ssl", true));
|
assertThat(stats, hasEntry("ssl", true));
|
||||||
assertThat(stats, hasEntry("user_search", userSearch));
|
assertThat(stats, hasEntry("user_search", userSearch));
|
||||||
assertThat(stats, hasEntry("load_balance_type", loadBalanceType));
|
assertThat(stats, hasEntry("load_balance_type", loadBalanceType));
|
||||||
|
|
|
@ -20,7 +20,7 @@ public class UsernamePasswordRealmTests extends ESTestCase {
|
||||||
int count = randomIntBetween(0, 1000);
|
int count = randomIntBetween(0, 1000);
|
||||||
UsernamePasswordRealm.UserbaseSize size = UsernamePasswordRealm.UserbaseSize.resolve(count);
|
UsernamePasswordRealm.UserbaseSize size = UsernamePasswordRealm.UserbaseSize.resolve(count);
|
||||||
if (count < 10) {
|
if (count < 10) {
|
||||||
assertThat(size, is(UsernamePasswordRealm.UserbaseSize.SMALL));
|
assertThat(size, is(UsernamePasswordRealm.UserbaseSize.TINY));
|
||||||
} else if (count < 100) {
|
} else if (count < 100) {
|
||||||
assertThat(size, is(UsernamePasswordRealm.UserbaseSize.SMALL));
|
assertThat(size, is(UsernamePasswordRealm.UserbaseSize.SMALL));
|
||||||
} else if (count < 500) {
|
} else if (count < 500) {
|
||||||
|
|
|
@ -6,7 +6,6 @@
|
||||||
package org.elasticsearch.shield.authc.support;
|
package org.elasticsearch.shield.authc.support;
|
||||||
|
|
||||||
import org.elasticsearch.ElasticsearchSecurityException;
|
import org.elasticsearch.ElasticsearchSecurityException;
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.common.settings.Settings;
|
import org.elasticsearch.common.settings.Settings;
|
||||||
import org.elasticsearch.common.util.concurrent.ThreadContext;
|
import org.elasticsearch.common.util.concurrent.ThreadContext;
|
||||||
import org.elasticsearch.test.ESTestCase;
|
import org.elasticsearch.test.ESTestCase;
|
||||||
|
@ -14,6 +13,7 @@ import org.junit.Rule;
|
||||||
import org.junit.rules.ExpectedException;
|
import org.junit.rules.ExpectedException;
|
||||||
|
|
||||||
import java.nio.charset.StandardCharsets;
|
import java.nio.charset.StandardCharsets;
|
||||||
|
import java.util.Base64;
|
||||||
|
|
||||||
import static org.elasticsearch.test.ShieldTestsUtils.assertAuthenticationException;
|
import static org.elasticsearch.test.ShieldTestsUtils.assertAuthenticationException;
|
||||||
import static org.hamcrest.Matchers.equalTo;
|
import static org.hamcrest.Matchers.equalTo;
|
||||||
|
@ -35,7 +35,7 @@ public class UsernamePasswordTokenTests extends ESTestCase {
|
||||||
assertThat(header, notNullValue());
|
assertThat(header, notNullValue());
|
||||||
assertTrue(header.startsWith("Basic "));
|
assertTrue(header.startsWith("Basic "));
|
||||||
String token = header.substring("Basic ".length());
|
String token = header.substring("Basic ".length());
|
||||||
token = new String(Base64.decode(token), StandardCharsets.UTF_8);
|
token = new String(Base64.getDecoder().decode(token), StandardCharsets.UTF_8);
|
||||||
int i = token.indexOf(":");
|
int i = token.indexOf(":");
|
||||||
assertTrue(i > 0);
|
assertTrue(i > 0);
|
||||||
String username = token.substring(0, i);
|
String username = token.substring(0, i);
|
||||||
|
@ -46,7 +46,7 @@ public class UsernamePasswordTokenTests extends ESTestCase {
|
||||||
|
|
||||||
public void testExtractToken() throws Exception {
|
public void testExtractToken() throws Exception {
|
||||||
ThreadContext threadContext = new ThreadContext(Settings.EMPTY);
|
ThreadContext threadContext = new ThreadContext(Settings.EMPTY);
|
||||||
String header = "Basic " + Base64.encodeBytes("user1:test123".getBytes(StandardCharsets.UTF_8));
|
String header = "Basic " + Base64.getEncoder().encodeToString("user1:test123".getBytes(StandardCharsets.UTF_8));
|
||||||
threadContext.putHeader(UsernamePasswordToken.BASIC_AUTH_HEADER, header);
|
threadContext.putHeader(UsernamePasswordToken.BASIC_AUTH_HEADER, header);
|
||||||
UsernamePasswordToken token = UsernamePasswordToken.extractToken(threadContext);
|
UsernamePasswordToken token = UsernamePasswordToken.extractToken(threadContext);
|
||||||
assertThat(token, notNullValue());
|
assertThat(token, notNullValue());
|
||||||
|
|
|
@ -22,6 +22,8 @@ import org.elasticsearch.shield.user.User;
|
||||||
import org.elasticsearch.test.ESTestCase;
|
import org.elasticsearch.test.ESTestCase;
|
||||||
import org.elasticsearch.transport.TransportRequest;
|
import org.elasticsearch.transport.TransportRequest;
|
||||||
|
|
||||||
|
import java.util.Arrays;
|
||||||
|
|
||||||
import static org.hamcrest.Matchers.is;
|
import static org.hamcrest.Matchers.is;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -45,17 +47,27 @@ public class KibanaRoleTests extends ESTestCase {
|
||||||
assertThat(KibanaRole.INSTANCE.runAs().isEmpty(), is(true));
|
assertThat(KibanaRole.INSTANCE.runAs().isEmpty(), is(true));
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testIndices() {
|
public void testUnauthorizedIndices() {
|
||||||
final String kibanaIndex = ".kibana";
|
|
||||||
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher("indices:foo").test(kibanaIndex), is(true));
|
|
||||||
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher("indices:bar").test(kibanaIndex), is(true));
|
|
||||||
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher(DeleteIndexAction.NAME).test(kibanaIndex), is(true));
|
|
||||||
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher(CreateIndexAction.NAME).test(kibanaIndex), is(true));
|
|
||||||
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher(IndexAction.NAME).test(kibanaIndex), is(true));
|
|
||||||
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher(DeleteAction.NAME).test(kibanaIndex), is(true));
|
|
||||||
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher(UpdateSettingsAction.NAME).test(kibanaIndex), is(true));
|
|
||||||
|
|
||||||
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher(IndexAction.NAME).test("foo"), is(false));
|
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher(IndexAction.NAME).test("foo"), is(false));
|
||||||
|
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher(IndexAction.NAME).test(".reporting"), is(false));
|
||||||
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher("indices:foo").test(randomAsciiOfLengthBetween(8, 24)), is(false));
|
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher("indices:foo").test(randomAsciiOfLengthBetween(8, 24)), is(false));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void testKibanaIndices() {
|
||||||
|
Arrays.asList(".kibana", ".kibana-devnull").forEach(this::testAllIndexAccess);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void testReportingIndices() {
|
||||||
|
testAllIndexAccess(".reporting-" + randomAsciiOfLength(randomIntBetween(0, 13)));
|
||||||
|
}
|
||||||
|
|
||||||
|
private void testAllIndexAccess(String index) {
|
||||||
|
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher("indices:foo").test(index), is(true));
|
||||||
|
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher("indices:bar").test(index), is(true));
|
||||||
|
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher(DeleteIndexAction.NAME).test(index), is(true));
|
||||||
|
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher(CreateIndexAction.NAME).test(index), is(true));
|
||||||
|
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher(IndexAction.NAME).test(index), is(true));
|
||||||
|
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher(DeleteAction.NAME).test(index), is(true));
|
||||||
|
assertThat(KibanaRole.INSTANCE.indices().allowedIndicesMatcher(UpdateSettingsAction.NAME).test(index), is(true));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -358,7 +358,7 @@ public class FileRolesStoreTests extends ESTestCase {
|
||||||
assertThat(messages, notNullValue());
|
assertThat(messages, notNullValue());
|
||||||
assertThat(messages, hasSize(4));
|
assertThat(messages, hasSize(4));
|
||||||
// the system role will always be checked first
|
// the system role will always be checked first
|
||||||
assertThat(messages.get(0).text, containsString("role [__es_system_role] is reserved"));
|
assertThat(messages.get(0).text, containsString("role [_system] is reserved"));
|
||||||
assertThat(messages.get(1).text, containsString("role [superuser] is reserved"));
|
assertThat(messages.get(1).text, containsString("role [superuser] is reserved"));
|
||||||
assertThat(messages.get(2).text, containsString("role [kibana] is reserved"));
|
assertThat(messages.get(2).text, containsString("role [kibana] is reserved"));
|
||||||
assertThat(messages.get(3).text, containsString("role [transport_client] is reserved"));
|
assertThat(messages.get(3).text, containsString("role [transport_client] is reserved"));
|
||||||
|
|
|
@ -9,10 +9,10 @@ import org.elasticsearch.shield.SecurityContext;
|
||||||
import org.elasticsearch.shield.authz.permission.KibanaRole;
|
import org.elasticsearch.shield.authz.permission.KibanaRole;
|
||||||
import org.elasticsearch.shield.authz.permission.SuperuserRole;
|
import org.elasticsearch.shield.authz.permission.SuperuserRole;
|
||||||
import org.elasticsearch.shield.authz.permission.TransportClientRole;
|
import org.elasticsearch.shield.authz.permission.TransportClientRole;
|
||||||
|
import org.elasticsearch.shield.user.ElasticUser;
|
||||||
import org.elasticsearch.shield.user.KibanaUser;
|
import org.elasticsearch.shield.user.KibanaUser;
|
||||||
import org.elasticsearch.shield.user.SystemUser;
|
import org.elasticsearch.shield.user.SystemUser;
|
||||||
import org.elasticsearch.shield.user.User;
|
import org.elasticsearch.shield.user.User;
|
||||||
import org.elasticsearch.shield.user.XPackUser;
|
|
||||||
import org.elasticsearch.test.ESTestCase;
|
import org.elasticsearch.test.ESTestCase;
|
||||||
import org.junit.Before;
|
import org.junit.Before;
|
||||||
|
|
||||||
|
@ -41,7 +41,7 @@ public class ReservedRolesStoreTests extends ESTestCase {
|
||||||
|
|
||||||
public void testRetrievingReservedRolesNonKibanaUser() {
|
public void testRetrievingReservedRolesNonKibanaUser() {
|
||||||
if (randomBoolean()) {
|
if (randomBoolean()) {
|
||||||
when(securityContext.getUser()).thenReturn(XPackUser.INSTANCE);
|
when(securityContext.getUser()).thenReturn(ElasticUser.INSTANCE);
|
||||||
}
|
}
|
||||||
|
|
||||||
assertThat(reservedRolesStore.role(SuperuserRole.NAME), sameInstance(SuperuserRole.INSTANCE));
|
assertThat(reservedRolesStore.role(SuperuserRole.NAME), sameInstance(SuperuserRole.INSTANCE));
|
||||||
|
|
|
@ -10,6 +10,7 @@ import org.elasticsearch.common.Strings;
|
||||||
import org.elasticsearch.common.io.stream.ByteBufferStreamInput;
|
import org.elasticsearch.common.io.stream.ByteBufferStreamInput;
|
||||||
import org.elasticsearch.common.io.stream.BytesStreamOutput;
|
import org.elasticsearch.common.io.stream.BytesStreamOutput;
|
||||||
import org.elasticsearch.test.ESTestCase;
|
import org.elasticsearch.test.ESTestCase;
|
||||||
|
import org.elasticsearch.xpack.XPackClient;
|
||||||
|
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
@ -58,7 +59,7 @@ public class UserTests extends ESTestCase {
|
||||||
assertThat(readFromRunAs.runAs(), is(nullValue()));
|
assertThat(readFromRunAs.runAs(), is(nullValue()));
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testSystemReadAndWrite() throws Exception {
|
public void testSystemUserReadAndWrite() throws Exception {
|
||||||
BytesStreamOutput output = new BytesStreamOutput();
|
BytesStreamOutput output = new BytesStreamOutput();
|
||||||
|
|
||||||
User.writeTo(SystemUser.INSTANCE, output);
|
User.writeTo(SystemUser.INSTANCE, output);
|
||||||
|
@ -68,6 +69,16 @@ public class UserTests extends ESTestCase {
|
||||||
assertThat(readFrom.runAs(), is(nullValue()));
|
assertThat(readFrom.runAs(), is(nullValue()));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void testXPackUserReadAndWrite() throws Exception {
|
||||||
|
BytesStreamOutput output = new BytesStreamOutput();
|
||||||
|
|
||||||
|
User.writeTo(XPackUser.INSTANCE, output);
|
||||||
|
User readFrom = User.readFrom(ByteBufferStreamInput.wrap(output.bytes()));
|
||||||
|
|
||||||
|
assertThat(readFrom, is(sameInstance(XPackUser.INSTANCE)));
|
||||||
|
assertThat(readFrom.runAs(), is(nullValue()));
|
||||||
|
}
|
||||||
|
|
||||||
public void testFakeInternalUserSerialization() throws Exception {
|
public void testFakeInternalUserSerialization() throws Exception {
|
||||||
BytesStreamOutput output = new BytesStreamOutput();
|
BytesStreamOutput output = new BytesStreamOutput();
|
||||||
output.writeBoolean(true);
|
output.writeBoolean(true);
|
||||||
|
@ -102,10 +113,10 @@ public class UserTests extends ESTestCase {
|
||||||
|
|
||||||
public void testReservedUserSerialization() throws Exception {
|
public void testReservedUserSerialization() throws Exception {
|
||||||
BytesStreamOutput output = new BytesStreamOutput();
|
BytesStreamOutput output = new BytesStreamOutput();
|
||||||
User.writeTo(XPackUser.INSTANCE, output);
|
User.writeTo(ElasticUser.INSTANCE, output);
|
||||||
User readFrom = User.readFrom(ByteBufferStreamInput.wrap(output.bytes()));
|
User readFrom = User.readFrom(ByteBufferStreamInput.wrap(output.bytes()));
|
||||||
|
|
||||||
assertThat(readFrom, is(sameInstance(XPackUser.INSTANCE)));
|
assertThat(readFrom, is(sameInstance(ElasticUser.INSTANCE)));
|
||||||
|
|
||||||
output = new BytesStreamOutput();
|
output = new BytesStreamOutput();
|
||||||
User.writeTo(KibanaUser.INSTANCE, output);
|
User.writeTo(KibanaUser.INSTANCE, output);
|
||||||
|
|
|
@ -5,7 +5,7 @@ admin:
|
||||||
- names: '*'
|
- names: '*'
|
||||||
privileges: [ all ]
|
privileges: [ all ]
|
||||||
|
|
||||||
__es_system_role:
|
_system:
|
||||||
cluster:
|
cluster:
|
||||||
- all
|
- all
|
||||||
indices:
|
indices:
|
||||||
|
|
|
@ -59,10 +59,8 @@ indices:data/read/field_stats
|
||||||
indices:data/read/get
|
indices:data/read/get
|
||||||
indices:data/read/xpack/graph/explore
|
indices:data/read/xpack/graph/explore
|
||||||
indices:data/read/mget
|
indices:data/read/mget
|
||||||
indices:data/read/mpercolate
|
|
||||||
indices:data/read/msearch
|
indices:data/read/msearch
|
||||||
indices:data/read/mtv
|
indices:data/read/mtv
|
||||||
indices:data/read/percolate
|
|
||||||
cluster:admin/script/get
|
cluster:admin/script/get
|
||||||
indices:data/read/scroll
|
indices:data/read/scroll
|
||||||
indices:data/read/scroll/clear
|
indices:data/read/scroll/clear
|
||||||
|
|
|
@ -37,6 +37,8 @@ import org.elasticsearch.xpack.common.secret.SecretModule;
|
||||||
import org.elasticsearch.xpack.extensions.XPackExtension;
|
import org.elasticsearch.xpack.extensions.XPackExtension;
|
||||||
import org.elasticsearch.xpack.extensions.XPackExtensionsService;
|
import org.elasticsearch.xpack.extensions.XPackExtensionsService;
|
||||||
import org.elasticsearch.xpack.notification.Notification;
|
import org.elasticsearch.xpack.notification.Notification;
|
||||||
|
import org.elasticsearch.xpack.notification.email.Account;
|
||||||
|
import org.elasticsearch.xpack.notification.email.support.BodyPartSource;
|
||||||
import org.elasticsearch.xpack.rest.action.RestXPackInfoAction;
|
import org.elasticsearch.xpack.rest.action.RestXPackInfoAction;
|
||||||
import org.elasticsearch.xpack.common.text.TextTemplateModule;
|
import org.elasticsearch.xpack.common.text.TextTemplateModule;
|
||||||
import org.elasticsearch.xpack.rest.action.RestXPackUsageAction;
|
import org.elasticsearch.xpack.rest.action.RestXPackUsageAction;
|
||||||
|
@ -84,6 +86,9 @@ public class XPackPlugin extends Plugin {
|
||||||
throw bogus; // some other bug
|
throw bogus; // some other bug
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
// some classes need to have their own clinit blocks
|
||||||
|
BodyPartSource.init();
|
||||||
|
Account.init();
|
||||||
}
|
}
|
||||||
|
|
||||||
protected final Settings settings;
|
protected final Settings settings;
|
||||||
|
|
|
@ -5,12 +5,12 @@
|
||||||
*/
|
*/
|
||||||
package org.elasticsearch.xpack.common.http.auth.basic;
|
package org.elasticsearch.xpack.common.http.auth.basic;
|
||||||
|
|
||||||
import org.elasticsearch.common.Base64;
|
|
||||||
import org.elasticsearch.xpack.common.http.auth.ApplicableHttpAuth;
|
import org.elasticsearch.xpack.common.http.auth.ApplicableHttpAuth;
|
||||||
import org.elasticsearch.xpack.common.secret.SecretService;
|
import org.elasticsearch.xpack.common.secret.SecretService;
|
||||||
|
|
||||||
import java.net.HttpURLConnection;
|
import java.net.HttpURLConnection;
|
||||||
import java.nio.charset.StandardCharsets;
|
import java.nio.charset.StandardCharsets;
|
||||||
|
import java.util.Base64;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*/
|
*/
|
||||||
|
@ -24,7 +24,7 @@ public class ApplicableBasicAuth extends ApplicableHttpAuth<BasicAuth> {
|
||||||
}
|
}
|
||||||
|
|
||||||
public static String headerValue(String username, char[] password) {
|
public static String headerValue(String username, char[] password) {
|
||||||
return "Basic " + Base64.encodeBytes((username + ":" + new String(password)).getBytes(StandardCharsets.UTF_8));
|
return "Basic " + Base64.getEncoder().encodeToString((username + ":" + new String(password)).getBytes(StandardCharsets.UTF_8));
|
||||||
}
|
}
|
||||||
|
|
||||||
public void apply(HttpURLConnection connection) {
|
public void apply(HttpURLConnection connection) {
|
||||||
|
|
|
@ -32,13 +32,6 @@ public class Account {
|
||||||
static final String SMTP_PROTOCOL = "smtp";
|
static final String SMTP_PROTOCOL = "smtp";
|
||||||
|
|
||||||
static {
|
static {
|
||||||
// required as java doesn't always find the correct mailcap to properly handle mime types
|
|
||||||
final MailcapCommandMap mailcap = (MailcapCommandMap) CommandMap.getDefaultCommandMap();
|
|
||||||
mailcap.addMailcap("text/html;; x-java-content-handler=com.sun.mail.handlers.text_html");
|
|
||||||
mailcap.addMailcap("text/xml;; x-java-content-handler=com.sun.mail.handlers.text_xml");
|
|
||||||
mailcap.addMailcap("text/plain;; x-java-content-handler=com.sun.mail.handlers.text_plain");
|
|
||||||
mailcap.addMailcap("multipart/*;; x-java-content-handler=com.sun.mail.handlers.multipart_mixed");
|
|
||||||
mailcap.addMailcap("message/rfc822;; x-java-content-handler=com.sun.mail.handlers.message_rfc822");
|
|
||||||
SecurityManager sm = System.getSecurityManager();
|
SecurityManager sm = System.getSecurityManager();
|
||||||
if (sm != null) {
|
if (sm != null) {
|
||||||
sm.checkPermission(new SpecialPermission());
|
sm.checkPermission(new SpecialPermission());
|
||||||
|
@ -46,12 +39,22 @@ public class Account {
|
||||||
AccessController.doPrivileged(new PrivilegedAction<Void>() {
|
AccessController.doPrivileged(new PrivilegedAction<Void>() {
|
||||||
@Override
|
@Override
|
||||||
public Void run() {
|
public Void run() {
|
||||||
|
// required as java doesn't always find the correct mailcap to properly handle mime types
|
||||||
|
final MailcapCommandMap mailcap = (MailcapCommandMap) CommandMap.getDefaultCommandMap();
|
||||||
|
mailcap.addMailcap("text/html;; x-java-content-handler=com.sun.mail.handlers.text_html");
|
||||||
|
mailcap.addMailcap("text/xml;; x-java-content-handler=com.sun.mail.handlers.text_xml");
|
||||||
|
mailcap.addMailcap("text/plain;; x-java-content-handler=com.sun.mail.handlers.text_plain");
|
||||||
|
mailcap.addMailcap("multipart/*;; x-java-content-handler=com.sun.mail.handlers.multipart_mixed");
|
||||||
|
mailcap.addMailcap("message/rfc822;; x-java-content-handler=com.sun.mail.handlers.message_rfc822");
|
||||||
CommandMap.setDefaultCommandMap(mailcap);
|
CommandMap.setDefaultCommandMap(mailcap);
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// exists only to allow ensuring class is initialized
|
||||||
|
public static void init() {}
|
||||||
|
|
||||||
static final Settings DEFAULT_SMTP_TIMEOUT_SETTINGS = Settings.builder()
|
static final Settings DEFAULT_SMTP_TIMEOUT_SETTINGS = Settings.builder()
|
||||||
.put("connection_timeout", TimeValue.timeValueMinutes(2))
|
.put("connection_timeout", TimeValue.timeValueMinutes(2))
|
||||||
.put("write_timeout", TimeValue.timeValueMinutes(2))
|
.put("write_timeout", TimeValue.timeValueMinutes(2))
|
||||||
|
|
|
@ -5,18 +5,30 @@
|
||||||
*/
|
*/
|
||||||
package org.elasticsearch.xpack.notification.email.support;
|
package org.elasticsearch.xpack.notification.email.support;
|
||||||
|
|
||||||
|
import org.elasticsearch.SpecialPermission;
|
||||||
import org.elasticsearch.common.xcontent.ToXContent;
|
import org.elasticsearch.common.xcontent.ToXContent;
|
||||||
|
|
||||||
|
import javax.activation.CommandMap;
|
||||||
import javax.activation.FileTypeMap;
|
import javax.activation.FileTypeMap;
|
||||||
import javax.mail.MessagingException;
|
import javax.mail.MessagingException;
|
||||||
import javax.mail.internet.MimeBodyPart;
|
import javax.mail.internet.MimeBodyPart;
|
||||||
|
import java.security.AccessController;
|
||||||
|
import java.security.PrivilegedAction;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public abstract class BodyPartSource implements ToXContent {
|
public abstract class BodyPartSource implements ToXContent {
|
||||||
|
|
||||||
protected static FileTypeMap fileTypeMap = FileTypeMap.getDefaultFileTypeMap();
|
protected static FileTypeMap fileTypeMap;
|
||||||
|
static {
|
||||||
|
SecurityManager sm = System.getSecurityManager();
|
||||||
|
if (sm != null) {
|
||||||
|
sm.checkPermission(new SpecialPermission());
|
||||||
|
}
|
||||||
|
fileTypeMap = AccessController.doPrivileged(
|
||||||
|
(PrivilegedAction<FileTypeMap>)() -> FileTypeMap.getDefaultFileTypeMap());
|
||||||
|
}
|
||||||
|
|
||||||
protected final String id;
|
protected final String id;
|
||||||
protected final String name;
|
protected final String name;
|
||||||
|
@ -46,4 +58,7 @@ public abstract class BodyPartSource implements ToXContent {
|
||||||
|
|
||||||
public abstract MimeBodyPart bodyPart() throws MessagingException;
|
public abstract MimeBodyPart bodyPart() throws MessagingException;
|
||||||
|
|
||||||
|
// exists only to allow ensuring class is initialized
|
||||||
|
public static void init() {}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -11,6 +11,8 @@ grant {
|
||||||
// to load the class with the application class loader
|
// to load the class with the application class loader
|
||||||
permission java.lang.RuntimePermission "setContextClassLoader";
|
permission java.lang.RuntimePermission "setContextClassLoader";
|
||||||
permission java.lang.RuntimePermission "getClassLoader";
|
permission java.lang.RuntimePermission "getClassLoader";
|
||||||
|
// TODO: remove use of this jar as soon as possible!!!!
|
||||||
|
permission java.lang.RuntimePermission "accessClassInPackage.com.sun.activation.registries";
|
||||||
|
|
||||||
// bouncy castle
|
// bouncy castle
|
||||||
permission java.security.SecurityPermission "putProviderProperty.BC";
|
permission java.security.SecurityPermission "putProviderProperty.BC";
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
{
|
{
|
||||||
"xpack.info": {
|
"xpack.info": {
|
||||||
"documentation": "Retrieve information about xpack, including buid number/timestamp and license status",
|
"documentation": "Retrieve information about xpack, including build number/timestamp and license status",
|
||||||
"methods": [ "GET" ],
|
"methods": [ "GET" ],
|
||||||
"url": {
|
"url": {
|
||||||
"path": "/_xpack",
|
"path": "/_xpack",
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
{
|
{
|
||||||
"xpack.info": {
|
"xpack.usage": {
|
||||||
"documentation": "Retrieve information about xpack features usage",
|
"documentation": "Retrieve information about xpack features usage",
|
||||||
"methods": [ "GET" ],
|
"methods": [ "GET" ],
|
||||||
"url": {
|
"url": {
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
# Integration tests xpack info API
|
# Integration tests xpack info and usage API
|
||||||
#
|
#
|
||||||
"X-Pack Info":
|
"X-Pack Info and Usage":
|
||||||
|
|
||||||
- do:
|
- do:
|
||||||
cluster.health:
|
cluster.health:
|
||||||
|
@ -83,6 +83,17 @@
|
||||||
- is_true: features.monitoring.description
|
- is_true: features.monitoring.description
|
||||||
- is_true: tagline
|
- is_true: tagline
|
||||||
|
|
||||||
|
- do:
|
||||||
|
xpack.usage: {}
|
||||||
|
- is_true: watcher.enabled
|
||||||
|
- is_true: watcher.available
|
||||||
|
- is_true: security.enabled
|
||||||
|
- is_true: security.available
|
||||||
|
- is_true: graph.enabled
|
||||||
|
- is_true: graph.available
|
||||||
|
- is_true: monitoring.enabled
|
||||||
|
- is_true: monitoring.available
|
||||||
|
|
||||||
- do:
|
- do:
|
||||||
xpack.info:
|
xpack.info:
|
||||||
categories: "_none"
|
categories: "_none"
|
||||||
|
|
|
@ -5,7 +5,6 @@
|
||||||
*/
|
*/
|
||||||
package org.elasticsearch.script;
|
package org.elasticsearch.script;
|
||||||
|
|
||||||
import org.elasticsearch.script.ScriptMode;
|
|
||||||
import org.elasticsearch.xpack.common.text.DefaultTextTemplateEngine;
|
import org.elasticsearch.xpack.common.text.DefaultTextTemplateEngine;
|
||||||
|
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
@ -29,8 +28,7 @@ public class MockMustacheScriptEngine extends MockScriptEngine {
|
||||||
}
|
}
|
||||||
|
|
||||||
public void onModule(ScriptModule module) {
|
public void onModule(ScriptModule module) {
|
||||||
module.addScriptEngine(new ScriptEngineRegistry.ScriptEngineRegistration(MockMustacheScriptEngine.class,
|
module.addScriptEngine(new ScriptEngineRegistry.ScriptEngineRegistration(MockMustacheScriptEngine.class, NAME, true));
|
||||||
NAME, ScriptMode.ON));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,7 +7,6 @@ package org.elasticsearch.script;
|
||||||
|
|
||||||
import org.elasticsearch.common.Nullable;
|
import org.elasticsearch.common.Nullable;
|
||||||
import org.elasticsearch.plugins.Plugin;
|
import org.elasticsearch.plugins.Plugin;
|
||||||
import org.elasticsearch.script.ScriptMode;
|
|
||||||
import org.elasticsearch.search.lookup.SearchLookup;
|
import org.elasticsearch.search.lookup.SearchLookup;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
@ -39,7 +38,7 @@ public class SleepScriptEngine implements ScriptEngineService {
|
||||||
|
|
||||||
public void onModule(ScriptModule module) {
|
public void onModule(ScriptModule module) {
|
||||||
module.addScriptEngine(new ScriptEngineRegistry.ScriptEngineRegistration(SleepScriptEngine.class,
|
module.addScriptEngine(new ScriptEngineRegistry.ScriptEngineRegistration(SleepScriptEngine.class,
|
||||||
SleepScriptEngine.NAME, ScriptMode.ON));
|
SleepScriptEngine.NAME, true));
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,6 +6,9 @@
|
||||||
package org.elasticsearch.xpack.watcher.history;
|
package org.elasticsearch.xpack.watcher.history;
|
||||||
|
|
||||||
import org.elasticsearch.action.search.SearchResponse;
|
import org.elasticsearch.action.search.SearchResponse;
|
||||||
|
import org.elasticsearch.common.logging.ESLogger;
|
||||||
|
import org.elasticsearch.common.logging.ESLoggerFactory;
|
||||||
|
import org.elasticsearch.common.logging.Loggers;
|
||||||
import org.elasticsearch.common.settings.Settings;
|
import org.elasticsearch.common.settings.Settings;
|
||||||
import org.elasticsearch.search.aggregations.Aggregations;
|
import org.elasticsearch.search.aggregations.Aggregations;
|
||||||
import org.elasticsearch.search.aggregations.bucket.terms.Terms;
|
import org.elasticsearch.search.aggregations.bucket.terms.Terms;
|
||||||
|
@ -15,6 +18,9 @@ import org.elasticsearch.xpack.watcher.execution.ExecutionState;
|
||||||
import org.elasticsearch.xpack.watcher.test.AbstractWatcherIntegrationTestCase;
|
import org.elasticsearch.xpack.watcher.test.AbstractWatcherIntegrationTestCase;
|
||||||
import org.elasticsearch.xpack.watcher.transport.actions.put.PutWatchResponse;
|
import org.elasticsearch.xpack.watcher.transport.actions.put.PutWatchResponse;
|
||||||
import org.junit.After;
|
import org.junit.After;
|
||||||
|
import org.junit.AfterClass;
|
||||||
|
import org.junit.Before;
|
||||||
|
import org.junit.BeforeClass;
|
||||||
|
|
||||||
import static org.elasticsearch.search.aggregations.AggregationBuilders.terms;
|
import static org.elasticsearch.search.aggregations.AggregationBuilders.terms;
|
||||||
import static org.elasticsearch.search.builder.SearchSourceBuilder.searchSource;
|
import static org.elasticsearch.search.builder.SearchSourceBuilder.searchSource;
|
||||||
|
@ -32,14 +38,17 @@ import static org.hamcrest.Matchers.notNullValue;
|
||||||
* not analyzed so they can be used in aggregations
|
* not analyzed so they can be used in aggregations
|
||||||
*/
|
*/
|
||||||
public class HistoryTemplateEmailMappingsTests extends AbstractWatcherIntegrationTestCase {
|
public class HistoryTemplateEmailMappingsTests extends AbstractWatcherIntegrationTestCase {
|
||||||
|
private static final ESLogger logger = Loggers.getLogger(HistoryTemplateEmailMappingsTests.class);
|
||||||
static final String USERNAME = "_user";
|
static final String USERNAME = "_user";
|
||||||
static final String PASSWORD = "_passwd";
|
static final String PASSWORD = "_passwd";
|
||||||
|
|
||||||
private EmailServer server;
|
private static EmailServer server;
|
||||||
|
|
||||||
@After
|
@AfterClass
|
||||||
public void cleanup() throws Exception {
|
public static void cleanup() throws Exception {
|
||||||
server.stop();
|
if (server != null) {
|
||||||
|
server.stop();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -52,12 +61,16 @@ public class HistoryTemplateEmailMappingsTests extends AbstractWatcherIntegratio
|
||||||
return false; // remove shield noise from this test
|
return false; // remove shield noise from this test
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@BeforeClass
|
||||||
protected Settings nodeSettings(int nodeOrdinal) {
|
public static void setupEmailServer() {
|
||||||
if(server == null) {
|
if(server == null) {
|
||||||
//Need to construct the Email Server here as this happens before init()
|
//Need to construct the Email Server here as this happens before init()
|
||||||
server = EmailServer.localhost("2500-2600", USERNAME, PASSWORD, logger);
|
server = EmailServer.localhost("2500-2600", USERNAME, PASSWORD, logger);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected Settings nodeSettings(int nodeOrdinal) {
|
||||||
return Settings.builder()
|
return Settings.builder()
|
||||||
.put(super.nodeSettings(nodeOrdinal))
|
.put(super.nodeSettings(nodeOrdinal))
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue