lib/pghero/methods/explain.rb in pghero-3.0.1 vs lib/pghero/methods/explain.rb in pghero-3.1.0

- old
+ new

@@ -1,8 +1,10 @@ module PgHero module Methods module Explain + # TODO remove in 4.0 + # note: this method is not affected by the explain option def explain(sql) sql = squish(sql) explanation = nil # use transaction for safety @@ -14,16 +16,48 @@ end explanation end + # TODO rename to explain in 4.0 + # note: this method is not affected by the explain option + def explain_v2(sql, analyze: nil, verbose: nil, costs: nil, settings: nil, buffers: nil, wal: nil, timing: nil, summary: nil, format: "text") + options = [] + add_explain_option(options, "ANALYZE", analyze) + add_explain_option(options, "VERBOSE", verbose) + add_explain_option(options, "SETTINGS", settings) + add_explain_option(options, "COSTS", costs) + add_explain_option(options, "BUFFERS", buffers) + add_explain_option(options, "WAL", wal) + add_explain_option(options, "TIMING", timing) + add_explain_option(options, "SUMMARY", summary) + options << "FORMAT #{explain_format(format)}" + + explain("(#{options.join(", ")}) #{sql}") + end + private def explain_safe? select_all("SELECT 1; SELECT 1") false rescue ActiveRecord::StatementInvalid true + end + + def add_explain_option(options, name, value) + unless value.nil? + options << "#{name}#{value ? "" : " FALSE"}" + end + end + + # important! validate format to prevent injection + def explain_format(format) + if ["text", "xml", "json", "yaml"].include?(format) + format.upcase + else + raise ArgumentError, "Unknown format" + end end end end end