mirror of
https://github.com/postgresml/pgcat.git
synced 2026-03-23 09:26:30 +00:00
* Ruby integration tests * forgot a file * refactor * refactoring * more refactoring * remove config helper * try multiple databases * fix * more databases * Use pg stats * ports * speed * Fix tests * preload library * comment
83 lines
2.1 KiB
Ruby
83 lines
2.1 KiB
Ruby
require 'pg'
|
|
require 'toxiproxy'
|
|
|
|
class PgInstance
|
|
attr_reader :port
|
|
attr_reader :username
|
|
attr_reader :password
|
|
attr_reader :database_name
|
|
|
|
def initialize(port, username, password, database_name)
|
|
@original_port = port
|
|
@toxiproxy_port = 10000 + port.to_i
|
|
@port = @toxiproxy_port
|
|
|
|
@username = username
|
|
@password = password
|
|
@database_name = database_name
|
|
@toxiproxy_name = "database_#{@original_port}"
|
|
Toxiproxy.populate([{
|
|
name: @toxiproxy_name,
|
|
listen: "0.0.0.0:#{@toxiproxy_port}",
|
|
upstream: "localhost:#{@original_port}",
|
|
}])
|
|
|
|
# Toxiproxy server will outlive our PgInstance objects
|
|
# so we want to destroy our proxies before exiting
|
|
# Ruby finalizer is ideal for doing this
|
|
ObjectSpace.define_finalizer(@toxiproxy_name, proc { Toxiproxy[@toxiproxy_name].destroy })
|
|
end
|
|
|
|
def with_connection
|
|
conn = PG.connect("postgres://#{@username}:#{@password}@localhost:#{port}/#{database_name}")
|
|
yield conn
|
|
ensure
|
|
conn&.close
|
|
end
|
|
|
|
def reset
|
|
reset_toxics
|
|
reset_stats
|
|
end
|
|
|
|
def toxiproxy
|
|
Toxiproxy[@toxiproxy_name]
|
|
end
|
|
|
|
def take_down
|
|
if block_given?
|
|
Toxiproxy[@toxiproxy_name].toxic(:limit_data, bytes: 5).apply { yield }
|
|
else
|
|
Toxiproxy[@toxiproxy_name].toxic(:limit_data, bytes: 5).toxics.each(&:save)
|
|
end
|
|
end
|
|
|
|
def add_latency(latency)
|
|
if block_given?
|
|
Toxiproxy[@toxiproxy_name].toxic(:latency, latency: latency).apply { yield }
|
|
else
|
|
Toxiproxy[@toxiproxy_name].toxic(:latency, latency: latency).toxics.each(&:save)
|
|
end
|
|
end
|
|
|
|
def delete_proxy
|
|
Toxiproxy[@toxiproxy_name].delete
|
|
end
|
|
|
|
def reset_toxics
|
|
Toxiproxy[@toxiproxy_name].toxics.each(&:destroy)
|
|
end
|
|
|
|
def reset_stats
|
|
with_connection { |c| c.async_exec("SELECT pg_stat_statements_reset()") }
|
|
end
|
|
|
|
def count_query(query)
|
|
with_connection { |c| c.async_exec("SELECT SUM(calls) FROM pg_stat_statements WHERE query = '#{query}'")[0]["sum"].to_i }
|
|
end
|
|
|
|
def count_select_1_plus_2
|
|
with_connection { |c| c.async_exec("SELECT SUM(calls) FROM pg_stat_statements WHERE query = 'SELECT $1 + $2'")[0]["sum"].to_i }
|
|
end
|
|
end
|