forked from opensearch-project/security
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Adds tests for demo configuration java tool (opensearch-project#3807)
### Description This PR adds tests associated with the demo-configuration tool. ## Issues Resolved: - Resolves opensearch-project#3636 ### Testing - Unit Testing - Integration Testing ### Check List - [x] New functionality includes testing ~- [ ] New functionality has been documented~ - [x] Commits are signed per the DCO using --signoff By submitting this pull request, I confirm that my contribution is made under the terms of the Apache 2.0 license. For more information on following Developer Certificate of Origin and signing off your commits, please check [here](https://github.com/opensearch-project/OpenSearch/blob/main/CONTRIBUTING.md#developer-certificate-of-origin). --------- Signed-off-by: Darshit Chanpura <[email protected]> Signed-off-by: Prabhas Kurapati <[email protected]>
- Loading branch information
1 parent
75ee447
commit a57def3
Showing
8 changed files
with
1,173 additions
and
1 deletion.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
50 changes: 50 additions & 0 deletions
50
src/test/java/org/opensearch/security/sanity/tests/InvalidAdminPasswordIT.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,50 @@ | ||
/* | ||
* SPDX-License-Identifier: Apache-2.0 | ||
* | ||
* The OpenSearch Contributors require contributions made to | ||
* this file be licensed under the Apache-2.0 license or a | ||
* compatible open source license. | ||
* | ||
* Modifications Copyright OpenSearch Contributors. See | ||
* GitHub history for details. | ||
*/ | ||
|
||
package org.opensearch.security.sanity.tests; | ||
|
||
import org.hamcrest.MatcherAssert; | ||
import org.junit.AfterClass; | ||
import org.junit.BeforeClass; | ||
import org.junit.Test; | ||
|
||
import org.opensearch.client.Request; | ||
import org.opensearch.client.Response; | ||
import org.opensearch.client.ResponseException; | ||
|
||
import static org.hamcrest.Matchers.equalTo; | ||
import static org.hamcrest.Matchers.is; | ||
|
||
public class InvalidAdminPasswordIT extends SecurityRestTestCase { | ||
|
||
static String currentPasswordVariable = System.getProperty("password"); | ||
|
||
@BeforeClass | ||
public static void setUpAdminAsPasswordVariable() { | ||
System.setProperty("password", "admin"); | ||
} | ||
|
||
@AfterClass | ||
public static void restorePasswordProperty() { | ||
System.setProperty("password", currentPasswordVariable); | ||
} | ||
|
||
@Test | ||
public void testAdminCredentials_adminAsPassword_shouldFail() throws Exception { | ||
try { | ||
client().performRequest(new Request("GET", "")); | ||
} catch (ResponseException e) { | ||
Response res = e.getResponse(); | ||
MatcherAssert.assertThat(res.getStatusLine().getStatusCode(), is(equalTo(401))); | ||
MatcherAssert.assertThat(res.getStatusLine().getReasonPhrase(), is(equalTo("Unauthorized"))); | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
178 changes: 178 additions & 0 deletions
178
src/test/java/org/opensearch/security/tools/democonfig/CertificateGeneratorTests.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,178 @@ | ||
/* | ||
* SPDX-License-Identifier: Apache-2.0 | ||
* | ||
* The OpenSearch Contributors require contributions made to | ||
* this file be licensed under the Apache-2.0 license or a | ||
* compatible open source license. | ||
* | ||
* Modifications Copyright OpenSearch Contributors. See | ||
* GitHub history for details. | ||
*/ | ||
|
||
package org.opensearch.security.tools.democonfig; | ||
|
||
import java.io.BufferedReader; | ||
import java.io.File; | ||
import java.io.FileInputStream; | ||
import java.io.FileReader; | ||
import java.security.KeyFactory; | ||
import java.security.PrivateKey; | ||
import java.security.cert.Certificate; | ||
import java.security.cert.CertificateFactory; | ||
import java.security.cert.X509Certificate; | ||
import java.security.spec.PKCS8EncodedKeySpec; | ||
import java.time.Instant; | ||
import java.time.LocalDate; | ||
import java.time.Period; | ||
import java.util.Base64; | ||
import java.util.Date; | ||
import java.util.TimeZone; | ||
|
||
import org.junit.After; | ||
import org.junit.Before; | ||
import org.junit.Test; | ||
|
||
import org.opensearch.security.tools.democonfig.util.NoExitSecurityManager; | ||
|
||
import static org.hamcrest.MatcherAssert.assertThat; | ||
import static org.hamcrest.Matchers.equalTo; | ||
import static org.hamcrest.Matchers.greaterThanOrEqualTo; | ||
import static org.hamcrest.Matchers.is; | ||
import static org.opensearch.security.tools.democonfig.util.DemoConfigHelperUtil.createDirectory; | ||
import static org.opensearch.security.tools.democonfig.util.DemoConfigHelperUtil.deleteDirectoryRecursive; | ||
import static org.junit.Assert.fail; | ||
|
||
public class CertificateGeneratorTests { | ||
|
||
private static Installer installer; | ||
|
||
@Before | ||
public void setUp() { | ||
installer = Installer.getInstance(); | ||
installer.buildOptions(); | ||
installer.OPENSEARCH_CONF_DIR = System.getProperty("user.dir") + File.separator + "test-conf"; | ||
createDirectory(installer.OPENSEARCH_CONF_DIR); | ||
} | ||
|
||
@After | ||
public void tearDown() { | ||
deleteDirectoryRecursive(installer.OPENSEARCH_CONF_DIR); | ||
Installer.resetInstance(); | ||
} | ||
|
||
@Test | ||
public void testCreateDemoCertificates() throws Exception { | ||
CertificateGenerator certificateGenerator = new CertificateGenerator(installer); | ||
Certificates[] certificatesArray = Certificates.values(); | ||
|
||
certificateGenerator.createDemoCertificates(); | ||
|
||
// root-ca.pem, esnode.pem, esnode-key.pem, kirk.pem, kirk-key.pem | ||
int expectedNumberOfCertificateFiles = 5; | ||
|
||
int certsFound = 0; | ||
|
||
for (Certificates cert : certificatesArray) { | ||
String certFilePath = installer.OPENSEARCH_CONF_DIR + File.separator + cert.getFileName(); | ||
File certFile = new File(certFilePath); | ||
assertThat(certFile.exists(), is(equalTo(true))); | ||
assertThat(certFile.canRead(), is(equalTo(true))); | ||
|
||
if (certFilePath.endsWith("-key.pem")) { | ||
checkPrivateKeyValidity(certFilePath); | ||
} else { | ||
checkCertificateValidity(certFilePath); | ||
} | ||
|
||
// increment a count since a valid certificate was found | ||
certsFound++; | ||
} | ||
|
||
assertThat(certsFound, equalTo(expectedNumberOfCertificateFiles)); | ||
} | ||
|
||
@Test | ||
public void testCreateDemoCertificates_invalidPath() { | ||
installer.OPENSEARCH_CONF_DIR = "invalidPath"; | ||
CertificateGenerator certificateGenerator = new CertificateGenerator(installer); | ||
try { | ||
System.setSecurityManager(new NoExitSecurityManager()); | ||
certificateGenerator.createDemoCertificates(); | ||
} catch (SecurityException e) { | ||
assertThat(e.getMessage(), equalTo("System.exit(-1) blocked to allow print statement testing.")); | ||
} finally { | ||
System.setSecurityManager(null); | ||
} | ||
} | ||
|
||
private static void checkCertificateValidity(String certPath) throws Exception { | ||
try (FileInputStream certInputStream = new FileInputStream(certPath)) { | ||
CertificateFactory cf = CertificateFactory.getInstance("X.509"); | ||
Certificate certificate = cf.generateCertificate(certInputStream); | ||
|
||
if (certificate instanceof X509Certificate) { | ||
X509Certificate x509Certificate = (X509Certificate) certificate; | ||
Date expiryDate = x509Certificate.getNotAfter(); | ||
Instant expiry = expiryDate.toInstant(); | ||
|
||
Period duration = getPeriodBetween(x509Certificate.getNotBefore().toInstant(), expiry); | ||
if (certPath.endsWith("-ca.pem")) { | ||
// root-ca.pem is already expired as the validity is only 30 days from generation | ||
// so we just check interval to be of 30 days | ||
assertThat(duration.getDays(), equalTo(30)); | ||
return; | ||
} | ||
|
||
// we check that cert is valid for total of ~10 yrs | ||
// we don't check days as leaps years may cause flaky-ness | ||
assertThat(duration.getYears(), equalTo(9)); | ||
assertThat(duration.getMonths(), equalTo(11)); | ||
|
||
x509Certificate.checkValidity(); | ||
verifyExpiryAtLeastAYearFromNow(expiry); | ||
|
||
assertThat(x509Certificate.getSigAlgName(), is(equalTo("SHA256withRSA"))); | ||
} | ||
} | ||
} | ||
|
||
private static void verifyExpiryAtLeastAYearFromNow(Instant expiry) { | ||
Period gap = getPeriodBetween(Instant.now(), expiry); | ||
assertThat(gap.getYears(), greaterThanOrEqualTo(1)); | ||
} | ||
|
||
private static Period getPeriodBetween(Instant start, Instant end) { | ||
LocalDate startDate = LocalDate.ofInstant(start, TimeZone.getTimeZone("EDT").toZoneId()); | ||
LocalDate endDate = LocalDate.ofInstant(end, TimeZone.getTimeZone("EDT").toZoneId()); | ||
|
||
return Period.between(startDate, endDate); | ||
} | ||
|
||
private void checkPrivateKeyValidity(String keyPath) { | ||
try { | ||
String pemContent = readPEMFile(keyPath); | ||
|
||
String base64Data = pemContent.replaceAll("-----BEGIN PRIVATE KEY-----|-----END PRIVATE KEY-----", "").replaceAll("\\s", ""); | ||
|
||
byte[] keyBytes = Base64.getDecoder().decode(base64Data); | ||
KeyFactory kf = KeyFactory.getInstance("RSA"); | ||
PrivateKey key = kf.generatePrivate(new PKCS8EncodedKeySpec(keyBytes)); | ||
assertThat(key.getFormat(), is(equalTo("PKCS#8"))); | ||
assertThat(key.getAlgorithm(), is(equalTo("RSA"))); | ||
assertThat(key.isDestroyed(), is(equalTo(false))); | ||
} catch (Exception e) { | ||
fail("Error checking key validity: " + e.getMessage()); | ||
} | ||
} | ||
|
||
private static String readPEMFile(String pemFilePath) throws Exception { | ||
StringBuilder pemContent = new StringBuilder(); | ||
try (BufferedReader reader = new BufferedReader(new FileReader(pemFilePath))) { | ||
String line; | ||
while ((line = reader.readLine()) != null) { | ||
pemContent.append(line).append("\n"); | ||
} | ||
} | ||
return pemContent.toString(); | ||
} | ||
} |
Oops, something went wrong.