Class: Mongo::Auth::ScramConversationBase Private

Inherits:
SaslConversationBase show all
Defined in:
lib/mongo/auth/scram_conversation_base.rb

Overview

This class is part of a private API. You should avoid using this class if possible, as it may be removed or be changed in the future.

Defines common behavior around authentication conversations between the client and the server.

Since:

  • 2.0.0

API:

  • private

Constant Summary collapse

MIN_ITER_COUNT =

This constant is part of a private API. You should avoid using this constant if possible, as it may be removed or be changed in the future.

The minimum iteration count for SCRAM-SHA-1 and SCRAM-SHA-256.

Since:

  • 2.0.0

API:

  • private

4096

Constants inherited from SaslConversationBase

Mongo::Auth::SaslConversationBase::CLIENT_CONTINUE_MESSAGE, Mongo::Auth::SaslConversationBase::CLIENT_FIRST_MESSAGE

Instance Attribute Summary collapse

Attributes inherited from ConversationBase

#connection, #user

Instance Method Summary collapse

Methods inherited from SaslConversationBase

#start

Methods inherited from ConversationBase

#build_message, #validate_external_auth_source

Constructor Details

#initialize(user, connection, client_nonce: nil) ⇒ ScramConversationBase

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.

Create the new conversation.

Parameters:

  • The user to converse about.

  • (defaults to: nil)

    The client nonce to use. If this conversation is created for a connection that performed speculative authentication, this client nonce must be equal to the client nonce used for speculative authentication; otherwise, the client nonce must not be specified.

Since:

  • 2.0.0

API:

  • private



38
39
40
41
# File 'lib/mongo/auth/scram_conversation_base.rb', line 38

def initialize(user, connection, client_nonce: nil)
  super
  @client_nonce = client_nonce || SecureRandom.base64
end

Instance Attribute Details

#client_nonceString (readonly)

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.

Returns client_nonce The client nonce.

Returns:

  • client_nonce The client nonce.

Since:

  • 2.0.0

API:

  • private



44
45
46
# File 'lib/mongo/auth/scram_conversation_base.rb', line 44

def client_nonce
  @client_nonce
end

#idInteger (readonly)

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.

Get the id of the conversation.

Examples:

Get the id of the conversation.

conversation.id

Returns:

  • The conversation id.

Since:

  • 2.0.0

API:

  • private



52
53
54
# File 'lib/mongo/auth/scram_conversation_base.rb', line 52

def id
  @id
end

Instance Method Details

#continue(reply_document, connection) ⇒ Protocol::Message

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.

Continue the SCRAM conversation. This sends the client final message to the server after setting the reply from the previous server communication.

Parameters:

  • The reply document of the previous message.

  • The connection being authenticated.

Returns:

  • The next message to send.

Since:

  • 2.0.0

API:

  • private



73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
# File 'lib/mongo/auth/scram_conversation_base.rb', line 73

def continue(reply_document, connection)
  @id = reply_document['conversationId']
  payload_data = reply_document['payload'].data
  parsed_data = parse_payload(payload_data)
  @server_nonce = parsed_data.fetch('r')
  @salt = Base64.strict_decode64(parsed_data.fetch('s'))
  @iterations = parsed_data.fetch('i').to_i.tap do |i|
    if i < MIN_ITER_COUNT
      raise Error::InsufficientIterationCount.new(
        Error::InsufficientIterationCount.message(MIN_ITER_COUNT, i))
    end
  end
  @auth_message = "#{first_bare},#{payload_data},#{without_proof}"

  validate_server_nonce!

  selector = CLIENT_CONTINUE_MESSAGE.merge(
    payload: client_final_message,
    conversationId: id,
  )
  build_message(connection, user.auth_source, selector)
end

#finalize(connection) ⇒ Protocol::Message

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.

Finalize the SCRAM conversation. This is meant to be iterated until the provided reply indicates the conversation is finished.

Parameters:

  • The connection being authenticated.

Returns:

  • The next message to send.

Since:

  • 2.0.0

API:

  • private



111
112
113
114
115
116
117
# File 'lib/mongo/auth/scram_conversation_base.rb', line 111

def finalize(connection)
  selector = CLIENT_CONTINUE_MESSAGE.merge(
    payload: client_empty_message,
    conversationId: id,
  )
  build_message(connection, user.auth_source, selector)
end

#process_continue_response(reply_document) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.

Processes the second response from the server.

Parameters:

  • The reply document of the continue response.

Since:

  • 2.0.0

API:

  • private



100
101
102
103
# File 'lib/mongo/auth/scram_conversation_base.rb', line 100

def process_continue_response(reply_document)
  payload_data = parse_payload(reply_document['payload'].data)
  check_server_signature(payload_data)
end

#server_verified?true | fase

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.

Whether the client verified the ServerSignature from the server.

Returns:

  • Whether the server’s signature was verified.

See Also:

Since:

  • 2.0.0

API:

  • private



59
60
61
# File 'lib/mongo/auth/scram_conversation_base.rb', line 59

def server_verified?
  !!@server_verified
end

#speculative_auth_documentHash | nil

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.

Returns the hash to provide to the server in the handshake as value of the speculativeAuthenticate key.

If the auth mechanism does not support speculative authentication, this method returns nil.

Returns:

  • Speculative authentication document.

Since:

  • 2.0.0

API:

  • private



126
127
128
# File 'lib/mongo/auth/scram_conversation_base.rb', line 126

def speculative_auth_document
  client_first_document.merge(db: user.auth_source)
end