Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
Show all changes
27 commits
Select commit Hold shift + click to select a range
e4fc0a0
feat: support keystore in transport for mtls
arithmetic1728 Oct 15, 2020
3f3d403
fix format
arithmetic1728 Oct 15, 2020
0feec05
update code
arithmetic1728 Oct 15, 2020
a71a009
add tests
arithmetic1728 Oct 16, 2020
3c10eaa
update test and doc
arithmetic1728 Oct 16, 2020
275bad0
update names
arithmetic1728 Oct 23, 2020
e21791c
create keystore from cert and key string
arithmetic1728 Oct 23, 2020
2edb134
change certAndKey from string to inputstream
arithmetic1728 Oct 26, 2020
09847d7
add mtls file
arithmetic1728 Oct 27, 2020
c4bc00d
Update google-http-client/src/main/java/com/google/api/client/http/ja…
arithmetic1728 Oct 29, 2020
a97ea3d
Update google-http-client/src/main/java/com/google/api/client/http/ja…
arithmetic1728 Oct 29, 2020
7469467
Update google-http-client/src/main/java/com/google/api/client/util/Ss…
arithmetic1728 Oct 29, 2020
a61ed1a
Update google-http-client/src/main/java/com/google/api/client/util/Ss…
arithmetic1728 Oct 29, 2020
93c3452
Update google-http-client/src/test/java/com/google/api/client/util/Se…
arithmetic1728 Oct 29, 2020
d195f65
Update google-http-client/src/main/java/com/google/api/client/util/Ss…
arithmetic1728 Oct 29, 2020
13d7d19
update the code
arithmetic1728 Oct 29, 2020
bade79a
fix name
arithmetic1728 Oct 29, 2020
a8d60ea
chore: add Beta annotation for new mtls functions
arithmetic1728 Oct 30, 2020
271c262
resolve conflict
arithmetic1728 Oct 30, 2020
eb9a90d
update Beta
arithmetic1728 Oct 30, 2020
f90ac74
add since tag
arithmetic1728 Oct 30, 2020
509c481
Merge branch 'master' of https://github.com/googleapis/google-http-ja…
arithmetic1728 Oct 31, 2020
fc72936
feat: add isMtls property to ApacheHttpTransport
arithmetic1728 Oct 29, 2020
02e53d2
update Beta annotation
arithmetic1728 Oct 31, 2020
254675e
format
arithmetic1728 Nov 1, 2020
f477636
Merge pull request #2 from arithmetic1728/apache
arithmetic1728 Nov 1, 2020
a14cac4
fix tag
arithmetic1728 Nov 1, 2020
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
change certAndKey from string to inputstream
  • Loading branch information
arithmetic1728 committed Oct 26, 2020
commit 2edb1346b65ef8cc4fe51dfaa28377785240fff0
Original file line number Diff line number Diff line change
Expand Up @@ -263,51 +263,48 @@ public static void loadKeyStoreFromCertificates(
/**
* Create a keystore for mutual TLS with the certificate and private key provided.
*
* <p>certAndKey should have the following format:
*
* <pre>
* -----BEGIN CERTIFICATE-----
* ......
* -----END CERTIFICATE------
* ----BEGIN PRIVATE KEY-----
* ......
* -----END PRIVATE KEY-----
* </pre>
*
* @param certAndKey Concatenation of a x509 certificate PEM string and a PKCS#8 unencrypted
* private key PEM string.
* @param certAndKey Certificate and private key input stream. The stream should contain one
* certificate and one unencrypted private key. If there are multiple certificates, only the
* first certificate will be used.
* @return keystore for mutual TLS.
*/
public static KeyStore createMtlsKeyStore(String certAndKey)
public static KeyStore createMtlsKeyStore(InputStream certAndKey)
throws GeneralSecurityException, IOException {
KeyStore keystore = KeyStore.getInstance("JKS");
try {
keystore.load(null);
} catch (IOException ignored) {
// shouldn't throw any exception to load a null keystore.
}
keystore.load(null);

PemReader.Section certSection = null;
PemReader.Section keySection = null;
PemReader reader = new PemReader(new InputStreamReader(certAndKey));

while (certSection == null || keySection == null) {
// Read the certificate and private key.
PemReader.Section section = reader.readNextSection();
if (section == null) {
break;
}

byte[] certAndKeyBytes = certAndKey.getBytes();
if ("CERTIFICATE".equals(section.getTitle())) {
certSection = section;
} else if ("PRIVATE KEY".equals(section.getTitle())) {
keySection = section;
}
}

// Read the certificate.
InputStreamReader reader = new InputStreamReader(new ByteArrayInputStream(certAndKeyBytes));
PemReader.Section section = PemReader.readFirstSectionAndClose(reader, "CERTIFICATE");
if (section == null) {
if (certSection == null) {
throw new IllegalArgumentException("certificate is missing from certAndKey string");
}
if (keySection == null) {
throw new IllegalArgumentException("private key is missing from certAndKey string");
}

CertificateFactory certFactory = CertificateFactory.getInstance("X.509");
X509Certificate cert =
(X509Certificate)
certFactory.generateCertificate(
new ByteArrayInputStream(section.getBase64DecodedBytes()));
new ByteArrayInputStream(certSection.getBase64DecodedBytes()));

// Read the private key.
reader = new InputStreamReader(new ByteArrayInputStream(certAndKeyBytes));
section = PemReader.readFirstSectionAndClose(reader, "PRIVATE KEY");
if (section == null) {
throw new IllegalArgumentException("private key is missing from certAndKey string");
}
PKCS8EncodedKeySpec keySpecPKCS8 = new PKCS8EncodedKeySpec(section.getBase64DecodedBytes());
PKCS8EncodedKeySpec keySpecPKCS8 = new PKCS8EncodedKeySpec(keySection.getBase64DecodedBytes());
PrivateKey key =
KeyFactory.getInstance(cert.getPublicKey().getAlgorithm()).generatePrivate(keySpecPKCS8);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
import com.google.api.client.testing.util.SecurityTestUtils;
import com.google.common.io.Resources;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.net.URL;
import java.nio.charset.StandardCharsets;
import java.security.KeyStore;
Expand Down Expand Up @@ -170,8 +171,10 @@ public void testVerifyX509WrongCa() throws Exception {
}

public void testCreateMtlsKeyStoreNoCert() throws Exception {
URL url = getClass().getClassLoader().getResource("com/google/api/client/util/privateKey.pem");
final String certMissing = Resources.toString(url, StandardCharsets.UTF_8);
final InputStream certMissing =
getClass()
.getClassLoader()
.getResourceAsStream("com/google/api/client/util/privateKey.pem");
IllegalArgumentException exception =
assertThrows(
IllegalArgumentException.class,
Expand All @@ -187,8 +190,8 @@ public void run() throws Throwable {
}

public void testCreateMtlsKeyStoreNoPrivateKey() throws Exception {
URL url = getClass().getClassLoader().getResource("com/google/api/client/util/cert.pem");
final String privateKeyMissing = Resources.toString(url, StandardCharsets.UTF_8);
final InputStream privateKeyMissing =
getClass().getClassLoader().getResourceAsStream("com/google/api/client/util/cert.pem");
IllegalArgumentException exception =
assertThrows(
IllegalArgumentException.class,
Expand All @@ -210,7 +213,9 @@ public void testCreateMtlsKeyStoreSuccess() throws Exception {
url = getClass().getClassLoader().getResource("com/google/api/client/util/privateKey.pem");
String privateKey = Resources.toString(url, StandardCharsets.UTF_8);

String certAndKey = cert + "\n" + privateKey;
String certAndKeyString = privateKey + "\n" + cert;
ByteArrayInputStream certAndKey = new ByteArrayInputStream(certAndKeyString.getBytes());

KeyStore mtlsKeyStore = SecurityUtils.createMtlsKeyStore(certAndKey);

assertEquals(mtlsKeyStore.size(), 1);
Expand Down