Class: PG::Connection

Inherits:
Object show all
Defined in:
lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb

Overview

The PostgreSQL connection class. The interface for this class is based on libpq, the C application programmer’s interface to PostgreSQL. Some familiarity with libpq is recommended, but not necessary.

For example, to send query to the database on the localhost:

require 'pg'
conn = PG::Connection.open(:dbname => 'test')
res = conn.exec_params('SELECT $1 AS a, $2 AS b, $3 AS c', [1, 2, nil])
# Equivalent to:
#  res  = conn.exec('SELECT 1 AS a, 2 AS b, NULL AS c')

See the PG::Result class for information on working with the results of a query.

Many methods of this class have three variants kind of:

  1. #exec - the base method which is an alias to #async_exec . This is the method that should be used in general.

  2. #async_exec - the async aware version of the method, implemented by libpq’s async API.

  3. #sync_exec - the method version that is implemented by blocking function(s) of libpq.

Sync and async version of the method can be switched by Connection.async_api= , however it is not recommended to change the default.

Constant Summary collapse

CONNECT_ARGUMENT_ORDER =

The order the options are passed to the ::connect method.

%w[host port options tty dbname user password]
REDIRECT_CLASS_METHODS =
{
  :new => [:async_connect, :sync_connect],
  :connect => [:async_connect, :sync_connect],
  :open => [:async_connect, :sync_connect],
  :setdb => [:async_connect, :sync_connect],
  :setdblogin => [:async_connect, :sync_connect],
  :ping => [:async_ping, :sync_ping],
}
REDIRECT_SEND_METHODS =

These methods are affected by PQsetnonblocking

{
  :isnonblocking => [:async_isnonblocking, :sync_isnonblocking],
  :nonblocking? => [:async_isnonblocking, :sync_isnonblocking],
  :put_copy_data => [:async_put_copy_data, :sync_put_copy_data],
  :put_copy_end => [:async_put_copy_end, :sync_put_copy_end],
  :flush => [:async_flush, :sync_flush],
}
REDIRECT_METHODS =
{
  :exec => [:async_exec, :sync_exec],
  :query => [:async_exec, :sync_exec],
  :exec_params => [:async_exec_params, :sync_exec_params],
  :prepare => [:async_prepare, :sync_prepare],
  :exec_prepared => [:async_exec_prepared, :sync_exec_prepared],
  :describe_portal => [:async_describe_portal, :sync_describe_portal],
  :describe_prepared => [:async_describe_prepared, :sync_describe_prepared],
  :setnonblocking => [:async_setnonblocking, :sync_setnonblocking],
  :get_result => [:async_get_result, :sync_get_result],
  :get_last_result => [:async_get_last_result, :sync_get_last_result],
  :get_copy_data => [:async_get_copy_data, :sync_get_copy_data],
  :reset => [:async_reset, :sync_reset],
  :set_client_encoding => [:async_set_client_encoding, :sync_set_client_encoding],
  :client_encoding= => [:async_set_client_encoding, :sync_set_client_encoding],
  :cancel => [:async_cancel, :sync_cancel],
}

Class Method Summary collapse

Instance Method Summary collapse

Class Method Details

.async_api=(enable) ⇒ Object

Switch between sync and async libpq API.

PG::Connection.async_api = true

this is the default. It sets an alias from #exec to #async_exec, #reset to #async_reset and so on.

PG::Connection.async_api = false

sets an alias from #exec to #sync_exec, #reset to #sync_reset and so on.

pg-1.1.0+ defaults to libpq’s async API for query related blocking methods. pg-1.3.0+ defaults to libpq’s async API for all possibly blocking methods.

PLEASE NOTE: This method is not part of the public API and is for debug and development use only. Do not use this method in production code. Any issues with the default setting of async_api=true should be reported to the maintainers instead.



864
865
866
867
868
869
870
871
872
873
874
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 864

def async_api=(enable)
  self.async_send_api = enable
  REDIRECT_METHODS.each do |ali, (async, sync)|
    remove_method(ali) if method_defined?(ali)
    alias_method( ali, enable ? async : sync )
  end
  REDIRECT_CLASS_METHODS.each do |ali, (async, sync)|
    singleton_class.remove_method(ali) if method_defined?(ali)
    singleton_class.alias_method(ali, enable ? async : sync )
  end
end

.async_send_api=(enable) ⇒ Object



841
842
843
844
845
846
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 841

def async_send_api=(enable)
  REDIRECT_SEND_METHODS.each do |ali, (async, sync)|
    undef_method(ali) if method_defined?(ali)
    alias_method( ali, enable ? async : sync )
  end
end

.conndefaults_hashObject

Return the Postgres connection defaults structure as a Hash keyed by option keyword (as a Symbol).

See also #conndefaults



282
283
284
285
286
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 282

def self.conndefaults_hash
  return self.conndefaults.each_with_object({}) do |info, hash|
    hash[ info[:keyword].to_sym ] = info[:val]
  end
end

.connect_hash_to_string(hash) ⇒ Object

Convert Hash options to connection String

Values are properly quoted and escaped.



45
46
47
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 45

def self.connect_hash_to_string( hash )
  hash.map { |k,v| "#{k}=#{quote_connstr(v)}" }.join( ' ' )
end

.new(*args) ⇒ Object Also known as: async_connect, connect, open, setdb, setdblogin

call-seq:

PG::Connection.new -> conn
PG::Connection.new(connection_hash) -> conn
PG::Connection.new(connection_string) -> conn
PG::Connection.new(host, port, options, tty, dbname, user, password) ->  conn

Create a connection to the specified server.

connection_hash must be a ruby Hash with connection parameters. See the list of valid parameters in the PostgreSQL documentation.

There are two accepted formats for connection_string: plain keyword = value strings and URIs. See the documentation of connection strings.

The positional parameter form has the same functionality except that the missing parameters will always take on default values. The parameters are:

host

server hostname

port

server port number

options

backend options

tty

(ignored in all versions of PostgreSQL)

dbname

connecting database name

user

login user name

password

login password

Examples:

# Connect using all defaults
PG::Connection.new

# As a Hash
PG::Connection.new( dbname: 'test', port: 5432 )

# As a String
PG::Connection.new( "dbname=test port=5432" )

# As an Array
PG::Connection.new( nil, 5432, nil, nil, 'test', nil, nil )

# As an URI
PG::Connection.new( "postgresql://user:[email protected]:5432/testdb?sslmode=require" )

If the Ruby default internal encoding is set (i.e., Encoding.default_internal != nil), the connection will have its client_encoding set accordingly.

Raises a PG::Error if the connection fails.



694
695
696
697
698
699
700
701
702
703
704
705
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 694

def new(*args)
  conn = connect_to_hosts(*args)

  if block_given?
    begin
      return yield conn
    ensure
      conn.finish
    end
  end
  conn
end

.parse_connect_args(*args) ⇒ Object

Parse the connection args into a connection-parameter string. See PG::Connection.new for valid arguments.

It accepts:

  • an option String kind of “host=name port=5432”

  • an option Hash kind of “name”, port: 5432

  • URI string

  • URI object

  • positional arguments

The method adds the option “fallback_application_name” if it isn’t already set. It returns a connection string with “key=value” pairs.



61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 61

def self.parse_connect_args( *args )
  hash_arg = args.last.is_a?( Hash ) ? args.pop.transform_keys(&:to_sym) : {}
  iopts = {}

  if args.length == 1
    case args.first
    when URI, /=/, /:\/\//
      # Option or URL string style
      conn_string = args.first.to_s
      iopts = PG::Connection.conninfo_parse(conn_string).each_with_object({}){|h, o| o[h[:keyword].to_sym] = h[:val] if h[:val] }
    else
      # Positional parameters (only host given)
      iopts[CONNECT_ARGUMENT_ORDER.first.to_sym] = args.first
    end
  else
    # Positional parameters with host and more
    max = CONNECT_ARGUMENT_ORDER.length
    raise ArgumentError,
        "Extra positional parameter %d: %p" % [ max + 1, args[max] ] if args.length > max

    CONNECT_ARGUMENT_ORDER.zip( args ) do |(k,v)|
      iopts[ k.to_sym ] = v if v
    end
    iopts.delete(:tty) # ignore obsolete tty parameter
  end

  iopts.merge!( hash_arg )

  if !iopts[:fallback_application_name]
    iopts[:fallback_application_name] = $0.sub( /^(.{30}).{4,}(.{30})$/ ){ $1+"..."+$2 }
  end

  return connect_hash_to_string(iopts)
end

.ping(*args) ⇒ Object Also known as: async_ping

call-seq:

PG::Connection.ping(connection_hash)       -> Integer
PG::Connection.ping(connection_string)     -> Integer
PG::Connection.ping(host, port, options, tty, dbname, , password) ->  Integer

Check server status.

See PG::Connection.new for a description of the parameters.

Returns one of:

PQPING_OK

server is accepting connections

PQPING_REJECT

server is alive but rejecting connections

PQPING_NO_RESPONSE

could not establish connection

PQPING_NO_ATTEMPT

connection not attempted (bad params)



789
790
791
792
793
794
795
796
797
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 789

def ping(*args)
  if Fiber.respond_to?(:scheduler) && Fiber.scheduler
    # Run PQping in a second thread to avoid blocking of the scheduler.
    # Unfortunately there's no nonblocking way to run ping.
    Thread.new { sync_ping(*args) }.value
  else
    sync_ping(*args)
  end
end

.quote_connstr(value) ⇒ Object

Quote a single value for use in a connection-parameter string.



38
39
40
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 38

def self.quote_connstr( value )
  return "'" + value.to_s.gsub( /[\\']/ ) {|m| '\\' + m } + "'"
end

Instance Method Details

#cancelObject Also known as: async_cancel

call-seq:

conn.cancel() -> String

Requests cancellation of the command currently being processed.

Returns nil on success, or a string containing the error message if a failure occurs.



518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 518

def cancel
  be_pid = backend_pid
  be_key = backend_key
  cancel_request = [0x10, 1234, 5678, be_pid, be_key].pack("NnnNN")

  if Fiber.respond_to?(:scheduler) && Fiber.scheduler && RUBY_PLATFORM =~ /mingw|mswin/
    # Ruby's nonblocking IO is not really supported on Windows.
    # We work around by using threads and explicit calls to wait_readable/wait_writable.
    cl = Thread.new(socket_io.remote_address) { |ra| ra.connect }.value
    begin
      cl.write_nonblock(cancel_request)
    rescue IO::WaitReadable, Errno::EINTR
      cl.wait_writable
      retry
    end
    begin
      cl.read_nonblock(1)
    rescue IO::WaitReadable, Errno::EINTR
      cl.wait_readable
      retry
    rescue EOFError
    end
  elsif RUBY_ENGINE == 'truffleruby'
    begin
      cl = socket_io.remote_address.connect
    rescue NotImplementedError
      # Workaround for truffleruby < 21.3.0
      cl2 = Socket.for_fd(socket_io.fileno)
      cl2.autoclose = false
      adr = cl2.remote_address
      if adr.ip?
        cl = TCPSocket.new(adr.ip_address, adr.ip_port)
        cl.autoclose = false
      else
        cl = UNIXSocket.new(adr.unix_path)
        cl.autoclose = false
      end
    end
    cl.write(cancel_request)
    cl.read(1)
  else
    cl = socket_io.remote_address.connect
    # Send CANCEL_REQUEST_CODE and parameters
    cl.write(cancel_request)
    # Wait for the postmaster to close the connection, which indicates that it's processed the request.
    cl.read(1)
  end

  cl.close
  nil
rescue SystemCallError => err
  err.to_s
end

#conndefaultsObject

Returns an array of Hashes with connection defaults. See ::conndefaults for details.



274
275
276
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 274

def conndefaults
  return self.class.conndefaults
end

#conndefaults_hashObject

Returns a Hash with connection defaults. See ::conndefaults_hash for details.



290
291
292
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 290

def conndefaults_hash
  return self.class.conndefaults_hash
end

#conninfo_hashObject

Return the Postgres connection info structure as a Hash keyed by option keyword (as a Symbol).

See also #conninfo



298
299
300
301
302
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 298

def conninfo_hash
  return self.conninfo.each_with_object({}) do |info, hash|
    hash[ info[:keyword].to_sym ] = info[:val]
  end
end

#copy_data(sql, coder = nil) ⇒ Object

call-seq:

conn.copy_data( sql [, coder] ) {|sql_result| ... } -> PG::Result

Execute a copy process for transferring data to or from the server.

This issues the SQL COPY command via #exec. The response to this (if there is no error in the command) is a PG::Result object that is passed to the block, bearing a status code of PGRES_COPY_OUT or PGRES_COPY_IN (depending on the specified copy direction). The application should then use #put_copy_data or #get_copy_data to receive or transmit data rows and should return from the block when finished.

#copy_data returns another PG::Result object when the data transfer is complete. An exception is raised if some problem was encountered, so it isn’t required to make use of any of them. At this point further SQL commands can be issued via #exec. (It is not possible to execute other SQL commands using the same connection while the COPY operation is in progress.)

This method ensures, that the copy process is properly terminated in case of client side or server side failures. Therefore, in case of blocking mode of operation, #copy_data is preferred to raw calls of #put_copy_data, #get_copy_data and #put_copy_end.

coder can be a PG::Coder derivation (typically PG::TextEncoder::CopyRow or PG::TextDecoder::CopyRow). This enables encoding of data fields given to #put_copy_data or decoding of fields received by #get_copy_data.

Example with CSV input format:

conn.exec "create table my_table (a text,b text,c text,d text)"
conn.copy_data "COPY my_table FROM STDIN CSV" do
  conn.put_copy_data "some,data,to,copy\n"
  conn.put_copy_data "more,data,to,copy\n"
end

This creates my_table and inserts two CSV rows.

The same with text format encoder PG::TextEncoder::CopyRow and Array input:

enco = PG::TextEncoder::CopyRow.new
conn.copy_data "COPY my_table FROM STDIN", enco do
  conn.put_copy_data ['some', 'data', 'to', 'copy']
  conn.put_copy_data ['more', 'data', 'to', 'copy']
end

Example with CSV output format:

conn.copy_data "COPY my_table TO STDOUT CSV" do
  while row=conn.get_copy_data
    p row
  end
end

This prints all rows of my_table to stdout:

"some,data,to,copy\n"
"more,data,to,copy\n"

The same with text format decoder PG::TextDecoder::CopyRow and Array output:

deco = PG::TextDecoder::CopyRow.new
conn.copy_data "COPY my_table TO STDOUT", deco do
  while row=conn.get_copy_data
    p row
  end
end

This receives all rows of my_table as ruby array:

["some", "data", "to", "copy"]
["more", "data", "to", "copy"]


185
186
187
188
189
190
191
192
193
194
195
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
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 185

def copy_data( sql, coder=nil )
  raise PG::NotInBlockingMode.new("copy_data can not be used in nonblocking mode", connection: self) if nonblocking?
  res = exec( sql )

  case res.result_status
  when PGRES_COPY_IN
    begin
      if coder
        old_coder = self.encoder_for_put_copy_data
        self.encoder_for_put_copy_data = coder
      end
      yield res
    rescue Exception => err
      errmsg = "%s while copy data: %s" % [ err.class.name, err.message ]
      put_copy_end( errmsg )
      get_result
      raise
    else
      put_copy_end
      get_last_result
    ensure
      self.encoder_for_put_copy_data = old_coder if coder
    end

  when PGRES_COPY_OUT
    begin
      if coder
        old_coder = self.decoder_for_get_copy_data
        self.decoder_for_get_copy_data = coder
      end
      yield res
    rescue Exception => err
      cancel
      begin
        while get_copy_data
        end
      rescue PG::Error
        # Ignore error in cleanup to avoid losing original exception
      end
      while get_result
      end
      raise err
    else
      res = get_last_result
      if !res || res.result_status != PGRES_COMMAND_OK
        while get_copy_data
        end
        while get_result
        end
        raise PG::NotAllCopyDataRetrieved.new("Not all COPY data retrieved", connection: self)
      end
      res
    ensure
      self.decoder_for_get_copy_data = old_coder if coder
    end

  else
    raise ArgumentError, "SQL command is no COPY statement: #{sql}"
  end
end

#encrypt_password(password, username, algorithm = nil) ⇒ Object Also known as: async_encrypt_password

call-seq:

conn.encrypt_password( password, username, algorithm=nil ) -> String

This function is intended to be used by client applications that wish to send commands like ALTER USER joe PASSWORD 'pwd'. It is good practice not to send the original cleartext password in such a command, because it might be exposed in command logs, activity displays, and so on. Instead, use this function to convert the password to encrypted form before it is sent.

The password and username arguments are the cleartext password, and the SQL name of the user it is for. algorithm specifies the encryption algorithm to use to encrypt the password. Currently supported algorithms are md5 and scram-sha-256 (on and off are also accepted as aliases for md5, for compatibility with older server versions). Note that support for scram-sha-256 was introduced in PostgreSQL version 10, and will not work correctly with older server versions. If algorithm is omitted or nil, this function will query the server for the current value of the password_encryption setting. That can block, and will fail if the current transaction is aborted, or if the connection is busy executing another query. If you wish to use the default algorithm for the server but want to avoid blocking, query password_encryption yourself before calling #encrypt_password, and pass that value as the algorithm.

Return value is the encrypted password. The caller can assume the string doesn’t contain any special characters that would require escaping.

Available since PostgreSQL-10. See also corresponding libpq function.



491
492
493
494
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 491

def encrypt_password( password, username, algorithm=nil )
  algorithm ||= exec("SHOW password_encryption").getvalue(0,0)
  sync_encrypt_password(password, username, algorithm)
end

#get_copy_data(async = false, decoder = nil) ⇒ Object Also known as: async_get_copy_data

call-seq:

conn.get_copy_data( [ nonblock = false [, decoder = nil ]] ) -> Object

Return one row of data, nil if the copy is done, or false if the call would block (only possible if nonblock is true).

If decoder is not set or nil, data is returned as binary string.

If decoder is set to a PG::Coder derivation, the return type depends on this decoder. PG::TextDecoder::CopyRow decodes the received data fields from one row of PostgreSQL’s COPY text format to an Array of Strings. Optionally the decoder can type cast the single fields to various Ruby types in one step, if PG::TextDecoder::CopyRow#type_map is set accordingly.

See also #copy_data.



359
360
361
362
363
364
365
366
367
368
369
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 359

def get_copy_data(async=false, decoder=nil)
  if async
    return sync_get_copy_data(async, decoder)
  else
    while (res=sync_get_copy_data(true, decoder)) == false
      socket_io.wait_readable
      consume_input
    end
    return res
  end
end

#get_resultObject Also known as: async_get_result

call-seq:

conn.get_result() -> PG::Result
conn.get_result() {|pg_result| block }

Blocks waiting for the next result from a call to #send_query (or another asynchronous command), and returns it. Returns nil if no more results are available.

Note: call this function repeatedly until it returns nil, or else you will not be able to issue further commands.

If the optional code block is given, it will be passed result as an argument, and the PG::Result object will automatically be cleared when the block terminates. In this instance, conn.exec returns the value of the block.



336
337
338
339
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 336

def get_result
  block
  sync_get_result
end

#inspectObject

Return a String representation of the object suitable for debugging.



97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 97

def inspect
  str = self.to_s
  str[-1,0] = if finished?
    " finished"
  else
    stats = []
    stats << " status=#{ PG.constants.grep(/CONNECTION_/).find{|c| PG.const_get(c) == status} }" if status != CONNECTION_OK
    stats << " transaction_status=#{ PG.constants.grep(/PQTRANS_/).find{|c| PG.const_get(c) == transaction_status} }" if transaction_status != PG::PQTRANS_IDLE
    stats << " nonblocking=#{ isnonblocking }" if isnonblocking
    stats << " pipeline_status=#{ PG.constants.grep(/PQ_PIPELINE_/).find{|c| PG.const_get(c) == pipeline_status} }" if respond_to?(:pipeline_status) && pipeline_status != PG::PQ_PIPELINE_OFF
    stats << " client_encoding=#{ get_client_encoding }" if get_client_encoding != "UTF8"
    stats << " type_map_for_results=#{ type_map_for_results.to_s }" unless type_map_for_results.is_a?(PG::TypeMapAllStrings)
    stats << " type_map_for_queries=#{ type_map_for_queries.to_s }" unless type_map_for_queries.is_a?(PG::TypeMapAllStrings)
    stats << " encoder_for_put_copy_data=#{ encoder_for_put_copy_data.to_s }" if encoder_for_put_copy_data
    stats << " decoder_for_get_copy_data=#{ decoder_for_get_copy_data.to_s }" if decoder_for_get_copy_data
    " host=#{host} port=#{port} user=#{user}#{stats.join}"
  end
  return str
end

#isnonblockingObject Also known as: async_isnonblocking, nonblocking?

call-seq:

conn.isnonblocking() -> Boolean

Returns the blocking status of the database connection. Returns true if the connection is set to nonblocking mode and false if blocking.



407
408
409
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 407

def isnonblocking
  false
end

#put_copy_data(buffer, encoder = nil) ⇒ Object Also known as: async_put_copy_data

call-seq:

conn.put_copy_data( buffer [, encoder] ) -> Boolean

Transmits buffer as copy data to the server. Returns true if the data was sent, false if it was not sent (false is only possible if the connection is in nonblocking mode, and this command would block).

encoder can be a PG::Coder derivation (typically PG::TextEncoder::CopyRow). This encodes the data fields given as buffer from an Array of Strings to PostgreSQL’s COPY text format inclusive proper escaping. Optionally the encoder can type cast the fields from various Ruby types in one step, if PG::TextEncoder::CopyRow#type_map is set accordingly.

Raises an exception if an error occurs.

See also #copy_data.



431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 431

def put_copy_data(buffer, encoder=nil)
  # sync_put_copy_data does a non-blocking attept to flush data.
  until res=sync_put_copy_data(buffer, encoder)
    # It didn't flush immediately and allocation of more buffering memory failed.
    # Wait for all data sent by doing a blocking flush.
    res = flush
  end

  # And do a blocking flush every 100 calls.
  # This is to avoid memory bloat, when sending the data is slower than calls to put_copy_data happen.
  if (@calls_to_put_copy_data += 1) > 100
    @calls_to_put_copy_data = 0
    res = flush
  end
  res
end

#put_copy_end(*args) ⇒ Object Also known as: async_put_copy_end

call-seq:

conn.put_copy_end( [ error_message ] ) -> Boolean

Sends end-of-data indication to the server.

error_message is an optional parameter, and if set, forces the COPY command to fail with the string error_message.

Returns true if the end-of-data was sent, #false* if it was not sent (false is only possible if the connection is in nonblocking mode, and this command would block).



461
462
463
464
465
466
467
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 461

def put_copy_end(*args)
  until sync_put_copy_end(*args)
    flush
  end
  @calls_to_put_copy_data = 0
  flush
end

#resetObject Also known as: async_reset

call-seq:

conn.reset()

Resets the backend connection. This method closes the backend connection and tries to re-connect.



503
504
505
506
507
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 503

def reset
  reset_start
  async_connect_or_reset(:reset_poll)
  self
end

#setnonblocking(enabled) ⇒ Object Also known as: async_setnonblocking

call-seq:

conn.setnonblocking(Boolean) -> nil

Sets the nonblocking status of the connection. In the blocking state, calls to #send_query will block until the message is sent to the server, but will not wait for the query results. In the nonblocking state, calls to #send_query will return an error if the socket is not ready for writing. Note: This function does not affect #exec, because that function doesn’t return until the server has processed the query and returned the results.

Returns nil.



393
394
395
396
397
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 393

def setnonblocking(enabled)
  singleton_class.async_send_api = !enabled
  self.flush_data = !enabled
  sync_setnonblocking(true)
end

#ssl_attributesObject

call-seq:

conn.ssl_attributes -> Hash<String,String>

Returns SSL-related information about the connection as key/value pairs

The available attributes varies depending on the SSL library being used, and the type of connection.

See also #ssl_attribute



315
316
317
318
319
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 315

def ssl_attributes
  ssl_attribute_names.each.with_object({}) do |n,h|
    h[n] = ssl_attribute(n)
  end
end

#transactionObject

call-seq:

conn.transaction { |conn| ... } -> result of the block

Executes a BEGIN at the start of the block, and a COMMIT at the end of the block, or ROLLBACK if any exception occurs.



258
259
260
261
262
263
264
265
266
267
268
269
270
# File 'lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/pg-1.4.5/lib/pg/connection.rb', line 258

def transaction
  rollback = false
  exec "BEGIN"
  yield(self)
rescue Exception
  rollback = true
  cancel if transaction_status == PG::PQTRANS_ACTIVE
  block
  exec "ROLLBACK"
  raise
ensure
  exec "COMMIT" unless rollback
end