Class: PgCanary::Rules::RegexWithoutTrgm
- Includes:
- IndexPredicates
- Defined in:
- lib/pg_canary/rules/definitions/regex_without_trgm.rb
Overview
Regular-expression search (~, ~*, SIMILAR TO) cannot use a plain btree index; only a pg_trgm GIN/GiST index can serve it. The regex variant of leading_wildcard_like.
Constant Summary collapse
- REGEX_OPS =
%w[~ ~* !~ !~*].freeze
Constants included from IndexPredicates
IndexPredicates::TRGM_ACCESS_METHODS
Constants included from PgQuerySupport
PgQuerySupport::COMPARISON_OPS
Instance Method Summary collapse
Methods inherited from Base
all, #enabled?, options, rule_name
Instance Method Details
#check(query) ⇒ Object
17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 |
# File 'lib/pg_canary/rules/definitions/regex_without_trgm.rb', line 17 def check(query) detections = [] query.each_scope do |scope| next unless scope.where_clause walk_within_scope(scope.where_clause) do |node| next unless node.is_a?(PgQuery::A_Expr) operator = display_operator(node) next unless operator column_ref = strip_type_casts(node.lexpr) next unless column_ref.is_a?(PgQuery::ColumnRef) table, column = scope.resolve(column_ref) next unless table && column next unless applicable_table?(query, table) next if trgm_index?(query, table, column) detections << detection( query, table: table, columns: column, message: "Regular-expression search (#{operator}) on #{table}.#{column} cannot use " \ "a btree index and will scan every row in production.", suggestion: <<~SUGGESTION.chomp Consider the pg_trgm extension with a GIN index: CREATE EXTENSION IF NOT EXISTS pg_trgm; CREATE INDEX index_#{table}_on_#{column}_trgm ON #{table} USING gin (#{column} gin_trgm_ops); SUGGESTION ) end end detections end |
#default_enabled ⇒ Object
11 12 13 |
# File 'lib/pg_canary/rules/definitions/regex_without_trgm.rb', line 11 def default_enabled true end |