Beispiel #1
0
 def test_encrypt_decrypt_with_primary_key_succeeds(self):
   private_handle_with_primary = cleartext_keyset_handle.read(
       tink.JsonKeysetReader(PRIVATE_KEYSET_WITH_PRIMARY))
   public_handle_with_primary = cleartext_keyset_handle.read(
       tink.JsonKeysetReader(PUBLIC_KEYSET_WITH_PRIMARY))
   dec = private_handle_with_primary.primitive(hybrid.HybridDecrypt)
   enc = public_handle_with_primary.primitive(hybrid.HybridEncrypt)
   ciphertext = enc.encrypt(b'plaintext', b'context')
   self.assertEqual(dec.decrypt(ciphertext, b'context'), b'plaintext')
Beispiel #2
0
 def test_encrypt_decrypt_without_primary_key_fails(self):
   with self.assertRaises(tink.TinkError):
     cleartext_keyset_handle.read(
         tink.JsonKeysetReader(PRIVATE_KEYSET_WITHOUT_PRIMARY))
   # Currently, the public keyset only fails when 'encrypt' is called.
   # TODO(b/228140127): It would be preferable that it fails earlier.
   public_handle_without_primary = cleartext_keyset_handle.read(
       tink.JsonKeysetReader(PUBLIC_KEYSET_WITHOUT_PRIMARY))
   enc_without_primary = public_handle_without_primary.primitive(
       hybrid.HybridEncrypt)
   with self.assertRaises(tink.TinkError):
     enc_without_primary.encrypt(b'plaintext', b'context')
Beispiel #3
0
  def ReadEncrypted(
      self, request: testing_api_pb2.KeysetReadEncryptedRequest,
      context: grpc.ServicerContext
  ) -> testing_api_pb2.KeysetReadEncryptedResponse:
    """Reads an encrypted keyset."""
    try:
      master_keyset_handle = cleartext_keyset_handle.read(
          tink.BinaryKeysetReader(request.master_keyset))
      master_aead = master_keyset_handle.primitive(aead.Aead)

      if request.keyset_reader_type == testing_api_pb2.KEYSET_READER_BINARY:
        reader = tink.BinaryKeysetReader(request.encrypted_keyset)
      elif request.keyset_reader_type == testing_api_pb2.KEYSET_READER_JSON:
        reader = tink.JsonKeysetReader(request.encrypted_keyset.decode('utf8'))
      else:
        raise ValueError('unknown keyset reader type')
      if request.HasField('associated_data'):
        keyset_handle = tink.read_keyset_handle_with_associated_data(
            reader, master_aead, request.associated_data.value)
      else:
        keyset_handle = tink.read_keyset_handle(reader, master_aead)

      keyset = io.BytesIO()
      cleartext_keyset_handle.write(
          tink.BinaryKeysetWriter(keyset), keyset_handle)
      return testing_api_pb2.KeysetReadEncryptedResponse(
          keyset=keyset.getvalue())
    except tink.TinkError as e:
      return testing_api_pb2.KeysetReadEncryptedResponse(err=str(e))
Beispiel #4
0
def main(argv):
    del argv  # Unused.

    # Initialise Tink
    try:
        jwt.register_jwt_signature()
    except tink.TinkError as e:
        logging.exception('Error initialising Tink: %s', e)
        return 1

    # Read the keyset into a KeysetHandle
    with open(FLAGS.keyset_path, 'rt') as keyset_file:
        try:
            text = keyset_file.read()
            keyset_handle = cleartext_keyset_handle.read(
                tink.JsonKeysetReader(text))
        except tink.TinkError as e:
            logging.exception('Error reading keyset: %s', e)
            return 1

    # Export Public Keyset as JWK set
    public_jwk_set = jwt.jwk_set_from_public_keyset_handle(
        keyset_handle.public_keyset_handle())
    with open(FLAGS.public_jwk_set_path, 'wt') as public_jwk_set_file:
        public_jwk_set_file.write(public_jwk_set)
    logging.info('The public JWK set has been written to %s',
                 FLAGS.public_jwk_set_path)
Beispiel #5
0
 def test_write_encrypted_read_encrypted(self):
     encrypted_keyset = example_encrypted_keyset()
     stream = io.StringIO()
     writer = tink.JsonKeysetWriter(stream)
     writer.write_encrypted(encrypted_keyset)
     reader = tink.JsonKeysetReader(stream.getvalue())
     self.assertEqual(encrypted_keyset, reader.read_encrypted())
Beispiel #6
0
def main(argv):
  del argv

  context_info = b'' if not FLAGS.context_info else bytes(
      FLAGS.context_info, 'utf-8')

  # Initialise Tink.
  try:
    hybrid.register()
  except tink.TinkError:
    logging.exception('Error initialising Tink.')
    return 1

  # Read the keyset into a keyset_handle.
  with open(FLAGS.keyset_path, 'rt') as keyset_file:
    text = keyset_file.read()
    try:
      keyset_handle = cleartext_keyset_handle.read(tink.JsonKeysetReader(text))
    except tink.TinkError:
      logging.exception('Error reading key.')
      return 1

  # Get the primitive.
  try:
    primitive = keyset_handle.primitive(hybrid.HybridDecrypt)
  except tink.TinkError:
    logging.exception(
        'Error creating hybrid decrypt primitive from keyset.')
    return 1

  with open(FLAGS.input_path, 'rb') as input_file:
    with open(FLAGS.output_path, 'wb') as output_file:
      data = input_file.read()
      plaintext = primitive.decrypt(data, context_info)
      output_file.write(plaintext)
Beispiel #7
0
def main(argv):
    del argv  # Unused.

    # Initialise Tink
    try:
        jwt.register_jwt_signature()
    except tink.TinkError as e:
        logging.exception('Error initialising Tink: %s', e)
        return 1

    # Read the keyset into a KeysetHandle
    with open(_PUBLIC_KEYSET_PATH.value, 'rt') as keyset_file:
        try:
            text = keyset_file.read()
            public_keyset_handle = tink.read_no_secret_keyset_handle(
                tink.JsonKeysetReader(text))
        except tink.TinkError as e:
            logging.exception('Error reading keyset: %s', e)
            return 1

    # Export Public Keyset as JWK set
    public_jwk_set = jwt.jwk_set_from_public_keyset_handle(
        public_keyset_handle)
    with open(_PUBLIC_JWK_SET_PATH.value, 'wt') as public_jwk_set_file:
        public_jwk_set_file.write(public_jwk_set)
    logging.info('The public JWK set has been written to %s',
                 _PUBLIC_JWK_SET_PATH.value)
Beispiel #8
0
def main(argv):
    del argv  # Unused.

    # Initialise Tink
    try:
        jwt.register_jwt_signature()
    except tink.TinkError as e:
        logging.exception('Error initialising Tink: %s', e)
        return 1

    # Read the keyset into a keyset_handle
    with open(FLAGS.keyset_path, 'rt') as keyset_file:
        try:
            text = keyset_file.read()
            keyset_handle = cleartext_keyset_handle.read(
                tink.JsonKeysetReader(text))
        except tink.TinkError as e:
            logging.exception('Error reading keyset: %s', e)
            return 1

    now = datetime.datetime.now(tz=datetime.timezone.utc)
    if FLAGS.mode == 'sign':
        # Get the JwtPublicKeySign primitive
        try:
            jwt_sign = keyset_handle.primitive(jwt.JwtPublicKeySign)
        except tink.TinkError as e:
            logging.exception('Error creating JwtPublicKeySign: %s', e)
            return 1

        # Create token
        raw_jwt = jwt.new_raw_jwt(subject=FLAGS.subject,
                                  expiration=now +
                                  datetime.timedelta(seconds=100))
        token = jwt_sign.sign_and_encode(raw_jwt)
        with open(FLAGS.token_path, 'wt') as token_file:
            token_file.write(token)
        logging.info('Token has been written to %s', FLAGS.token_path)
        return 0

    # Get the JwtPublicKeyVerify primitive
    try:
        jwt_verify = keyset_handle.primitive(jwt.JwtPublicKeyVerify)
    except tink.TinkError as e:
        logging.exception('Error creating JwtPublicKeyVerify: %s', e)
        return 1

    # Verify token
    with open(FLAGS.token_path, 'rt') as token_file:
        token = token_file.read()
    validator = jwt.new_validator(expected_subject=FLAGS.subject)
    try:
        verified_jwt = jwt_verify.verify_and_decode(token, validator)
        expires_in = verified_jwt.expiration() - now
        logging.info('Token is valid and expires in %s seconds',
                     expires_in.seconds)
        return 0
    except tink.TinkError as e:
        logging.info('JWT verification failed: %s', e)
        return 1
Beispiel #9
0
def main(argv):
    if len(argv) != 4:
        raise app.UsageError(
            'Expected 3 arguments, got %d.\n'
            'Usage: %s keyset-file (encrypt | decrypt) associated-data' %
            (len(argv) - 1, argv[0]))

    keyset_filename = argv[1]
    operation = argv[2]
    aad = argv[3].encode('utf-8')  # TODO take hex and binascii.unhexlify

    if operation not in ('encrypt', 'decrypt'):
        logging.error('Operation %s not recognised', operation)
        return 1

    # Initialise Tink.
    try:
        tink.tink_config.register()
    except tink.TinkError as e:
        logging.error('Error initialising Tink: %s', e)
        return 1

    # Read the keyset.
    with open(keyset_filename, 'rb') as keyset_file:
        try:
            text = keyset_file.read()
            keyset = cleartext_keyset_handle.read(tink.JsonKeysetReader(text))
        except tink.TinkError as e:
            logging.error('Error reading key: %s', e)
            return 1

    # Get the primitive.
    try:
        cipher = keyset.primitive(tink.Aead)
    except tink.TinkError as e:
        logging.error('Error creating primitive: %s', e)
        return 1

    # Compute the operation.
    input_data = sys.stdin.buffer.read()

    try:
        if operation == 'encrypt':
            output_data = cipher.encrypt(input_data, aad)
        elif operation == 'decrypt':
            output_data = cipher.decrypt(input_data, aad)
        else:
            # Unreachable: We checked operation at the start.
            logging.error('(unreachable) Operation %s not recognised',
                          operation)
            return 1
    except tink.TinkError as e:
        logging.error('Operation failed: %s', e)
        return 1

    sys.stdout.buffer.write(output_data)
    return 0
Beispiel #10
0
def main(argv):
  del argv  # Unused

  mode = FLAGS.mode
  if mode not in ('encrypt', 'decrypt'):
    logging.error('Incorrect mode. Please select "encrypt" or "decrypt".')
    return 1
  context_info = b'' if not FLAGS.context_info else bytes(
      FLAGS.context_info, 'utf-8')

  # Initialise Tink
  try:
    hybrid.register()
  except tink.TinkError as e:
    logging.exception('Error initialising Tink: %s', e)
    return 1

  # Read the keyset into a keyset_handle
  with open(FLAGS.keyset_path, 'rt') as keyset_file:
    try:
      text = keyset_file.read()
      keyset_handle = cleartext_keyset_handle.read(tink.JsonKeysetReader(text))
    except tink.TinkError as e:
      logging.exception('Error reading key: %s', e)
      return 1

  with open(FLAGS.input_path, 'rb') as input_file:
    data = input_file.read()

  if mode == 'encrypt':
    # Get the primitive
    try:
      primitive = keyset_handle.primitive(hybrid.HybridEncrypt)
    except tink.TinkError as e:
      logging.exception(
          'Error creating hybrid encrypt primitive from keyset: %s', e)
      return 1
    # Encrypt data
    with open(FLAGS.output_path, 'wb') as output_file:
      ciphertext = primitive.encrypt(data, context_info)
      output_file.write(ciphertext)
      return 0

  # Get the primitive
  try:
    primitive = keyset_handle.primitive(hybrid.HybridDecrypt)
  except tink.TinkError as e:
    logging.exception(
        'Error creating hybrid encrypt primitive from keyset: %s', e)
    return 1
  # Decrypt data
  with open(FLAGS.output_path, 'wb') as output_file:
    plaintext = primitive.decrypt(data, context_info)
    output_file.write(plaintext)

  return 0
Beispiel #11
0
 def test_write_read_with_unicode_chars(self):
     keyset = tink_pb2.Keyset()
     key = keyset.key.add()
     key.key_data.type_url = (
         u'\xe3\x82\xb3\xe3\x83\xb3\xe3\x83\x8b\xe3\x83\x81\xe3\x83\x8f')
     stream = io.StringIO()
     writer = tink.JsonKeysetWriter(stream)
     writer.write(keyset)
     reader = tink.JsonKeysetReader(stream.getvalue())
     self.assertEqual(keyset, reader.read())
def main(argv):
    if len(argv) != 5 and len(argv) != 6:
        raise app.UsageError(
            'Expected 4 or 5 arguments, got %d.\n'
            'Usage: %s encrypt/decrypt key-file input-file output-file '
            '[associated-data]' % (len(argv) - 1, argv[0]))

    mode = argv[1]
    key_file_path = argv[2]
    input_file_path = argv[3]
    output_file_path = argv[4]
    associated_data = b'' if len(argv) == 5 else bytes(argv[5], 'utf-8')

    # Initialise Tink
    try:
        daead.register()
    except tink.TinkError as e:
        logging.error('Error initialising Tink: %s', e)
        return 1

    # Read the keyset into a keyset_handle
    with open(key_file_path, 'rt') as keyset_file:
        try:
            text = keyset_file.read()
            keyset_handle = cleartext_keyset_handle.read(
                tink.JsonKeysetReader(text))
        except tink.TinkError as e:
            logging.exception('Error reading key: %s', e)
            return 1

    # Get the primitive
    try:
        cipher = keyset_handle.primitive(daead.DeterministicAead)
    except tink.TinkError as e:
        logging.error('Error creating primitive: %s', e)
        return 1

    with open(input_file_path, 'rb') as input_file:
        input_data = input_file.read()
        if mode == 'decrypt':
            output_data = cipher.decrypt_deterministically(
                input_data, associated_data)
        elif mode == 'encrypt':
            output_data = cipher.encrypt_deterministically(
                input_data, associated_data)
        else:
            logging.error(
                'Error mode not supported. Please choose "encrypt" or "decrypt".'
            )
            return 1

        with open(output_file_path, 'wb') as output_file:
            output_file.write(output_data)
Beispiel #13
0
def main(argv):
    del argv  # Unused.

    # Initialise Tink
    try:
        jwt.register_jwt_signature()
    except tink.TinkError as e:
        logging.exception('Error initialising Tink: %s', e)
        return 1

    # Read the keyset into a KeysetHandle
    if _PUBLIC_KEYSET_PATH.present:
        with open(_PUBLIC_KEYSET_PATH.value, 'rt') as public_keyset_file:
            try:
                text = public_keyset_file.read()
                keyset_handle = tink.read_no_secret_keyset_handle(
                    tink.JsonKeysetReader(text))
            except tink.TinkError as e:
                logging.exception('Error reading public keyset: %s', e)
                return 1
    elif _PUBLIC_JWK_SET_PATH.present:
        with open(_PUBLIC_JWK_SET_PATH.value, 'rt') as public_jwk_set_file:
            try:
                text = public_jwk_set_file.read()
                keyset_handle = jwt.jwk_set_to_public_keyset_handle(text)
            except tink.TinkError as e:
                logging.exception('Error reading public JWK set: %s', e)
                return 1
    else:
        logging.info(
            'Either --public_keyset_path or --public_jwk_set_path must be set')

    now = datetime.datetime.now(tz=datetime.timezone.utc)
    try:
        jwt_verify = keyset_handle.primitive(jwt.JwtPublicKeyVerify)
    except tink.TinkError as e:
        logging.exception('Error creating JwtPublicKeyVerify: %s', e)
        return 1

    # Verify token
    with open(_TOKEN_PATH.value, 'rt') as token_file:
        token = token_file.read()
    validator = jwt.new_validator(expected_audience=_AUDIENCE.value)
    try:
        verified_jwt = jwt_verify.verify_and_decode(token, validator)
        expires_in = verified_jwt.expiration() - now
        logging.info('Token is valid and expires in %s seconds',
                     expires_in.seconds)
        return 0
    except tink.TinkError as e:
        logging.info('JWT verification failed: %s', e)
        return 1
Beispiel #14
0
 def FromJson(
     self, request: testing_api_pb2.KeysetFromJsonRequest,
     context: grpc.ServicerContext) -> testing_api_pb2.KeysetFromJsonResponse:
   """Converts a keyset from JSON to binary format."""
   try:
     keyset_handle = cleartext_keyset_handle.read(
         tink.JsonKeysetReader(request.json_keyset))
     keyset = io.BytesIO()
     cleartext_keyset_handle.write(
         tink.BinaryKeysetWriter(keyset), keyset_handle)
     return testing_api_pb2.KeysetFromJsonResponse(keyset=keyset.getvalue())
   except tink.TinkError as e:
     return testing_api_pb2.KeysetFromJsonResponse(err=str(e))
Beispiel #15
0
def main(argv):
    del argv  # Unused.

    # Initialise Tink.
    try:
        mac.register()
    except tink.TinkError as e:
        logging.error('Error initialising Tink: %s', e)
        return 1

    # Read the keyset into a keyset_handle.
    with open(FLAGS.keyset_path, 'rt') as keyset_file:
        try:
            text = keyset_file.read()
            keyset_handle = cleartext_keyset_handle.read(
                tink.JsonKeysetReader(text))
        except tink.TinkError as e:
            logging.error('Error reading key: %s', e)
            return 1

    # Get the primitive.
    try:
        cipher = keyset_handle.primitive(mac.Mac)
    except tink.TinkError as e:
        logging.error('Error creating primitive: %s', e)
        return 1

    with open(FLAGS.data_path, 'rb') as data_file:
        data = data_file.read()

    if FLAGS.mode == 'compute':
        # Compute the MAC.
        code = cipher.compute_mac(data)
        with open(FLAGS.mac_path, 'wb') as mac_file:
            mac_file.write(binascii.hexlify(code))
        return 0

    with open(FLAGS.mac_path, 'rb') as mac_file:
        try:
            expected_mac = binascii.unhexlify(mac_file.read().strip())
        except binascii.Error as e:
            logging.exception('Error reading expected code: %s', e)
            return 1

    try:
        cipher.verify_mac(expected_mac, data)
        logging.info('MAC verification succeeded.')
        return 0
    except tink.TinkError as e:
        logging.info('MAC verification failed.')
        return 1
def example():
    """Encrypt and decrypt using deterministic AEAD."""
    # Register the deterministic AEAD key manager. This is needed to create a
    # DeterministicAead primitive later.
    daead.register()

    # A keyset created with "tinkey create-keyset --key-template=AES256_SIV". Note
    # that this keyset has the secret key information in cleartext.
    keyset = r"""{
      "key": [{
          "keyData": {
              "keyMaterialType":
                  "SYMMETRIC",
              "typeUrl":
                  "type.googleapis.com/google.crypto.tink.AesSivKey",
              "value":
                  "EkAl9HCMmKTN1p3V186uhZpJQ+tivyc4IKyE+opg6SsEbWQ/WesWHzwCRrlgRuxdaggvgMzwWhjPnkk9gptBnGLK"
          },
          "keyId": 1919301694,
          "outputPrefixType": "TINK",
          "status": "ENABLED"
      }],
      "primaryKeyId": 1919301694
  }"""

    # Create a keyset handle from the cleartext keyset in the previous
    # step. The keyset handle provides abstract access to the underlying keyset to
    # limit the exposure of accessing the raw key material. WARNING: In practice
    # it is unlikely you will want to use a cleartext_keyset_handle, as it implies
    # that your key material is passed in cleartext which is a security risk.
    keyset_handle = cleartext_keyset_handle.read(tink.JsonKeysetReader(keyset))

    # Retrieve the DeterministicAead primitive we want to use from the keyset
    # handle.
    primitive = keyset_handle.primitive(daead.DeterministicAead)

    # Use the primitive to encrypt a message. In this case the primary key of the
    # keyset will be used (which is also the only key in this example).
    ciphertext = primitive.encrypt_deterministically(b'msg',
                                                     b'associated_data')

    # Use the primitive to decrypt the message. Decrypt finds the correct key in
    # the keyset and decrypts the ciphertext. If no key is found or decryption
    # fails, it raises an error.
    output = primitive.decrypt_deterministically(ciphertext,
                                                 b'associated_data')
    # [END deterministic-aead-basic-example]
    assert output == b'msg'
Beispiel #17
0
def main(argv):
    del argv  # Unused.

    associated_data = b'' if not FLAGS.associated_data else bytes(
        FLAGS.associated_data, 'utf-8')

    # Initialise Tink
    try:
        daead.register()
    except tink.TinkError as e:
        logging.error('Error initialising Tink: %s', e)
        return 1

    # Read the keyset into a keyset_handle
    with open(FLAGS.keyset_path, 'rt') as keyset_file:
        try:
            text = keyset_file.read()
            keyset_handle = cleartext_keyset_handle.read(
                tink.JsonKeysetReader(text))
        except tink.TinkError as e:
            logging.exception('Error reading key: %s', e)
            return 1

    # Get the primitive
    try:
        cipher = keyset_handle.primitive(daead.DeterministicAead)
    except tink.TinkError as e:
        logging.error('Error creating primitive: %s', e)
        return 1

    with open(FLAGS.input_path, 'rb') as input_file:
        input_data = input_file.read()
        if FLAGS.mode == 'decrypt':
            output_data = cipher.decrypt_deterministically(
                input_data, associated_data)
        elif FLAGS.mode == 'encrypt':
            output_data = cipher.encrypt_deterministically(
                input_data, associated_data)
        else:
            logging.error(
                'Error mode not supported. Please choose "encrypt" or "decrypt".'
            )
            return 1

        with open(FLAGS.output_path, 'wb') as output_file:
            output_file.write(output_data)
Beispiel #18
0
def example():
  """Encrypt and decrypt using AEAD."""
  # Register the AEAD key managers. This is needed to create an Aead primitive
  # later.
  aead.register()

  # A keyset created with "tinkey create-keyset --key-template=AES256_GCM". Note
  # that this keyset has the secret key information in cleartext.
  keyset = r"""{
      "key": [{
          "keyData": {
              "keyMaterialType":
                  "SYMMETRIC",
              "typeUrl":
                  "type.googleapis.com/google.crypto.tink.AesGcmKey",
              "value":
                  "GiBWyUfGgYk3RTRhj/LIUzSudIWlyjCftCOypTr0jCNSLg=="
          },
          "keyId": 294406504,
          "outputPrefixType": "TINK",
          "status": "ENABLED"
      }],
      "primaryKeyId": 294406504
  }"""

  # Create a keyset handle from the cleartext keyset in the previous
  # step. The keyset handle provides abstract access to the underlying keyset to
  # limit the exposure of accessing the raw key material. WARNING: In practice
  # it is unlikely you will want to use a cleartext_keyset_handle, as it implies
  # that your key material is passed in cleartext which is a security risk.
  keyset_handle = cleartext_keyset_handle.read(tink.JsonKeysetReader(keyset))

  # Retrieve the Aead primitive we want to use from the keyset handle.
  primitive = keyset_handle.primitive(aead.Aead)

  # Use the primitive to encrypt a message. In this case the primary key of the
  # keyset will be used (which is also the only key in this example).
  ciphertext = primitive.encrypt(b'msg', b'associated_data')

  # Use the primitive to decrypt the message. Decrypt finds the correct key in
  # the keyset and decrypts the ciphertext. If no key is found or decryption
  # fails, it raises an error.
  output = primitive.decrypt(ciphertext, b'associated_data')
  # [END aead-basic-example]
  assert output == b'msg'
def main(argv):
    del argv

    associated_data = b'' if not FLAGS.associated_data else bytes(
        FLAGS.associated_data, 'utf-8')

    # Initialise Tink.
    try:
        streaming_aead.register()
    except tink.TinkError as e:
        logging.exception('Error initialising Tink: %s', e)
        return 1

    # Read the keyset into a keyset_handle.
    with open(FLAGS.keyset_path, 'rt') as keyset_file:
        try:
            text = keyset_file.read()
            keyset_handle = cleartext_keyset_handle.read(
                tink.JsonKeysetReader(text))
        except tink.TinkError as e:
            logging.exception('Error reading key: %s', e)
            return 1

    # Get the primitive.
    try:
        streaming_aead_primitive = keyset_handle.primitive(
            streaming_aead.StreamingAead)
    except tink.TinkError as e:
        logging.exception(
            'Error creating streaming AEAD primitive from keyset: %s', e)
        return 1

    # Encrypt or decrypt the file.
    with open(FLAGS.input_path, 'rb') as input_file:
        with open(FLAGS.output_path, 'wb') as output_file:
            if FLAGS.mode == 'encrypt':
                encrypt_file(input_file, output_file, associated_data,
                             streaming_aead_primitive)
            elif FLAGS.mode == 'decrypt':
                decrypt_file(input_file, output_file, associated_data,
                             streaming_aead_primitive)
Beispiel #20
0
 def test_read(self):
   json_keyset = """
       {
         "primaryKeyId": 42,
         "key": [
           {
             "keyData": {
               "typeUrl": "type.googleapis.com/google.crypto.tink.AesGcmKey",
               "keyMaterialType": "SYMMETRIC",
               "value": "GhCS/1+ejWpx68NfGt6ziYHd"
             },
             "outputPrefixType": "TINK",
             "keyId": 42,
             "status": "ENABLED"
           }
         ]
       }"""
   reader = tink.JsonKeysetReader(json_keyset)
   keyset = reader.read()
   self.assertEqual(keyset.primary_key_id, 42)
   self.assertLen(keyset.key, 1)
    def encrypt_with_cluster_key(self, cluster_public_key, secret,
                                 openssl_executable):
        if openssl_executable:
            return self.encode_token_using_openssl(cluster_public_key, secret,
                                                   openssl_executable)
        try:
            # pylint: disable=g-import-not-at-top
            import tink
            from tink import hybrid
            from tink import cleartext_keyset_handle
            # pylint: enable=g-import-not-at-top
        except ImportError:
            raise exceptions.PersonalAuthError(
                'Cannot load the Tink cryptography library. Either the '
                'library is not installed, or site packages are not '
                'enabled for the Google Cloud SDK. Please consult Cloud '
                'Dataproc Personal Auth documentation on adding Tink to '
                'Google Cloud SDK for further instructions.\n'
                'https://cloud.google.com/dataproc/docs/concepts/iam/personal-auth'
            )

        hybrid.register()
        context = b''

        # Extract value of key corresponding to primary key.
        public_key_value = json.loads(
            cluster_public_key)['key'][0]['keyData']['value']
        cluster_key_hash = hashlib.sha256(
            (public_key_value + '\n').encode('utf-8')).hexdigest()

        # Load public key and create keyset handle.
        reader = tink.JsonKeysetReader(cluster_public_key)
        kh_pub = cleartext_keyset_handle.read(reader)

        # Create encrypter instance.
        encrypter = kh_pub.primitive(hybrid.HybridEncrypt)
        ciphertext = encrypter.encrypt(secret.encode('utf-8'), context)

        encoded_token = base64.b64encode(ciphertext).decode('utf-8')
        return '{}:{}'.format(cluster_key_hash, encoded_token)
Beispiel #22
0
 def test_read_encrypted(self):
   # encryptedKeyset is a base64-encoding of 'some ciphertext with keyset'
   json_encrypted_keyset = """
       {
         "encryptedKeyset": "c29tZSBjaXBoZXJ0ZXh0IHdpdGgga2V5c2V0",
         "keysetInfo": {
           "primaryKeyId": 42,
           "keyInfo": [
             {
               "typeUrl": "type.googleapis.com/google.crypto.tink.AesGcmKey",
               "outputPrefixType": "TINK",
               "keyId": 42,
               "status": "ENABLED"
             }
           ]
         }
       }"""
   reader = tink.JsonKeysetReader(json_encrypted_keyset)
   enc_keyset = reader.read_encrypted()
   self.assertEqual(enc_keyset.encrypted_keyset,
                    b'some ciphertext with keyset')
   self.assertLen(enc_keyset.keyset_info.key_info, 1)
   self.assertEqual(enc_keyset.keyset_info.key_info[0].type_url,
                    'type.googleapis.com/google.crypto.tink.AesGcmKey')
Beispiel #23
0
def main(argv):
    del argv  # Unused.

    # Initialise Tink
    try:
        jwt.register_jwt_signature()
    except tink.TinkError as e:
        logging.exception('Error initialising Tink: %s', e)
        return 1

    # Read the keyset into a KeysetHandle
    with open(FLAGS.keyset_path, 'rt') as keyset_file:
        try:
            text = keyset_file.read()
            keyset_handle = cleartext_keyset_handle.read(
                tink.JsonKeysetReader(text))
        except tink.TinkError as e:
            logging.exception('Error reading keyset: %s', e)
            return 1

    now = datetime.datetime.now(tz=datetime.timezone.utc)

    # Get the JwtPublicKeySign primitive
    try:
        jwt_sign = keyset_handle.primitive(jwt.JwtPublicKeySign)
    except tink.TinkError as e:
        logging.exception('Error creating JwtPublicKeySign: %s', e)
        return 1

    # Create token
    raw_jwt = jwt.new_raw_jwt(audiences=[FLAGS.audience],
                              expiration=now + datetime.timedelta(seconds=100))
    token = jwt_sign.sign_and_encode(raw_jwt)
    with open(FLAGS.token_path, 'wt') as token_file:
        token_file.write(token)
    logging.info('Token has been written to %s', FLAGS.token_path)
Beispiel #24
0
def main(argv):
    if len(argv) not in (3, 4):
        raise app.UsageError(
            'Expected 2 or 3 arguments, got %d.\n'
            'Usage: %s keyset-file data-file [expected-code-file]' %
            (len(argv) - 1, argv[0]))

    keyset_filename = argv[1]
    data_filename = argv[2]
    expected_code_filename = argv[3] if len(argv) == 4 else None

    if expected_code_filename is not None:
        with open(expected_code_filename, 'rb') as expected_code_file:
            expected_code_hex = expected_code_file.read().strip()

        logging.info(
            'Using keyset from file %s to verify file %s against expected code %s',
            keyset_filename, data_filename, expected_code_hex.decode('utf-8'))
    else:
        expected_code_hex = None
        logging.info('Using keyset from file %s to verify file %s',
                     keyset_filename, data_filename)

    # Initialise Tink.
    try:
        tink.tink_config.register()
    except tink.TinkError as e:
        logging.error('Error initialising Tink: %s', e)
        return 1

    # Read the keyset into a keyset_handle.
    with open(keyset_filename, 'rt') as keyset_file:
        try:
            text = keyset_file.read()
            keyset_handle = cleartext_keyset_handle.read(
                tink.JsonKeysetReader(text))
        except tink.TinkError as e:
            logging.error('Error reading key: %s', e)
            return 1

    # Get the primitive.
    try:
        cipher = keyset_handle.primitive(tink.Mac)
    except tink.TinkError as e:
        logging.error('Error creating primitive: %s', e)
        return 1

    # Compute the MAC.
    with open(data_filename, 'rb') as data_file:
        data = data_file.read()

    if expected_code_hex is None:
        code = cipher.compute_mac(data)
        logging.info('MAC output is %s',
                     binascii.hexlify(code).decode('utf-8'))
        return 0

    try:
        expected_code = binascii.unhexlify(expected_code_hex)
    except binascii.Error as e:
        logging.error('Error reading expected code: %s', e)
        return 1

    try:
        cipher.verify_mac(expected_code, data)
        logging.info('MAC outputs matched. Success!')
        return 0
    except tink.TinkError as e:
        logging.info('MAC outputs did not match!')
        code = binascii.hexlify(cipher.compute_mac(data)).decode('utf-8')
        logging.info('Actual MAC output is %s', code)
        return 1
Beispiel #25
0
def main(argv):
  if len(argv) != 3 and len(argv) != 5:
    raise app.UsageError(
        'Invalid arguments.\n'
        'Usage: %s generate key-file.\n'
        'Usage: %s encrypt/decrypt key-file '
        'input-file output-file.' % (argv[0], argv[0])
        )

  mode = argv[1]
  if mode not in ('encrypt', 'decrypt', 'generate'):
    raise app.UsageError(
        'The first argument should be either encrypt, decrypt or generate')

  key_file_path = argv[2]
  input_file_path = argv[3] if len(argv) == 5 else None
  output_file_path = argv[4] if len(argv) == 5 else None

  # Initialise Tink
  try:
    aead.register()
  except tink.TinkError as e:
    logging.error('Error initialising Tink: %s', e)
    return 1

  if mode == 'generate':
    # [START generate-a-new-keyset]
    # Generate a new keyset
    try:
      key_template = aead.aead_key_templates.AES128_GCM
      keyset_handle = tink.KeysetHandle.generate_new(key_template)
    except tink.TinkError as e:
      logging.exception('Error creating primitive: %s', e)
      return 1
    # [END generate-a-new-keyset]

    # [START store-a-cleartext-keyset]
    with open(key_file_path, 'wt') as keyset_file:
      try:
        cleartext_keyset_handle.write(
            tink.JsonKeysetWriter(keyset_file), keyset_handle)
      except tink.TinkError as e:
        logging.exception('Error writing key: %s', e)
        return 1
    return 0
    # [END store-a-cleartext-keyset]

  # Use the input keyset to encrypt/decrypt data

  # Read the keyset into a keyset_handle
  with open(key_file_path, 'rt') as keyset_file:
    try:
      text = keyset_file.read()
      keyset_handle = cleartext_keyset_handle.read(tink.JsonKeysetReader(text))
    except tink.TinkError as e:
      logging.exception('Error reading key: %s', e)
      return 1

  # Get the primitive
  try:
    cipher = keyset_handle.primitive(aead.Aead)
  except tink.TinkError as e:
    logging.error('Error creating primitive: %s', e)
    return 1

  with open(input_file_path, 'rb') as input_file:
    input_data = input_file.read()
    if mode == 'decrypt':
      output_data = cipher.decrypt(input_data, b'envelope_example')
    elif mode == 'encrypt':
      output_data = cipher.encrypt(input_data, b'envelope_example')
    else:
      logging.error(
          'Error mode not supported. Please choose "encrypt" or "decrypt".')
      return 1

    with open(output_file_path, 'wb') as output_file:
      output_file.write(output_data)
Beispiel #26
0
def main(argv):
    del argv  # Unused.

    associated_data = b'' if not FLAGS.associated_data else bytes(
        FLAGS.associated_data, 'utf-8')

    # Initialise Tink
    try:
        aead.register()
    except tink.TinkError as e:
        logging.error('Error initialising Tink: %s', e)
        return 1

    # Read the GCP credentials and set up a client
    try:
        gcpkms.GcpKmsClient.register_client(FLAGS.kek_uri,
                                            FLAGS.gcp_credential_path)
    except tink.TinkError as e:
        logging.error('Error initializing GCP client: %s', e)
        return 1

    # Create an AEAD primitive from the key-encryption key (KEK) for encrypting
    # Tink keysets
    try:
        handle = tink.KeysetHandle.generate_new(
            aead.aead_key_templates.create_kms_aead_key_template(
                key_uri=FLAGS.kek_uri))
        gcp_aead = handle.primitive(aead.Aead)
    except tink.TinkError as e:
        logging.exception('Error creating KMS AEAD primitive: %s', e)
        return 1

    if FLAGS.mode == 'generate':
        # [START generate-a-new-keyset]
        # Generate a new keyset
        try:
            key_template = aead.aead_key_templates.AES128_GCM
            keyset_handle = tink.KeysetHandle.generate_new(key_template)
        except tink.TinkError as e:
            logging.exception('Error creating primitive: %s', e)
            return 1
        # [END generate-a-new-keyset]

        # [START encrypt-a-keyset]
        # Encrypt the keyset_handle with the remote key-encryption key (KEK)
        with open(FLAGS.keyset_path, 'wt') as keyset_file:
            try:
                keyset_handle.write(tink.JsonKeysetWriter(keyset_file),
                                    gcp_aead)
            except tink.TinkError as e:
                logging.exception('Error writing key: %s', e)
                return 1
        return 0
        # [END encrypt-a-keyset]

    # Use the keyset to encrypt/decrypt data

    # Read the encrypted keyset into a keyset_handle
    with open(FLAGS.keyset_path, 'rt') as keyset_file:
        try:
            text = keyset_file.read()
            keyset_handle = tink.KeysetHandle.read(tink.JsonKeysetReader(text),
                                                   gcp_aead)
        except tink.TinkError as e:
            logging.exception('Error reading key: %s', e)
            return 1

    # Get the primitive
    try:
        cipher = keyset_handle.primitive(aead.Aead)
    except tink.TinkError as e:
        logging.error('Error creating primitive: %s', e)
        return 1

    with open(FLAGS.input_path, 'rb') as input_file:
        input_data = input_file.read()
        if FLAGS.mode == 'decrypt':
            output_data = cipher.decrypt(input_data, associated_data)
        elif FLAGS.mode == 'encrypt':
            output_data = cipher.encrypt(input_data, associated_data)
        else:
            logging.error(
                'Error mode not supported. Please choose "encrypt" or "decrypt".'
            )
            return 1

        with open(FLAGS.output_path, 'wb') as output_file:
            output_file.write(output_data)
 def test_from_private_keyset_fails(self):
   reader = tink.JsonKeysetReader(PRIVATEKEY_KEYSET)
   keyset_handle = cleartext_keyset_handle.read(reader)
   with self.assertRaises(tink.TinkError):
     jwt.jwk_set_from_public_keyset_handle(keyset_handle)
 def test_from_crunchy_ecdsa_keyset_fails(self, keyset):
   crunchy_keyset = keyset.replace('RAW', 'CRUNCHY')
   reader = tink.JsonKeysetReader(crunchy_keyset)
   keyset_handle = cleartext_keyset_handle.read(reader)
   with self.assertRaises(tink.TinkError):
     jwt.jwk_set_from_public_keyset_handle(keyset_handle)
 def test_primary_key_id_missing_success(self):
   keyset = ES256_KEYSET.replace('"primaryKeyId":282600252,', '')
   reader = tink.JsonKeysetReader(keyset)
   keyset_handle = cleartext_keyset_handle.read(reader)
   jwk_set = jwt.jwk_set_from_public_keyset_handle(keyset_handle)
   self.assertEqual(jwk_set, ES256_JWK_SET)
 def test_convert_from_jwt_key(self, tink_keyset, expected_jwk_set):
   reader = tink.JsonKeysetReader(tink_keyset)
   keyset_handle = cleartext_keyset_handle.read(reader)
   jwk_set = jwt.jwk_set_from_public_keyset_handle(keyset_handle)
   self.assertEqual(jwk_set, expected_jwk_set)