123456789_123456789_123456789_123456789_123456789_

Class: Mongo::Crypt::ExplicitEncryptionContext Private

Relationships & Source Files
Extension / Inclusion / Inheritance Descendants
Subclasses:
Super Chains via Extension / Inclusion / Inheritance
Class Chain:
self, Context, Forwardable
Instance Chain:
self, Context
Inherits: Mongo::Crypt::Context
Defined in: lib/mongo/crypt/explicit_encryption_context.rb

Overview

A Context object initialized for explicit encryption

Class Method Summary

Context - Inherited

.new

Create a new Context object.

Instance Attribute Summary

Context - Inherited

Instance Method Summary

Context - Inherited

#bson_mode

Which BSON mode to use when creating documents from the outcome of the state machine.

#run_state_machine

Runs the mongocrypt_ctx_t state machine and handles all I/O on behalf of.

#state

Returns the state of the mongocrypt_ctx_t.

#azure_access_token

Returns an Azure access token, retrieving it if necessary.

#feed_collection_info, #feed_kms,
#gcp_access_token

Retrieves a GCP access token.

#mongocrypt_done

Indicate that state machine is done feeding I/O responses back to libmongocrypt.

#mongocrypt_feed

Feeds the result of a ::Mongo operation back to libmongocrypt.

#provide_collection_info, #provide_collection_info_with_db, #provide_keys, #provide_markings,
#raise_kms_retry_error

Raise a KmsError that wraps the KMS status message (which describes the retry exhaustion) with the error from the last attempt.

#retrieve_kms_credentials

Retrieves KMS credentials for providers that are configured for automatic credentials retrieval.

Constructor Details

.new(mongocrypt, io, doc, options = {}) ⇒ ExplicitEncryptionContext

Note:

The Range algorithm is experimental only. It is not intended for

Note:

The "substring" query type is unstable and subject to backwards

Create a new ExplicitEncryptionContext object

public use. breaking changes.

Parameters:

  • mongocrypt (Mongo::Crypt::Handle)

    a Handle that wraps a mongocrypt_t object used to create a new mongocrypt_ctx_t

  • io (ClientEncryption::IO)

    A instance of the IO class that implements driver I/O methods required to run the state machine

  • doc (BSON::Document)

    A document to encrypt

  • options (Hash) (defaults to: {})

Options Hash (options):

  • :key_id (BSON::Binary)

    A BSON::Binary object of type :uuid representing the UUID of the data key to use for encryption.

  • :key_alt_name (String)

    The alternate name of the data key that will be used to encrypt the value.

  • :algorithm (String)

    The algorithm used to encrypt the value. Valid algorithms are "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic", "AEAD_AES_256_CBC_HMAC_SHA_512-Random", "Indexed", "Unindexed", "Range", "String".

  • :contention_factor (Integer | nil)

    Contention factor to be applied if encryption algorithm is set to "Indexed", "Range", or "String". If not provided, it defaults to a value of 0. Contention factor should be set only if encryption algorithm is set to "Indexed", "Range", or "String".

  • query_type (String | nil)

    Query type to be applied if encryption algorithm is set to "Indexed", "Range", or "String". Allowed values are "equality", "range", "prefix", "suffix", and "substring".

  • :range_opts (Hash | nil)

    Specifies index options for a Queryable Encryption field supporting "range" queries. Allowed options are:

    • :min
    • :max
    • :trim_factor
    • :sparsity
    • :precision min, max, trim_factor, sparsity, and precision must match the values set in the encryptedFields of the destination collection. For double and decimal128, min/max/precision must all be set, or all be unset.
  • :string_opts (Hash | nil)

    Specifies index options for a Queryable Encryption field supporting "prefix", "suffix", or "substring" queries (algorithm "String"). Allowed options are:

    • :case_sensitive
    • :diacritic_sensitive
    • :prefix (Hash with :str_min_query_length, :str_max_query_length)
    • :suffix (Hash with :str_min_query_length, :str_max_query_length)
    • :substring (Hash with :str_max_length, :str_min_query_length, :str_max_query_length) The options must match the values set in the encryptedFields of the destination collection.

Raises:

[ GitHub ]

  
# File 'lib/mongo/crypt/explicit_encryption_context.rb', line 79

def initialize(mongocrypt, io, doc, options = {})
  super(mongocrypt, io)
  set_key_opts(options)
  set_algorithm_opts(options)
  init(doc)
end

Instance Method Details

#convert_range_opts(range_opts) (private)

Raises:

  • (ArgumentError)
[ GitHub ]

  
# File 'lib/mongo/crypt/explicit_encryption_context.rb', line 150

def convert_range_opts(range_opts)
  raise ArgumentError.new(':range_opts is required for the "Range" algorithm') if range_opts.nil?

  range_opts.dup.tap do |opts|
    opts[:sparsity] = BSON::Int64.new(opts[:sparsity]) if opts[:sparsity] && !opts[:sparsity].is_a?(BSON::Int64)
    opts[:trimFactor] = opts.delete(:trim_factor) if opts[:trim_factor]
  end
end

#convert_string_opts(string_opts) (private)

Raises:

  • (ArgumentError)
[ GitHub ]

  
# File 'lib/mongo/crypt/explicit_encryption_context.rb', line 159

def convert_string_opts(string_opts)
  raise ArgumentError.new(':string_opts is required for the "String" algorithm') if string_opts.nil?

  string_opts.dup.tap do |opts|
    opts[:caseSensitive] = opts.delete(:case_sensitive) if opts.key?(:case_sensitive)
    opts[:diacriticSensitive] = opts.delete(:diacritic_sensitive) if opts.key?(:diacritic_sensitive)
    %i[substring prefix suffix].each do |query_type|
      opts[query_type] = convert_string_query_opts(opts[query_type]) if opts[query_type]
    end
  end
end

#convert_string_query_opts(query_opts) (private)

[ GitHub ]

  
# File 'lib/mongo/crypt/explicit_encryption_context.rb', line 171

def convert_string_query_opts(query_opts)
  query_opts.dup.tap do |opts|
    opts[:strMaxLength] = opts.delete(:str_max_length) if opts.key?(:str_max_length)
    opts[:strMinQueryLength] = opts.delete(:str_min_query_length) if opts.key?(:str_min_query_length)
    opts[:strMaxQueryLength] = opts.delete(:str_max_query_length) if opts.key?(:str_max_query_length)
  end
end

#init(doc)

[ GitHub ]

  
# File 'lib/mongo/crypt/explicit_encryption_context.rb', line 86

def init(doc)
  Binding.ctx_explicit_encrypt_init(self, doc)
end

#set_algorithm_opts(options) (private)

[ GitHub ]

  
# File 'lib/mongo/crypt/explicit_encryption_context.rb', line 130

def set_algorithm_opts(options)
  Binding.ctx_setopt_algorithm(self, options[:algorithm])
  if %w[Indexed Range String].include?(options[:algorithm])
    Binding.ctx_setopt_contention_factor(self, options[:contention_factor]) if options[:contention_factor]
    Binding.ctx_setopt_query_type(self, options[:query_type]) if options[:query_type]
  else
    if options[:contention_factor]
      raise ArgumentError.new(':contention_factor is allowed only for "Indexed", "Range", or "String" algorithms')
    end
    if options[:query_type]
      raise ArgumentError.new(':query_type is allowed only for "Indexed", "Range", or "String" algorithms')
    end
  end
  if options[:algorithm] == 'Range'
    Binding.ctx_setopt_algorithm_range(self, convert_range_opts(options[:range_opts]))
  elsif options[:algorithm] == 'String'
    Binding.ctx_setopt_algorithm_text(self, convert_string_opts(options[:string_opts]))
  end
end

#set_key_alt_name(key_alt_name) (private)

Raises:

  • (ArgumentError)
[ GitHub ]

  
# File 'lib/mongo/crypt/explicit_encryption_context.rb', line 124

def set_key_alt_name(key_alt_name)
  raise ArgumentError.new(':key_alt_name option must be a String') unless key_alt_name.is_a?(String)

  Binding.ctx_setopt_key_alt_names(self, [ key_alt_name ])
end

#set_key_id(key_id) (private)

[ GitHub ]

  
# File 'lib/mongo/crypt/explicit_encryption_context.rb', line 113

def set_key_id(key_id)
  unless key_id.is_a?(BSON::Binary) &&
         key_id.type == :uuid
    raise ArgumentError.new(
      'Expected the :key_id option to be a BSON::Binary object with ' +
      "type :uuid. #{key_id} is an invalid :key_id option"
    )
  end
  Binding.ctx_setopt_key_id(self, key_id.data)
end

#set_key_opts(options) (private)

[ GitHub ]

  
# File 'lib/mongo/crypt/explicit_encryption_context.rb', line 92

def set_key_opts(options)
  if options[:key_id].nil? && options[:key_alt_name].nil?
    raise ArgumentError.new(
      'The :key_id and :key_alt_name options cannot both be nil. ' +
      'Specify a :key_id option or :key_alt_name option (but not both)'
    )
  end
  if options[:key_id] && options[:key_alt_name]
    raise ArgumentError.new(
      'The :key_id and :key_alt_name options cannot both be present. ' +
      'Identify the data key by specifying its id with the :key_id ' +
      'option or specifying its alternate name with the :key_alt_name option'
    )
  end
  if options[:key_id]
    set_key_id(options[:key_id])
  elsif options[:key_alt_name]
    set_key_alt_name(options[:key_alt_name])
  end
end