1 // Copyright 2020 Google LLC 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 // 15 //////////////////////////////////////////////////////////////////////////////// 16 17 package com.google.crypto.tink.testing; 18 19 import static com.google.common.truth.Truth.assertThat; 20 import static java.nio.charset.StandardCharsets.UTF_8; 21 import static java.util.concurrent.TimeUnit.SECONDS; 22 import static org.junit.Assert.assertThrows; 23 24 import com.google.crypto.tink.InsecureSecretKeyAccess; 25 import com.google.crypto.tink.KeyTemplate; 26 import com.google.crypto.tink.KeyTemplates; 27 import com.google.crypto.tink.KeysetHandle; 28 import com.google.crypto.tink.TinkProtoKeysetFormat; 29 import com.google.crypto.tink.config.TinkConfig; 30 import com.google.crypto.tink.daead.AesSivKeyManager; 31 import com.google.crypto.tink.internal.KeyTemplateProtoConverter; 32 import com.google.crypto.tink.mac.HmacKeyManager; 33 import com.google.crypto.tink.prf.HmacPrfKeyManager; 34 import com.google.crypto.tink.streamingaead.AesGcmHkdfStreamingKeyManager; 35 import com.google.crypto.tink.testing.proto.AeadDecryptRequest; 36 import com.google.crypto.tink.testing.proto.AeadDecryptResponse; 37 import com.google.crypto.tink.testing.proto.AeadEncryptRequest; 38 import com.google.crypto.tink.testing.proto.AeadEncryptResponse; 39 import com.google.crypto.tink.testing.proto.AeadGrpc; 40 import com.google.crypto.tink.testing.proto.AnnotatedKeyset; 41 import com.google.crypto.tink.testing.proto.BytesValue; 42 import com.google.crypto.tink.testing.proto.ComputeMacRequest; 43 import com.google.crypto.tink.testing.proto.ComputeMacResponse; 44 import com.google.crypto.tink.testing.proto.CreationRequest; 45 import com.google.crypto.tink.testing.proto.CreationResponse; 46 import com.google.crypto.tink.testing.proto.DeterministicAeadDecryptRequest; 47 import com.google.crypto.tink.testing.proto.DeterministicAeadDecryptResponse; 48 import com.google.crypto.tink.testing.proto.DeterministicAeadEncryptRequest; 49 import com.google.crypto.tink.testing.proto.DeterministicAeadEncryptResponse; 50 import com.google.crypto.tink.testing.proto.DeterministicAeadGrpc; 51 import com.google.crypto.tink.testing.proto.KeysetFromJsonRequest; 52 import com.google.crypto.tink.testing.proto.KeysetFromJsonResponse; 53 import com.google.crypto.tink.testing.proto.KeysetGenerateRequest; 54 import com.google.crypto.tink.testing.proto.KeysetGenerateResponse; 55 import com.google.crypto.tink.testing.proto.KeysetGrpc; 56 import com.google.crypto.tink.testing.proto.KeysetReadEncryptedRequest; 57 import com.google.crypto.tink.testing.proto.KeysetReadEncryptedResponse; 58 import com.google.crypto.tink.testing.proto.KeysetReaderType; 59 import com.google.crypto.tink.testing.proto.KeysetTemplateRequest; 60 import com.google.crypto.tink.testing.proto.KeysetTemplateResponse; 61 import com.google.crypto.tink.testing.proto.KeysetToJsonRequest; 62 import com.google.crypto.tink.testing.proto.KeysetToJsonResponse; 63 import com.google.crypto.tink.testing.proto.KeysetWriteEncryptedRequest; 64 import com.google.crypto.tink.testing.proto.KeysetWriteEncryptedResponse; 65 import com.google.crypto.tink.testing.proto.KeysetWriterType; 66 import com.google.crypto.tink.testing.proto.MacGrpc; 67 import com.google.crypto.tink.testing.proto.MetadataGrpc; 68 import com.google.crypto.tink.testing.proto.PrfSetComputeRequest; 69 import com.google.crypto.tink.testing.proto.PrfSetComputeResponse; 70 import com.google.crypto.tink.testing.proto.PrfSetGrpc; 71 import com.google.crypto.tink.testing.proto.PrfSetKeyIdsRequest; 72 import com.google.crypto.tink.testing.proto.PrfSetKeyIdsResponse; 73 import com.google.crypto.tink.testing.proto.ServerInfoRequest; 74 import com.google.crypto.tink.testing.proto.ServerInfoResponse; 75 import com.google.crypto.tink.testing.proto.StreamingAeadDecryptRequest; 76 import com.google.crypto.tink.testing.proto.StreamingAeadDecryptResponse; 77 import com.google.crypto.tink.testing.proto.StreamingAeadEncryptRequest; 78 import com.google.crypto.tink.testing.proto.StreamingAeadEncryptResponse; 79 import com.google.crypto.tink.testing.proto.StreamingAeadGrpc; 80 import com.google.crypto.tink.testing.proto.VerifyMacRequest; 81 import com.google.crypto.tink.testing.proto.VerifyMacResponse; 82 import com.google.protobuf.ByteString; 83 import io.grpc.ManagedChannel; 84 import io.grpc.Server; 85 import io.grpc.StatusRuntimeException; 86 import io.grpc.inprocess.InProcessChannelBuilder; 87 import io.grpc.inprocess.InProcessServerBuilder; 88 import java.util.Optional; 89 import org.junit.After; 90 import org.junit.Before; 91 import org.junit.Test; 92 import org.junit.runner.RunWith; 93 import org.junit.runners.JUnit4; 94 95 @RunWith(JUnit4.class) 96 public final class TestingServicesTest { 97 private Server server; 98 private ManagedChannel channel; 99 MetadataGrpc.MetadataBlockingStub metadataStub; 100 KeysetGrpc.KeysetBlockingStub keysetStub; 101 AeadGrpc.AeadBlockingStub aeadStub; 102 DeterministicAeadGrpc.DeterministicAeadBlockingStub daeadStub; 103 StreamingAeadGrpc.StreamingAeadBlockingStub streamingAeadStub; 104 MacGrpc.MacBlockingStub macStub; 105 PrfSetGrpc.PrfSetBlockingStub prfSetStub; 106 107 @Before setUp()108 public void setUp() throws Exception { 109 TinkConfig.register(); 110 String serverName = InProcessServerBuilder.generateName(); 111 server = 112 InProcessServerBuilder.forName(serverName) 113 .directExecutor() 114 .addService(new MetadataServiceImpl()) 115 .addService(new KeysetServiceImpl()) 116 .addService(new AeadServiceImpl()) 117 .addService(new DeterministicAeadServiceImpl()) 118 .addService(new StreamingAeadServiceImpl()) 119 .addService(new MacServiceImpl()) 120 .addService(new PrfSetServiceImpl()) 121 .build() 122 .start(); 123 channel = InProcessChannelBuilder.forName(serverName).directExecutor().build(); 124 metadataStub = MetadataGrpc.newBlockingStub(channel); 125 keysetStub = KeysetGrpc.newBlockingStub(channel); 126 aeadStub = AeadGrpc.newBlockingStub(channel); 127 daeadStub = DeterministicAeadGrpc.newBlockingStub(channel); 128 streamingAeadStub = StreamingAeadGrpc.newBlockingStub(channel); 129 macStub = MacGrpc.newBlockingStub(channel); 130 prfSetStub = PrfSetGrpc.newBlockingStub(channel); 131 } 132 133 @After tearDown()134 public void tearDown() throws Exception { 135 assertThat(channel.shutdown().awaitTermination(5, SECONDS)).isTrue(); 136 assertThat(server.shutdown().awaitTermination(5, SECONDS)).isTrue(); 137 } 138 generateKeyset( KeysetGrpc.KeysetBlockingStub keysetStub, byte[] template)139 private static KeysetGenerateResponse generateKeyset( 140 KeysetGrpc.KeysetBlockingStub keysetStub, byte[] template) { 141 KeysetGenerateRequest genRequest = 142 KeysetGenerateRequest.newBuilder().setTemplate(ByteString.copyFrom(template)).build(); 143 return keysetStub.generate(genRequest); 144 } 145 keysetToJson( KeysetGrpc.KeysetBlockingStub keysetStub, byte[] keyset)146 private static KeysetToJsonResponse keysetToJson( 147 KeysetGrpc.KeysetBlockingStub keysetStub, byte[] keyset) { 148 KeysetToJsonRequest request = 149 KeysetToJsonRequest.newBuilder().setKeyset(ByteString.copyFrom(keyset)).build(); 150 return keysetStub.toJson(request); 151 } 152 keysetFromJson( KeysetGrpc.KeysetBlockingStub keysetStub, String jsonKeyset)153 private static KeysetFromJsonResponse keysetFromJson( 154 KeysetGrpc.KeysetBlockingStub keysetStub, String jsonKeyset) { 155 KeysetFromJsonRequest request = 156 KeysetFromJsonRequest.newBuilder().setJsonKeyset(jsonKeyset).build(); 157 return keysetStub.fromJson(request); 158 } 159 160 @Test template_success()161 public void template_success() throws Exception { 162 KeysetTemplateRequest request = 163 KeysetTemplateRequest.newBuilder().setTemplateName("AES256_GCM").build(); 164 KeysetTemplateResponse response = keysetStub.getTemplate(request); 165 assertThat(response.getErr()).isEmpty(); 166 KeyTemplate template = 167 KeyTemplateProtoConverter.fromByteArray(response.getKeyTemplate().toByteArray()); 168 assertThat(template.toParameters()).isEqualTo(KeyTemplates.get("AES256_GCM").toParameters()); 169 } 170 171 @Test template_not_found()172 public void template_not_found() throws Exception { 173 KeysetTemplateRequest request = 174 KeysetTemplateRequest.newBuilder().setTemplateName("UNKNOWN_TEMPLATE").build(); 175 KeysetTemplateResponse response = keysetStub.getTemplate(request); 176 assertThat(response.getErr()).isNotEmpty(); 177 } 178 179 @Test fromJson_success()180 public void fromJson_success() throws Exception { 181 String jsonKeyset = 182 "" 183 + "{" 184 + " \"primaryKeyId\": 42," 185 + " \"key\": [" 186 + " {" 187 + " \"keyData\": {" 188 + " \"typeUrl\": \"type.googleapis.com/google.crypto.tink.AesGcmKey\"," 189 + " \"keyMaterialType\": \"SYMMETRIC\"," 190 + " \"value\": \"GhCC74uJ+2f4qlpaHwR4ylNQ\"" 191 + " }," 192 + " \"outputPrefixType\": \"TINK\"," 193 + " \"keyId\": 42," 194 + " \"status\": \"ENABLED\"" 195 + " }" 196 + " ]" 197 + "}"; 198 KeysetFromJsonResponse fromResponse = keysetFromJson(keysetStub, jsonKeyset); 199 assertThat(fromResponse.getErr()).isEmpty(); 200 byte[] serializedKeyset = fromResponse.getKeyset().toByteArray(); 201 202 KeysetHandle parseKeysetHandle = 203 TinkProtoKeysetFormat.parseKeyset(serializedKeyset, InsecureSecretKeyAccess.get()); 204 assertThat(parseKeysetHandle.getPrimary().getId()).isEqualTo(42); 205 } 206 207 @Test toFromJson_success()208 public void toFromJson_success() throws Exception { 209 byte[] template = KeyTemplateProtoConverter.toByteArray(KeyTemplates.get("AES128_GCM")); 210 211 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 212 assertThat(keysetResponse.getErr()).isEmpty(); 213 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 214 215 KeysetToJsonResponse toResponse = keysetToJson(keysetStub, keyset); 216 assertThat(toResponse.getErr()).isEmpty(); 217 String jsonKeyset = toResponse.getJsonKeyset(); 218 219 KeysetFromJsonResponse fromResponse = keysetFromJson(keysetStub, jsonKeyset); 220 assertThat(fromResponse.getErr()).isEmpty(); 221 byte[] output = fromResponse.getKeyset().toByteArray(); 222 223 assertThat(output).isEqualTo(keyset); 224 } 225 keysetReadEncrypted( KeysetGrpc.KeysetBlockingStub keysetStub, byte[] encryptedKeyset, byte[] masterKeyset, Optional<byte[]> associatedData)226 private static KeysetReadEncryptedResponse keysetReadEncrypted( 227 KeysetGrpc.KeysetBlockingStub keysetStub, 228 byte[] encryptedKeyset, 229 byte[] masterKeyset, 230 Optional<byte[]> associatedData) { 231 KeysetReadEncryptedRequest.Builder requestBuilder = 232 KeysetReadEncryptedRequest.newBuilder() 233 .setEncryptedKeyset(ByteString.copyFrom(encryptedKeyset)) 234 .setMasterKeyset(ByteString.copyFrom(masterKeyset)) 235 .setKeysetReaderType(KeysetReaderType.KEYSET_READER_BINARY); 236 if (associatedData.isPresent()) { 237 requestBuilder.setAssociatedData( 238 BytesValue.newBuilder().setValue(ByteString.copyFrom(associatedData.get())).build()); 239 } 240 return keysetStub.readEncrypted(requestBuilder.build()); 241 } 242 keysetWriteEncrypted( KeysetGrpc.KeysetBlockingStub keysetStub, byte[] keyset, byte[] masterKeyset, Optional<byte[]> associatedData)243 private static KeysetWriteEncryptedResponse keysetWriteEncrypted( 244 KeysetGrpc.KeysetBlockingStub keysetStub, 245 byte[] keyset, 246 byte[] masterKeyset, 247 Optional<byte[]> associatedData) { 248 KeysetWriteEncryptedRequest.Builder requestBuilder = 249 KeysetWriteEncryptedRequest.newBuilder() 250 .setKeyset(ByteString.copyFrom(keyset)) 251 .setMasterKeyset(ByteString.copyFrom(masterKeyset)) 252 .setKeysetWriterType(KeysetWriterType.KEYSET_WRITER_BINARY); 253 if (associatedData.isPresent()) { 254 requestBuilder.setAssociatedData( 255 BytesValue.newBuilder().setValue(ByteString.copyFrom(associatedData.get())).build()); 256 } 257 return keysetStub.writeEncrypted(requestBuilder.build()); 258 } 259 260 @Test generateEncryptDecryptKeyset()261 public void generateEncryptDecryptKeyset() throws Exception { 262 byte[] template = KeyTemplateProtoConverter.toByteArray(KeyTemplates.get("AES128_GCM")); 263 264 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 265 assertThat(keysetResponse.getErr()).isEmpty(); 266 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 267 268 KeysetGenerateResponse masterKeysetResponse = generateKeyset(keysetStub, template); 269 assertThat(masterKeysetResponse.getErr()).isEmpty(); 270 byte[] masterKeyset = masterKeysetResponse.getKeyset().toByteArray(); 271 272 KeysetWriteEncryptedResponse writeResponse = 273 keysetWriteEncrypted( 274 keysetStub, keyset, masterKeyset, /*associatedData=*/ Optional.empty()); 275 assertThat(writeResponse.getErr()).isEmpty(); 276 byte[] encryptedKeyset = writeResponse.getEncryptedKeyset().toByteArray(); 277 278 assertThat(encryptedKeyset).isNotEqualTo(keyset); 279 280 KeysetReadEncryptedResponse readResponse = 281 keysetReadEncrypted( 282 keysetStub, encryptedKeyset, masterKeyset, /*associatedData=*/ Optional.empty()); 283 assertThat(readResponse.getErr()).isEmpty(); 284 byte[] output = readResponse.getKeyset().toByteArray(); 285 286 assertThat(output).isEqualTo(keyset); 287 288 // Empty associated data should be the same as no associated data. 289 KeysetReadEncryptedResponse readResponseWithEmptyAssociatedData = 290 keysetReadEncrypted( 291 keysetStub, 292 encryptedKeyset, 293 masterKeyset, 294 /*associatedData=*/ Optional.of(new byte[0])); 295 assertThat(readResponseWithEmptyAssociatedData.getErr()).isEmpty(); 296 assertThat(readResponseWithEmptyAssociatedData.getKeyset().toByteArray()).isEqualTo(keyset); 297 298 KeysetReadEncryptedResponse readResponseWithInvalidAssociatedData = 299 keysetReadEncrypted( 300 keysetStub, 301 encryptedKeyset, 302 masterKeyset, 303 Optional.of("invalidAssociatedData".getBytes(UTF_8))); 304 assertThat(readResponseWithInvalidAssociatedData.getErr()).isNotEmpty(); 305 } 306 307 @Test generateEncryptDecryptKeysetWithAssociatedData()308 public void generateEncryptDecryptKeysetWithAssociatedData() throws Exception { 309 byte[] template = KeyTemplateProtoConverter.toByteArray(KeyTemplates.get("AES128_GCM")); 310 byte[] associatedData = "a".getBytes(UTF_8); 311 312 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 313 assertThat(keysetResponse.getErr()).isEmpty(); 314 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 315 316 KeysetGenerateResponse masterKeysetResponse = generateKeyset(keysetStub, template); 317 assertThat(masterKeysetResponse.getErr()).isEmpty(); 318 byte[] masterKeyset = masterKeysetResponse.getKeyset().toByteArray(); 319 320 KeysetWriteEncryptedResponse writeResponse = 321 keysetWriteEncrypted(keysetStub, keyset, masterKeyset, Optional.of(associatedData)); 322 assertThat(writeResponse.getErr()).isEmpty(); 323 byte[] encryptedKeyset = writeResponse.getEncryptedKeyset().toByteArray(); 324 325 assertThat(encryptedKeyset).isNotEqualTo(keyset); 326 327 KeysetReadEncryptedResponse readResponse = 328 keysetReadEncrypted(keysetStub, encryptedKeyset, masterKeyset, Optional.of(associatedData)); 329 assertThat(readResponse.getErr()).isEmpty(); 330 byte[] output = readResponse.getKeyset().toByteArray(); 331 332 assertThat(output).isEqualTo(keyset); 333 334 KeysetReadEncryptedResponse readResponseWithInvalidAssociatedData = 335 keysetReadEncrypted( 336 keysetStub, 337 encryptedKeyset, 338 masterKeyset, 339 Optional.of("invalidAssociatedData".getBytes(UTF_8))); 340 assertThat(readResponseWithInvalidAssociatedData.getErr()).isNotEmpty(); 341 342 KeysetReadEncryptedResponse readResponseWithoutAssociatedData = 343 keysetReadEncrypted( 344 keysetStub, encryptedKeyset, masterKeyset, /*associatedData=*/ Optional.empty()); 345 assertThat(readResponseWithoutAssociatedData.getErr()).isNotEmpty(); 346 } 347 348 @Test generateEncryptDecryptKeysetWithEmptyAssociatedData()349 public void generateEncryptDecryptKeysetWithEmptyAssociatedData() throws Exception { 350 byte[] template = KeyTemplateProtoConverter.toByteArray(KeyTemplates.get("AES128_GCM")); 351 byte[] emptyAssociatedData = new byte[0]; 352 353 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 354 assertThat(keysetResponse.getErr()).isEmpty(); 355 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 356 357 KeysetGenerateResponse masterKeysetResponse = generateKeyset(keysetStub, template); 358 assertThat(masterKeysetResponse.getErr()).isEmpty(); 359 byte[] masterKeyset = masterKeysetResponse.getKeyset().toByteArray(); 360 361 KeysetWriteEncryptedResponse writeResponse = 362 keysetWriteEncrypted(keysetStub, keyset, masterKeyset, Optional.of(emptyAssociatedData)); 363 assertThat(writeResponse.getErr()).isEmpty(); 364 byte[] encryptedKeyset = writeResponse.getEncryptedKeyset().toByteArray(); 365 366 assertThat(encryptedKeyset).isNotEqualTo(keyset); 367 368 KeysetReadEncryptedResponse readResponse = 369 keysetReadEncrypted( 370 keysetStub, encryptedKeyset, masterKeyset, Optional.of(emptyAssociatedData)); 371 assertThat(readResponse.getErr()).isEmpty(); 372 byte[] output = readResponse.getKeyset().toByteArray(); 373 assertThat(output).isEqualTo(keyset); 374 375 KeysetReadEncryptedResponse readResponseWithoutAssociatedData = 376 keysetReadEncrypted(keysetStub, encryptedKeyset, masterKeyset, Optional.empty()); 377 assertThat(readResponseWithoutAssociatedData.getErr()).isEmpty(); 378 assertThat(readResponseWithoutAssociatedData.getKeyset().toByteArray()).isEqualTo(keyset); 379 } 380 381 @Test encryptDecryptInvalidKeyset_fails()382 public void encryptDecryptInvalidKeyset_fails() throws Exception { 383 byte[] invalidData = "invalid".getBytes(UTF_8); 384 byte[] template = KeyTemplateProtoConverter.toByteArray(KeyTemplates.get("AES128_GCM")); 385 386 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 387 assertThat(keysetResponse.getErr()).isEmpty(); 388 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 389 390 KeysetGenerateResponse masterKeysetResponse = generateKeyset(keysetStub, template); 391 assertThat(masterKeysetResponse.getErr()).isEmpty(); 392 byte[] masterKeyset = masterKeysetResponse.getKeyset().toByteArray(); 393 394 KeysetWriteEncryptedResponse writeResponse1 = 395 keysetWriteEncrypted(keysetStub, keyset, invalidData, /*associatedData=*/ Optional.empty()); 396 assertThat(writeResponse1.getErr()).isNotEmpty(); 397 398 KeysetWriteEncryptedResponse writeResponse2 = 399 keysetWriteEncrypted( 400 keysetStub, invalidData, masterKeyset, /*associatedData=*/ Optional.empty()); 401 assertThat(writeResponse2.getErr()).isNotEmpty(); 402 403 KeysetReadEncryptedResponse readResponse1 = 404 keysetReadEncrypted(keysetStub, keyset, invalidData, /*associatedData=*/ Optional.empty()); 405 assertThat(readResponse1.getErr()).isNotEmpty(); 406 407 KeysetReadEncryptedResponse readResponse2 = 408 keysetReadEncrypted( 409 keysetStub, invalidData, masterKeyset, /*associatedData=*/ Optional.empty()); 410 assertThat(readResponse2.getErr()).isNotEmpty(); 411 } 412 413 // TODO(juerg): Add tests for KEYSET_WRITER_JSON. 414 415 @Test aeadCreateKeyset_success()416 public void aeadCreateKeyset_success() throws Exception { 417 byte[] template = KeyTemplateProtoConverter.toByteArray(KeyTemplates.get("AES128_GCM")); 418 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 419 assertThat(keysetResponse.getErr()).isEmpty(); 420 CreationResponse response = 421 aeadStub.create( 422 CreationRequest.newBuilder() 423 .setAnnotatedKeyset( 424 AnnotatedKeyset.newBuilder() 425 .setSerializedKeyset(keysetResponse.getKeyset()) 426 .build()) 427 .build()); 428 assertThat(response.getErr()).isEmpty(); 429 } 430 431 @Test aeadCreateKeyset_fails()432 public void aeadCreateKeyset_fails() throws Exception { 433 CreationResponse response = 434 aeadStub.create( 435 CreationRequest.newBuilder() 436 .setAnnotatedKeyset( 437 AnnotatedKeyset.newBuilder() 438 .setSerializedKeyset(ByteString.copyFrom(new byte[] {(byte) 0x80})) 439 .build()) 440 .build()); 441 assertThat(response.getErr()).isNotEmpty(); 442 } 443 aeadEncrypt( AeadGrpc.AeadBlockingStub aeadStub, byte[] keyset, byte[] plaintext, byte[] associatedData)444 private static AeadEncryptResponse aeadEncrypt( 445 AeadGrpc.AeadBlockingStub aeadStub, byte[] keyset, byte[] plaintext, byte[] associatedData) { 446 AeadEncryptRequest encRequest = 447 AeadEncryptRequest.newBuilder() 448 .setAnnotatedKeyset( 449 AnnotatedKeyset.newBuilder() 450 .setSerializedKeyset(ByteString.copyFrom(keyset)) 451 .build()) 452 .setPlaintext(ByteString.copyFrom(plaintext)) 453 .setAssociatedData(ByteString.copyFrom(associatedData)) 454 .build(); 455 return aeadStub.encrypt(encRequest); 456 } 457 aeadDecrypt( AeadGrpc.AeadBlockingStub aeadStub, byte[] keyset, byte[] ciphertext, byte[] associatedData)458 private static AeadDecryptResponse aeadDecrypt( 459 AeadGrpc.AeadBlockingStub aeadStub, byte[] keyset, byte[] ciphertext, byte[] associatedData) { 460 AeadDecryptRequest decRequest = 461 AeadDecryptRequest.newBuilder() 462 .setAnnotatedKeyset( 463 AnnotatedKeyset.newBuilder() 464 .setSerializedKeyset(ByteString.copyFrom(keyset)) 465 .build()) 466 .setCiphertext(ByteString.copyFrom(ciphertext)) 467 .setAssociatedData(ByteString.copyFrom(associatedData)) 468 .build(); 469 return aeadStub.decrypt(decRequest); 470 } 471 472 @Test aeadGenerateEncryptDecrypt_success()473 public void aeadGenerateEncryptDecrypt_success() throws Exception { 474 byte[] template = KeyTemplateProtoConverter.toByteArray(KeyTemplates.get("AES128_GCM")); 475 byte[] plaintext = "The quick brown fox jumps over the lazy dog".getBytes(UTF_8); 476 byte[] associatedData = "generate_encrypt_decrypt".getBytes(UTF_8); 477 478 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 479 assertThat(keysetResponse.getErr()).isEmpty(); 480 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 481 482 AeadEncryptResponse encResponse = aeadEncrypt(aeadStub, keyset, plaintext, associatedData); 483 assertThat(encResponse.getErr()).isEmpty(); 484 byte[] ciphertext = encResponse.getCiphertext().toByteArray(); 485 486 AeadDecryptResponse decResponse = aeadDecrypt(aeadStub, keyset, ciphertext, associatedData); 487 assertThat(decResponse.getErr()).isEmpty(); 488 byte[] output = decResponse.getPlaintext().toByteArray(); 489 490 assertThat(output).isEqualTo(plaintext); 491 } 492 493 @Test generateKeyset_failsOnBadTemplate()494 public void generateKeyset_failsOnBadTemplate() throws Exception { 495 byte[] badTemplate = "bad template".getBytes(UTF_8); 496 KeysetGenerateResponse genResponse = generateKeyset(keysetStub, badTemplate); 497 assertThat(genResponse.getErr()).isNotEmpty(); 498 } 499 500 @Test aeadDecrypt_failsOnBadCiphertext()501 public void aeadDecrypt_failsOnBadCiphertext() throws Exception { 502 byte[] template = KeyTemplateProtoConverter.toByteArray(KeyTemplates.get("AES128_GCM")); 503 byte[] badCiphertext = "bad ciphertext".getBytes(UTF_8); 504 byte[] associatedData = "aead_decrypt_fails_on_bad_ciphertext".getBytes(UTF_8); 505 506 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 507 assertThat(keysetResponse.getErr()).isEmpty(); 508 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 509 510 AeadDecryptResponse decResponse = aeadDecrypt(aeadStub, keyset, badCiphertext, associatedData); 511 assertThat(decResponse.getErr()).isNotEmpty(); 512 } 513 514 @Test deterministicAeadCreateKeyset_success()515 public void deterministicAeadCreateKeyset_success() throws Exception { 516 byte[] template = KeyTemplateProtoConverter.toByteArray(AesSivKeyManager.aes256SivTemplate()); 517 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 518 assertThat(keysetResponse.getErr()).isEmpty(); 519 CreationResponse response = 520 daeadStub.create( 521 CreationRequest.newBuilder() 522 .setAnnotatedKeyset( 523 AnnotatedKeyset.newBuilder().setSerializedKeyset(keysetResponse.getKeyset())) 524 .build()); 525 assertThat(response.getErr()).isEmpty(); 526 } 527 528 @Test deterministicAeadCreateKeyset_fails()529 public void deterministicAeadCreateKeyset_fails() throws Exception { 530 CreationResponse response = 531 daeadStub.create( 532 CreationRequest.newBuilder() 533 .setAnnotatedKeyset( 534 AnnotatedKeyset.newBuilder() 535 .setSerializedKeyset(ByteString.copyFrom(new byte[] {(byte) 0x80}))) 536 .build()); 537 assertThat(response.getErr()).isNotEmpty(); 538 } 539 daeadEncrypt( DeterministicAeadGrpc.DeterministicAeadBlockingStub daeadStub, byte[] keyset, byte[] plaintext, byte[] associatedData)540 private static DeterministicAeadEncryptResponse daeadEncrypt( 541 DeterministicAeadGrpc.DeterministicAeadBlockingStub daeadStub, 542 byte[] keyset, 543 byte[] plaintext, 544 byte[] associatedData) { 545 DeterministicAeadEncryptRequest encRequest = 546 DeterministicAeadEncryptRequest.newBuilder() 547 .setAnnotatedKeyset( 548 AnnotatedKeyset.newBuilder().setSerializedKeyset(ByteString.copyFrom(keyset))) 549 .setPlaintext(ByteString.copyFrom(plaintext)) 550 .setAssociatedData(ByteString.copyFrom(associatedData)) 551 .build(); 552 return daeadStub.encryptDeterministically(encRequest); 553 } 554 daeadDecrypt( DeterministicAeadGrpc.DeterministicAeadBlockingStub daeadStub, byte[] keyset, byte[] ciphertext, byte[] associatedData)555 private static DeterministicAeadDecryptResponse daeadDecrypt( 556 DeterministicAeadGrpc.DeterministicAeadBlockingStub daeadStub, 557 byte[] keyset, 558 byte[] ciphertext, 559 byte[] associatedData) { 560 DeterministicAeadDecryptRequest decRequest = 561 DeterministicAeadDecryptRequest.newBuilder() 562 .setAnnotatedKeyset( 563 AnnotatedKeyset.newBuilder() 564 .setSerializedKeyset(ByteString.copyFrom(keyset)) 565 .build()) 566 .setCiphertext(ByteString.copyFrom(ciphertext)) 567 .setAssociatedData(ByteString.copyFrom(associatedData)) 568 .build(); 569 return daeadStub.decryptDeterministically(decRequest); 570 } 571 572 @Test daeadGenerateEncryptDecryptDeterministically_success()573 public void daeadGenerateEncryptDecryptDeterministically_success() throws Exception { 574 byte[] template = KeyTemplateProtoConverter.toByteArray(AesSivKeyManager.aes256SivTemplate()); 575 byte[] plaintext = "The quick brown fox jumps over the lazy dog".getBytes(UTF_8); 576 byte[] associatedData = "generate_encrypt_decrypt".getBytes(UTF_8); 577 578 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 579 assertThat(keysetResponse.getErr()).isEmpty(); 580 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 581 582 DeterministicAeadEncryptResponse encResponse = 583 daeadEncrypt(daeadStub, keyset, plaintext, associatedData); 584 assertThat(encResponse.getErr()).isEmpty(); 585 byte[] ciphertext = encResponse.getCiphertext().toByteArray(); 586 587 DeterministicAeadDecryptResponse decResponse = 588 daeadDecrypt(daeadStub, keyset, ciphertext, associatedData); 589 assertThat(decResponse.getErr()).isEmpty(); 590 byte[] output = decResponse.getPlaintext().toByteArray(); 591 592 assertThat(output).isEqualTo(plaintext); 593 } 594 595 @Test daeadEncryptDeterministically_failsOnBadKeyset()596 public void daeadEncryptDeterministically_failsOnBadKeyset() throws Exception { 597 byte[] badKeyset = "bad keyset".getBytes(UTF_8); 598 byte[] plaintext = "The quick brown fox jumps over the lazy dog".getBytes(UTF_8); 599 byte[] associatedData = "aead_encrypt_fails_on_bad_keyset".getBytes(UTF_8); 600 assertThrows( 601 StatusRuntimeException.class, 602 () -> daeadEncrypt(daeadStub, badKeyset, plaintext, associatedData)); 603 } 604 605 @Test daeadDecryptDeterministically_failsOnBadCiphertext()606 public void daeadDecryptDeterministically_failsOnBadCiphertext() throws Exception { 607 byte[] template = KeyTemplateProtoConverter.toByteArray(AesSivKeyManager.aes256SivTemplate()); 608 byte[] badCiphertext = "bad ciphertext".getBytes(UTF_8); 609 byte[] associatedData = "aead_decrypt_fails_on_bad_ciphertext".getBytes(UTF_8); 610 611 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 612 assertThat(keysetResponse.getErr()).isEmpty(); 613 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 614 615 DeterministicAeadDecryptResponse decResponse = 616 daeadDecrypt(daeadStub, keyset, badCiphertext, associatedData); 617 assertThat(decResponse.getErr()).isNotEmpty(); 618 } 619 620 @Test daeadDecryptDeterministically_failsOnBadKeyset()621 public void daeadDecryptDeterministically_failsOnBadKeyset() throws Exception { 622 byte[] template = KeyTemplateProtoConverter.toByteArray(AesSivKeyManager.aes256SivTemplate()); 623 byte[] plaintext = "The quick brown fox jumps over the lazy dog".getBytes(UTF_8); 624 byte[] associatedData = "generate_encrypt_decrypt".getBytes(UTF_8); 625 626 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 627 assertThat(keysetResponse.getErr()).isEmpty(); 628 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 629 630 DeterministicAeadEncryptResponse encResponse = 631 daeadEncrypt(daeadStub, keyset, plaintext, associatedData); 632 assertThat(encResponse.getErr()).isEmpty(); 633 byte[] ciphertext = encResponse.getCiphertext().toByteArray(); 634 635 byte[] badKeyset = "bad keyset".getBytes(UTF_8); 636 assertThrows( 637 StatusRuntimeException.class, 638 () -> daeadDecrypt(daeadStub, badKeyset, ciphertext, associatedData)); 639 } 640 641 @Test streamingAeadCreateKeyset_success()642 public void streamingAeadCreateKeyset_success() throws Exception { 643 byte[] template = 644 KeyTemplateProtoConverter.toByteArray( 645 AesGcmHkdfStreamingKeyManager.aes128GcmHkdf4KBTemplate()); 646 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 647 assertThat(keysetResponse.getErr()).isEmpty(); 648 CreationResponse response = 649 streamingAeadStub.create( 650 CreationRequest.newBuilder() 651 .setAnnotatedKeyset( 652 AnnotatedKeyset.newBuilder() 653 .setSerializedKeyset(keysetResponse.getKeyset()) 654 .build()) 655 .build()); 656 assertThat(response.getErr()).isEmpty(); 657 } 658 659 @Test streamingAeadCreateKeyset_fails()660 public void streamingAeadCreateKeyset_fails() throws Exception { 661 CreationResponse response = 662 streamingAeadStub.create( 663 CreationRequest.newBuilder() 664 .setAnnotatedKeyset( 665 AnnotatedKeyset.newBuilder() 666 .setSerializedKeyset(ByteString.copyFrom(new byte[] {(byte) 0x80})) 667 .build()) 668 .build()); 669 assertThat(response.getErr()).isNotEmpty(); 670 } 671 streamingAeadEncrypt( StreamingAeadGrpc.StreamingAeadBlockingStub streamingAeadStub, byte[] keyset, byte[] plaintext, byte[] associatedData)672 private static StreamingAeadEncryptResponse streamingAeadEncrypt( 673 StreamingAeadGrpc.StreamingAeadBlockingStub streamingAeadStub, 674 byte[] keyset, 675 byte[] plaintext, 676 byte[] associatedData) { 677 StreamingAeadEncryptRequest encRequest = 678 StreamingAeadEncryptRequest.newBuilder() 679 .setAnnotatedKeyset( 680 AnnotatedKeyset.newBuilder() 681 .setSerializedKeyset(ByteString.copyFrom(keyset)) 682 .build()) 683 .setPlaintext(ByteString.copyFrom(plaintext)) 684 .setAssociatedData(ByteString.copyFrom(associatedData)) 685 .build(); 686 return streamingAeadStub.encrypt(encRequest); 687 } 688 streamingAeadDecrypt( StreamingAeadGrpc.StreamingAeadBlockingStub streamingAeadStub, byte[] keyset, byte[] ciphertext, byte[] associatedData)689 private static StreamingAeadDecryptResponse streamingAeadDecrypt( 690 StreamingAeadGrpc.StreamingAeadBlockingStub streamingAeadStub, 691 byte[] keyset, 692 byte[] ciphertext, 693 byte[] associatedData) { 694 StreamingAeadDecryptRequest decRequest = 695 StreamingAeadDecryptRequest.newBuilder() 696 .setAnnotatedKeyset( 697 AnnotatedKeyset.newBuilder() 698 .setSerializedKeyset(ByteString.copyFrom(keyset)) 699 .build()) 700 .setCiphertext(ByteString.copyFrom(ciphertext)) 701 .setAssociatedData(ByteString.copyFrom(associatedData)) 702 .build(); 703 return streamingAeadStub.decrypt(decRequest); 704 } 705 706 @Test streamingAeadGenerateEncryptDecrypt_success()707 public void streamingAeadGenerateEncryptDecrypt_success() throws Exception { 708 byte[] template = 709 KeyTemplateProtoConverter.toByteArray( 710 AesGcmHkdfStreamingKeyManager.aes128GcmHkdf4KBTemplate()); 711 byte[] plaintext = "The quick brown fox jumps over the lazy dog".getBytes(UTF_8); 712 byte[] associatedData = "generate_encrypt_decrypt".getBytes(UTF_8); 713 714 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 715 assertThat(keysetResponse.getErr()).isEmpty(); 716 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 717 718 StreamingAeadEncryptResponse encResponse = 719 streamingAeadEncrypt(streamingAeadStub, keyset, plaintext, associatedData); 720 assertThat(encResponse.getErr()).isEmpty(); 721 byte[] ciphertext = encResponse.getCiphertext().toByteArray(); 722 723 StreamingAeadDecryptResponse decResponse = 724 streamingAeadDecrypt(streamingAeadStub, keyset, ciphertext, associatedData); 725 assertThat(decResponse.getErr()).isEmpty(); 726 byte[] output = decResponse.getPlaintext().toByteArray(); 727 728 assertThat(output).isEqualTo(plaintext); 729 } 730 731 @Test streamingAeadEncrypt_failsOnBadKeyset()732 public void streamingAeadEncrypt_failsOnBadKeyset() throws Exception { 733 byte[] badKeyset = "bad keyset".getBytes(UTF_8); 734 byte[] plaintext = "The quick brown fox jumps over the lazy dog".getBytes(UTF_8); 735 byte[] associatedData = "streamingAead_encrypt_fails_on_bad_keyset".getBytes(UTF_8); 736 StreamingAeadEncryptResponse encResponse = 737 streamingAeadEncrypt(streamingAeadStub, badKeyset, plaintext, associatedData); 738 assertThat(encResponse.getErr()).isNotEmpty(); 739 } 740 741 @Test streamingAeadDecrypt_failsOnBadCiphertext()742 public void streamingAeadDecrypt_failsOnBadCiphertext() throws Exception { 743 byte[] template = 744 KeyTemplateProtoConverter.toByteArray( 745 AesGcmHkdfStreamingKeyManager.aes128GcmHkdf4KBTemplate()); 746 byte[] badCiphertext = "bad ciphertext".getBytes(UTF_8); 747 byte[] associatedData = "streamingAead_decrypt_fails_on_bad_ciphertext".getBytes(UTF_8); 748 749 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 750 assertThat(keysetResponse.getErr()).isEmpty(); 751 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 752 753 StreamingAeadDecryptResponse decResponse = 754 streamingAeadDecrypt(streamingAeadStub, keyset, badCiphertext, associatedData); 755 assertThat(decResponse.getErr()).isNotEmpty(); 756 } 757 758 @Test streamingAeadDecrypt_failsOnBadKeyset()759 public void streamingAeadDecrypt_failsOnBadKeyset() throws Exception { 760 byte[] template = 761 KeyTemplateProtoConverter.toByteArray( 762 AesGcmHkdfStreamingKeyManager.aes128GcmHkdf4KBTemplate()); 763 byte[] plaintext = "The quick brown fox jumps over the lazy dog".getBytes(UTF_8); 764 byte[] associatedData = "generate_encrypt_decrypt".getBytes(UTF_8); 765 766 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 767 assertThat(keysetResponse.getErr()).isEmpty(); 768 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 769 770 StreamingAeadEncryptResponse encResponse = 771 streamingAeadEncrypt(streamingAeadStub, keyset, plaintext, associatedData); 772 assertThat(encResponse.getErr()).isEmpty(); 773 byte[] ciphertext = encResponse.getCiphertext().toByteArray(); 774 775 byte[] badKeyset = "bad keyset".getBytes(UTF_8); 776 777 StreamingAeadDecryptResponse decResponse = 778 streamingAeadDecrypt(streamingAeadStub, badKeyset, ciphertext, associatedData); 779 assertThat(decResponse.getErr()).isNotEmpty(); 780 } 781 782 @Test macCreateKeyset_success()783 public void macCreateKeyset_success() throws Exception { 784 byte[] template = 785 KeyTemplateProtoConverter.toByteArray(HmacKeyManager.hmacSha256HalfDigestTemplate()); 786 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 787 assertThat(keysetResponse.getErr()).isEmpty(); 788 CreationResponse response = 789 macStub.create( 790 CreationRequest.newBuilder() 791 .setAnnotatedKeyset( 792 AnnotatedKeyset.newBuilder() 793 .setSerializedKeyset(keysetResponse.getKeyset()) 794 .build()) 795 .build()); 796 assertThat(response.getErr()).isEmpty(); 797 } 798 799 @Test macCreateKeyset_fails()800 public void macCreateKeyset_fails() throws Exception { 801 CreationResponse response = 802 macStub.create( 803 CreationRequest.newBuilder() 804 .setAnnotatedKeyset( 805 AnnotatedKeyset.newBuilder() 806 .setSerializedKeyset(ByteString.copyFrom(new byte[] {(byte) 0x80})) 807 .build()) 808 .build()); 809 assertThat(response.getErr()).isNotEmpty(); 810 } 811 computeMac( MacGrpc.MacBlockingStub macStub, byte[] keyset, byte[] data)812 private static ComputeMacResponse computeMac( 813 MacGrpc.MacBlockingStub macStub, byte[] keyset, byte[] data) { 814 ComputeMacRequest request = 815 ComputeMacRequest.newBuilder() 816 .setAnnotatedKeyset( 817 AnnotatedKeyset.newBuilder() 818 .setSerializedKeyset(ByteString.copyFrom(keyset)) 819 .build()) 820 .setData(ByteString.copyFrom(data)) 821 .build(); 822 return macStub.computeMac(request); 823 } 824 verifyMac( MacGrpc.MacBlockingStub macStub, byte[] keyset, byte[] macValue, byte[] data)825 private static VerifyMacResponse verifyMac( 826 MacGrpc.MacBlockingStub macStub, byte[] keyset, byte[] macValue, byte[] data) { 827 VerifyMacRequest request = 828 VerifyMacRequest.newBuilder() 829 .setAnnotatedKeyset( 830 AnnotatedKeyset.newBuilder() 831 .setSerializedKeyset(ByteString.copyFrom(keyset)) 832 .build()) 833 .setMacValue(ByteString.copyFrom(macValue)) 834 .setData(ByteString.copyFrom(data)) 835 .build(); 836 return macStub.verifyMac(request); 837 } 838 839 @Test computeVerifyMac_success()840 public void computeVerifyMac_success() throws Exception { 841 byte[] template = 842 KeyTemplateProtoConverter.toByteArray(HmacKeyManager.hmacSha256HalfDigestTemplate()); 843 byte[] data = "The quick brown fox jumps over the lazy dog".getBytes(UTF_8); 844 845 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 846 assertThat(keysetResponse.getErr()).isEmpty(); 847 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 848 849 ComputeMacResponse compResponse = computeMac(macStub, keyset, data); 850 assertThat(compResponse.getErr()).isEmpty(); 851 byte[] macValue = compResponse.getMacValue().toByteArray(); 852 853 VerifyMacResponse verifyResponse = verifyMac(macStub, keyset, macValue, data); 854 assertThat(verifyResponse.getErr()).isEmpty(); 855 } 856 857 @Test computeMac_failsOnBadKeyset()858 public void computeMac_failsOnBadKeyset() throws Exception { 859 byte[] badKeyset = "bad keyset".getBytes(UTF_8); 860 byte[] data = "The quick brown fox jumps over the lazy dog".getBytes(UTF_8); 861 862 ComputeMacResponse compResponse = computeMac(macStub, badKeyset, data); 863 assertThat(compResponse.getErr()).isNotEmpty(); 864 } 865 866 @Test verifyMac_failsOnBadMacValue()867 public void verifyMac_failsOnBadMacValue() throws Exception { 868 byte[] template = 869 KeyTemplateProtoConverter.toByteArray(HmacKeyManager.hmacSha256HalfDigestTemplate()); 870 byte[] data = "The quick brown fox jumps over the lazy dog".getBytes(UTF_8); 871 872 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 873 assertThat(keysetResponse.getErr()).isEmpty(); 874 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 875 876 VerifyMacResponse verifyResponse = 877 verifyMac(macStub, keyset, "bad mac_value".getBytes(UTF_8), data); 878 assertThat(verifyResponse.getErr()).isNotEmpty(); 879 } 880 881 @Test verifyMac_failsOnBadKeyset()882 public void verifyMac_failsOnBadKeyset() throws Exception { 883 byte[] template = 884 KeyTemplateProtoConverter.toByteArray(HmacKeyManager.hmacSha256HalfDigestTemplate()); 885 byte[] data = "The quick brown fox jumps over the lazy dog".getBytes(UTF_8); 886 887 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 888 assertThat(keysetResponse.getErr()).isEmpty(); 889 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 890 891 ComputeMacResponse compResponse = computeMac(macStub, keyset, data); 892 assertThat(compResponse.getErr()).isEmpty(); 893 byte[] macValue = compResponse.getMacValue().toByteArray(); 894 895 byte[] badKeyset = "bad keyset".getBytes(UTF_8); 896 VerifyMacResponse verifyResponse = verifyMac(macStub, badKeyset, macValue, data); 897 assertThat(verifyResponse.getErr()).isNotEmpty(); 898 } 899 900 @Test prfSetCreateKeyset_success()901 public void prfSetCreateKeyset_success() throws Exception { 902 byte[] template = KeyTemplateProtoConverter.toByteArray(HmacPrfKeyManager.hmacSha256Template()); 903 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 904 assertThat(keysetResponse.getErr()).isEmpty(); 905 CreationResponse response = 906 prfSetStub.create( 907 CreationRequest.newBuilder() 908 .setAnnotatedKeyset( 909 AnnotatedKeyset.newBuilder() 910 .setSerializedKeyset(keysetResponse.getKeyset()) 911 .build()) 912 .build()); 913 assertThat(response.getErr()).isEmpty(); 914 } 915 916 @Test prfSetCreateKeyset_fails()917 public void prfSetCreateKeyset_fails() throws Exception { 918 CreationResponse response = 919 prfSetStub.create( 920 CreationRequest.newBuilder() 921 .setAnnotatedKeyset( 922 AnnotatedKeyset.newBuilder() 923 .setSerializedKeyset(ByteString.copyFrom(new byte[] {(byte) 0x80})) 924 .build()) 925 .build()); 926 assertThat(response.getErr()).isNotEmpty(); 927 } 928 keyIds( PrfSetGrpc.PrfSetBlockingStub prfSetStub, byte[] keyset)929 private static PrfSetKeyIdsResponse keyIds( 930 PrfSetGrpc.PrfSetBlockingStub prfSetStub, byte[] keyset) { 931 PrfSetKeyIdsRequest request = 932 PrfSetKeyIdsRequest.newBuilder() 933 .setAnnotatedKeyset( 934 AnnotatedKeyset.newBuilder() 935 .setSerializedKeyset(ByteString.copyFrom(keyset)) 936 .build()) 937 .build(); 938 return prfSetStub.keyIds(request); 939 } 940 computePrf( PrfSetGrpc.PrfSetBlockingStub prfSetStub, byte[] keyset, int keyId, byte[] inputData, int outputLength)941 private static PrfSetComputeResponse computePrf( 942 PrfSetGrpc.PrfSetBlockingStub prfSetStub, 943 byte[] keyset, 944 int keyId, 945 byte[] inputData, 946 int outputLength) { 947 PrfSetComputeRequest request = 948 PrfSetComputeRequest.newBuilder() 949 .setAnnotatedKeyset( 950 AnnotatedKeyset.newBuilder() 951 .setSerializedKeyset(ByteString.copyFrom(keyset)) 952 .build()) 953 .setKeyId(keyId) 954 .setInputData(ByteString.copyFrom(inputData)) 955 .setOutputLength(outputLength) 956 .build(); 957 return prfSetStub.compute(request); 958 } 959 960 @Test computePrf_success()961 public void computePrf_success() throws Exception { 962 byte[] template = KeyTemplateProtoConverter.toByteArray( 963 HmacPrfKeyManager.hmacSha256Template()); 964 byte[] inputData = "The quick brown fox jumps over the lazy dog".getBytes(UTF_8); 965 int outputLength = 15; 966 967 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 968 assertThat(keysetResponse.getErr()).isEmpty(); 969 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 970 971 PrfSetKeyIdsResponse keyIdsResponse = keyIds(prfSetStub, keyset); 972 assertThat(keyIdsResponse.getErr()).isEmpty(); 973 int primaryKeyId = keyIdsResponse.getOutput().getPrimaryKeyId(); 974 975 PrfSetComputeResponse computeResponse = computePrf( 976 prfSetStub, keyset, primaryKeyId, inputData, outputLength); 977 assertThat(computeResponse.getErr()).isEmpty(); 978 assertThat(computeResponse.getOutput().size()).isEqualTo(outputLength); 979 } 980 981 @Test prfKeyIds_failsOnBadKeyset()982 public void prfKeyIds_failsOnBadKeyset() throws Exception { 983 byte[] badKeyset = "bad keyset".getBytes(UTF_8); 984 985 PrfSetKeyIdsResponse keyIdsResponse = keyIds(prfSetStub, badKeyset); 986 assertThat(keyIdsResponse.getErr()).isNotEmpty(); 987 } 988 989 @Test computePrf_failsOnUnknownKeyId()990 public void computePrf_failsOnUnknownKeyId() throws Exception { 991 byte[] template = KeyTemplateProtoConverter.toByteArray( 992 HmacPrfKeyManager.hmacSha256Template()); 993 byte[] inputData = "The quick brown fox jumps over the lazy dog".getBytes(UTF_8); 994 int outputLength = 15; 995 int badKeyId = 123456789; 996 997 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 998 assertThat(keysetResponse.getErr()).isEmpty(); 999 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 1000 1001 PrfSetComputeResponse computeResponse = computePrf( 1002 prfSetStub, keyset, badKeyId, inputData, outputLength); 1003 assertThat(computeResponse.getErr()).isNotEmpty(); 1004 } 1005 1006 @Test computePrf_failsOnBadOutputLength()1007 public void computePrf_failsOnBadOutputLength() throws Exception { 1008 byte[] template = KeyTemplateProtoConverter.toByteArray( 1009 HmacPrfKeyManager.hmacSha256Template()); 1010 byte[] inputData = "The quick brown fox jumps over the lazy dog".getBytes(UTF_8); 1011 int outputLength = 12345; 1012 1013 KeysetGenerateResponse keysetResponse = generateKeyset(keysetStub, template); 1014 assertThat(keysetResponse.getErr()).isEmpty(); 1015 byte[] keyset = keysetResponse.getKeyset().toByteArray(); 1016 1017 PrfSetKeyIdsResponse keyIdsResponse = keyIds(prfSetStub, keyset); 1018 assertThat(keyIdsResponse.getErr()).isEmpty(); 1019 int primaryKeyId = keyIdsResponse.getOutput().getPrimaryKeyId(); 1020 1021 PrfSetComputeResponse computeResponse = computePrf( 1022 prfSetStub, keyset, primaryKeyId, inputData, outputLength); 1023 assertThat(computeResponse.getErr()).isNotEmpty(); 1024 } 1025 1026 @Test getServerInfo_success()1027 public void getServerInfo_success() throws Exception { 1028 ServerInfoResponse response = 1029 metadataStub.getServerInfo(ServerInfoRequest.getDefaultInstance()); 1030 assertThat(response.getLanguage()).isEqualTo("java"); 1031 assertThat(response.getTinkVersion()).isNotEmpty(); 1032 } 1033 } 1034