Module: ActiveVersion::Audits::HasAudits::DatabaseAdapterHelper::ClassMethods

Defined in:
lib/active_version/audits/has_audits/database_adapter_helper.rb

Instance Method Summary collapse

Instance Method Details

#filter_empty_json_condition(relation, column_name, model_class = nil) ⇒ Object

Get adapter-agnostic condition to filter out empty JSON objects Uses ActiveRecord’s abstractions (where.not) which handle adapter differences



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
# File 'lib/active_version/audits/has_audits/database_adapter_helper.rb', line 22

def filter_empty_json_condition(relation, column_name, model_class = nil)
  model_class ||= relation.klass
  column = model_class.columns_hash[column_name.to_s]

  # Check column type to determine best approach
  if column
    column_type = column.type.to_s.downcase

    case column_type
    when "jsonb", "json"
      # For JSON/JSONB columns, use string comparison
      # ActiveRecord's where.not handles adapter-specific SQL generation
      relation.where.not(column_name => "{}")
    else
      # For TEXT columns, use Arel function for length check
      # ActiveRecord adapters will translate this appropriately
      table = model_class.arel_table
      column_arel = table[column_name.to_sym]
      length_func = Arel::Nodes::NamedFunction.new("LENGTH", [column_arel])
      relation.where(length_func.gt(2))
    end
  else
    # Fallback: use length check via Arel
    table = model_class.arel_table
    column_arel = table[column_name.to_sym]
    length_func = Arel::Nodes::NamedFunction.new("LENGTH", [column_arel])
    relation.where(length_func.gt(2))
  end
end

#json_column?(model_class, column_name) ⇒ Boolean

Check if a column is a JSON/JSONB type (not text)

Returns:

  • (Boolean)


11
12
13
14
15
16
17
18
# File 'lib/active_version/audits/has_audits/database_adapter_helper.rb', line 11

def json_column?(model_class, column_name)
  column = model_class.columns_hash[column_name.to_s]
  return false unless column

  # Check column type
  type = column.type.to_s.downcase
  type == "json" || type == "jsonb"
end

#not_empty_json_condition(column_name, model_class = ActiveRecord::Base) ⇒ Object

Get adapter-agnostic condition for checking if JSON is NOT empty Returns an Arel node that can be used in where clauses



54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
# File 'lib/active_version/audits/has_audits/database_adapter_helper.rb', line 54

def not_empty_json_condition(column_name, model_class = ActiveRecord::Base)
  column = model_class.columns_hash[column_name.to_s]
  table = model_class.arel_table
  column_arel = table[column_name.to_sym]

  if column
    column_type = column.type.to_s.downcase

    case column_type
    when "jsonb", "json"
      # For JSON/JSONB: use Arel's not_eq - ActiveRecord adapters handle this
      column_arel.not_eq("{}")
    else
      # For TEXT: use Arel function for length (adapter-agnostic)
      length_func = Arel::Nodes::NamedFunction.new("LENGTH", [column_arel])
      length_func.gt(2)
    end
  else
    # Fallback: use length check via Arel
    length_func = Arel::Nodes::NamedFunction.new("LENGTH", [column_arel])
    length_func.gt(2)
  end
end