Class: Mongo::Server::Monitor::Connection Private

Inherits:
ConnectionCommon show all
Includes:
Loggable
Defined in:
build/ruby-driver-master/lib/mongo/server/monitor/connection.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.

This class models the monitor connections and their behavior.

Since:

  • 2.0.0

Direct Known Subclasses

PushMonitor::Connection

Constant Summary

Constants included from Loggable

Loggable::PREFIX

Instance Attribute Summary collapse

Attributes inherited from ConnectionCommon

#compressor, #pid

Instance Method Summary collapse

Methods included from Loggable

#log_debug, #log_error, #log_fatal, #log_info, #log_warn, #logger

Methods inherited from ConnectionCommon

#connected?, #handshake_command, #handshake_document

Constructor Details

#initialize(address, options = {}) ⇒ Connection

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.

Note:

Monitoring connections do not authenticate.

Creates a new connection object to the specified target address with the specified options.

The constructor does not perform any I/O (and thus does not create sockets nor handshakes); call connect! method on the connection object to create the network connection.

Parameters:

  • address (Mongo::Address)

    The address the connection is for.

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

    The connection options.

Options Hash (options):

  • :app_metadata (Mongo::Server::Monitor::AppMetadata)

    Metadata to use for handshake. If missing or nil, handshake will not be performed. Although a Mongo::Server::AppMetadata instance will also work, monitoring connections are meant to use Mongo::Server::Monitor::AppMetadata instances in order to omit performing SCRAM negotiation with the server, as monitoring sockets do not authenticate.

  • :compressors (Array<String>)

    A list of potential compressors to use, in order of preference. The driver chooses the first compressor that is also supported by the server. Currently the driver only supports 'zstd', 'snappy' and 'zlib'.

  • :connect_timeout (Float)

    The timeout, in seconds, to use for network operations. This timeout is used for all socket operations rather than connect calls only, contrary to what the name implies,

Since:

  • 2.0.0



58
59
60
61
62
63
64
65
66
67
68
# File 'build/ruby-driver-master/lib/mongo/server/monitor/connection.rb', line 58

def initialize(address, options = {})
  @address = address
  @options = options.dup.freeze
  unless @app_metadata = options[:app_metadata]
    raise ArgumentError, 'App metadata is required'
  end
  @socket = nil
  @pid = Process.pid
  @compressor = nil
  @hello_ok = false
end

Instance Attribute Details

#addressMongo::Address (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 address The address to connect to.

Returns:

Since:

  • 2.0.0



74
75
76
# File 'build/ruby-driver-master/lib/mongo/server/monitor/connection.rb', line 74

def address
  @address
end

#optionsHash (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 options The passed in options.

Returns:

  • (Hash)

    options The passed in options.

Since:

  • 2.0.0



71
72
73
# File 'build/ruby-driver-master/lib/mongo/server/monitor/connection.rb', line 71

def options
  @options
end

#server_connection_idObject (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.

Since:

  • 2.0.0



89
90
91
# File 'build/ruby-driver-master/lib/mongo/server/monitor/connection.rb', line 89

def server_connection_id
  @server_connection_id
end

Instance Method Details

#check_documentBSON::Document

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.

Build a document that should be used for connection check.

Returns:

  • (BSON::Document)

    Document that should be sent to a server for connection check.

Since:

  • 2.0.0



228
229
230
231
232
233
234
235
236
237
238
239
# File 'build/ruby-driver-master/lib/mongo/server/monitor/connection.rb', line 228

def check_document
  server_api = @app_metadata.server_api || options[:server_api]
  if hello_ok? || server_api
    doc = HELLO_DOC
    if server_api
      doc = doc.merge(Utils.transform_server_api(server_api))
    end
    doc
  else
    LEGACY_HELLO_DOC
  end
end

#connect!true

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.

Note:

This method mutates the connection class by setting a socket if one previously did not exist.

Establishes a network connection to the target address.

If the connection is already established, this method does nothing.

Examples:

Connect to the host.

connection.connect!

Returns:

  • (true)

    If the connection succeeded.

Since:

  • 2.0.0



157
158
159
160
161
162
163
164
165
166
167
# File 'build/ruby-driver-master/lib/mongo/server/monitor/connection.rb', line 157

def connect!
  if @socket
    raise ArgumentError, 'Monitoring connection already connected'
  end

  @socket = add_server_diagnostics do
    address.socket(socket_timeout, ssl_options.merge(
      connection_address: address, monitor: true))
  end
  true
end

#disconnect!(options = nil) ⇒ true

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.

Note:

This method mutates the connection by setting the socket to nil if the closing succeeded.

Note:

This method accepts an options argument for compatibility with Server::Connections. However, all options are ignored.

Disconnect the connection.

Examples:

Disconnect from the host.

connection.disconnect!

Returns:

  • (true)

    If the disconnect succeeded.

Since:

  • 2.0.0



183
184
185
186
187
188
189
# File 'build/ruby-driver-master/lib/mongo/server/monitor/connection.rb', line 183

def disconnect!(options = nil)
  if socket
    socket.close rescue nil
    @socket = nil
  end
  true
end

#dispatch(message) ⇒ 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.

Sends a message and returns the result.

Parameters:

Returns:

Since:

  • 2.0.0



96
97
98
# File 'build/ruby-driver-master/lib/mongo/server/monitor/connection.rb', line 96

def dispatch(message)
  dispatch_bytes(message.serialize.to_s)
end

#dispatch_bytes(bytes, **opts) ⇒ 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.

Sends a preserialized message and returns the result.

Parameters:

  • bytes (String)

    The serialized message to send.

  • opts (Hash)

    a customizable set of options

Options Hash (**opts):

  • :read_socket_timeout (Numeric)

    The timeout to use for each read operation.

Returns:

Since:

  • 2.0.0



108
109
110
111
112
113
# File 'build/ruby-driver-master/lib/mongo/server/monitor/connection.rb', line 108

def dispatch_bytes(bytes, **opts)
  write_bytes(bytes)
  read_response(
    socket_timeout: opts[:read_socket_timeout],
  )
end

#handshake!BSON::Document

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.

Send handshake command to connected host and validate the response.

Returns:

  • (BSON::Document)

    Handshake response from server

Raises:

Since:

  • 2.0.0



196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
# File 'build/ruby-driver-master/lib/mongo/server/monitor/connection.rb', line 196

def handshake!
  command = handshake_command(
    handshake_document(
      @app_metadata,
      server_api: options[:server_api]
    )
  )
  payload = command.serialize.to_s
  message = dispatch_bytes(payload)
  result = Operation::Result.new(message)
  result.validate!
  reply = result.documents.first
  set_compressor!(reply)
  set_hello_ok!(reply)
  @server_connection_id = reply['connectionId']
  reply
rescue => exc
  msg = "Failed to handshake with #{address}"
  Utils.warn_bg_exception(msg, exc,
    logger: options[:logger],
    log_prefix: options[:log_prefix],
    bg_error_backtrace: options[:bg_error_backtrace],
  )
  raise
end

#read_response(**opts) ⇒ 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.

Parameters:

  • opts (Hash)

    a customizable set of options

Options Hash (**opts):

  • :socket_timeout (Numeric)

    The timeout to use for each read operation.

Since:

  • 2.0.0



129
130
131
132
133
134
135
136
137
138
139
140
141
142
# File 'build/ruby-driver-master/lib/mongo/server/monitor/connection.rb', line 129

def read_response(**opts)
  unless connected?
    raise ArgumentError, "Trying to read on an unconnected connection #{self}"
  end

  add_server_connection_id do
    add_server_diagnostics do
      Protocol::Message.deserialize(socket,
        Protocol::Message::MAX_MESSAGE_SIZE,
        nil,
        **opts)
    end
  end
end

#socket_timeoutFloat

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 monitoring socket timeout.

Note that monitoring connections use the connect timeout value as the socket timeout value. See the Server Discovery and Monitoring specification for details.

Returns:

  • (Float)

    The socket timeout in seconds.

Since:

  • 2.4.3



85
86
87
# File 'build/ruby-driver-master/lib/mongo/server/monitor/connection.rb', line 85

def socket_timeout
  options[:connect_timeout] || Server::CONNECT_TIMEOUT
end

#write_bytes(bytes) ⇒ 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.

Since:

  • 2.0.0



115
116
117
118
119
120
121
122
123
124
125
# File 'build/ruby-driver-master/lib/mongo/server/monitor/connection.rb', line 115

def write_bytes(bytes)
  unless connected?
    raise ArgumentError, "Trying to dispatch on an unconnected connection #{self}"
  end

  add_server_connection_id do
    add_server_diagnostics do
      socket.write(bytes)
    end
  end
end