app/periscope/periscope_controller.rb in periscope_rails-0.0.9 vs app/periscope/periscope_controller.rb in periscope_rails-0.0.10
- old
+ new
@@ -2,28 +2,38 @@
before_filter :authenticate
protect_from_forgery :except => [:look, :login]
def look
if !params[:sql].nil?
- render :json => run_sql(params[:sql])
+ render :json => merge_on_metadata(run_sql(params[:sql]))
else
- render :json => {:error => "Command not understood"}
+ render :json => merge_on_metadata({:error => "Command not understood"})
end
end
def login
- render :json => get_info()
+ render :json => merge_on_metadata(get_info())
end
private
def authenticate
unless PeriscopeRails::Config.check_password(params[:password].to_s)
- render :json => {:error => "Password invalid."}
+ render :json => merge_on_metadata({:error => "Password invalid."})
end
end
+ def merge_on_metadata(hash)
+ version = nil
+ begin
+ version = Gem.loaded_specs["periscope_rails"].version.version
+ rescue
+ version = "error"
+ end
+ return hash.merge({ :version => version, :database_type => get_db_type })
+ end
+
def run_sql(sql_command)
#TODO: protect based on CFG, not blacklist
bad_words = %W{drop delete update into insert index add remove grant revoke create createdb}
bad_words += %W{createuser createrole destroy disconnect exec execute dropdb primary key rollback ; --}
@@ -37,17 +47,12 @@
error_message = "Potentially harmful keyword found, blocking script."
else
begin #for whole query
active_record = PeriscopeRails::Config.get_active_record()
begin #just for costing
- begin
- is_postgres = ActiveRecord::Base.connection.instance_of? ActiveRecord::ConnectionAdapters::PostgreSQLAdapter
- rescue Exception => e
- is_postgres = false
- end
active_record.transaction do #costing
- if PeriscopeRails::Config.block_expensive_queries? and is_postgres
+ if PeriscopeRails::Config.block_expensive_queries? and get_db_type == "postgres"
active_record.connection.select_all("explain #{command}")[0]["QUERY PLAN"] =~ /rows=(\d+) width=(\d+)\)$/
row_count, width = $1.to_i, $2.to_i
if row_count > 0 and width > 0
raise "Command blocked, it may be too slow. Estimated at #{row_count} rows, commands must return fewer than #{PeriscopeRails::Config.max_rows} rows." if row_count > PeriscopeRails::Config.max_rows
raise "Command blocked, it may be too slow. Estimated at #{row_count * width} bytes, commands use less than #{PeriscopeRails::Config.max_size} bytes." if row_count * width > PeriscopeRails::Config.max_size
@@ -84,7 +89,23 @@
table_names = ActiveRecord::Base.connection.tables.sort
table_names.each do |table_name|
tables << {:name => table_name, :columns => ActiveRecord::Base.connection.columns(table_name)}
end
return {:tables => tables, :error => nil}
+ end
+
+ def get_db_type
+ begin
+ return "postgres" if ActiveRecord::Base.connection.instance_of? ActiveRecord::ConnectionAdapters::PostgreSQLAdapter
+ rescue Exception => e
+ begin
+ return "mysql" if ActiveRecord::Base.connection.instance_of? ActiveRecord::ConnectionAdapters::MysqlAdapter
+ rescue Exception => e
+ begin
+ return "mysql" if ActiveRecord::Base.connection.instance_of? ActiveRecord::ConnectionAdapters::Mysql2Adapter
+ rescue
+ return nil
+ end
+ end
+ end
end
end