Module: I18n::Tasks::Command::Commands::CheckPrism

Includes:
I18n::Tasks::Command::Collection
Included in:
I18n::Tasks::Commands
Defined in:
lib/i18n/tasks/command/commands/check_prism.rb

Instance Method Summary collapse

Methods included from I18n::Tasks::Command::Collection

included

Instance Method Details

#check_prism(opt = {}) ⇒ Object

Run both the default (Parser-based) and the Prism-enabled scanning and produce a plain-text report in tmp/i18n_tasks_check_prism.md suitable for pasting into an issue.



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
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
# File 'lib/i18n/tasks/command/commands/check_prism.rb', line 20

def check_prism(opt = {})
  now = Time.now
  report_path = File.join(Dir.pwd, "tmp", "i18n_tasks_check_prism.md")
  FileUtils.mkdir_p(File.dirname(report_path))

  # keep original search config and clear caches helper
  orig_search = (i18n.config[:search] || {}).dup

  results = {}

  # determine prism mode: use provided opt or default to rails when Rails present
  chosen_prism_mode = (opt[:prism_mode].presence || (rails_available? ? "rails" : "ruby")).to_s
  unless %w[rails ruby].include?(chosen_prism_mode)
    fail CommandError, "--prism-mode must be 'rails' or 'ruby'"
  end

  {default: nil, prism: chosen_prism_mode}.each do |label, prism_mode|
    i18n.config[:search] = orig_search.merge(prism: prism_mode)
    # clear caches used by UsedKeys
    i18n.instance_variable_set(:@scanner, nil)
    i18n.instance_variable_set(:@search_config, nil)
    i18n.instance_variable_set(:@keys_used_in_source_tree, nil)

    tree = i18n.used_in_source_tree
    keys = tree.nodes.select { |n| n.data[:occurrences].present? }
    results[label] = keys.each_with_object({}) do |node, h|
      full_key = node.full_key(root: false)
      h[full_key] = node.data[:occurrences]
    end
  end

  # restore original config and caches
  i18n.config[:search] = orig_search
  i18n.instance_variable_set(:@scanner, nil)
  i18n.instance_variable_set(:@search_config, nil)
  i18n.instance_variable_set(:@keys_used_in_source_tree, nil)

  default_keys = results[:default].keys
  prism_keys = results[:prism].keys

  only_default = (default_keys - prism_keys).sort
  only_prism = (prism_keys - default_keys).sort
  both = (default_keys & prism_keys).sort

  File.open(report_path, "w") do |f|
    f.puts "# i18n-tasks check_prism report"
    f.puts "Generated at: #{now.utc}"
    f.puts "Prism mode: #{chosen_prism_mode}"
    f.puts "Gem version: #{I18n::Tasks::VERSION}"
    f.puts ""
    f.puts "Summary"
    f.puts "- total keys (default parser): #{default_keys.size}"
    f.puts "- total keys (prism): #{prism_keys.size}"
    f.puts "- keys in both: #{both.size}"
    f.puts "- keys only in default parser: #{only_default.size}"
    f.puts "- keys only in prism: #{only_prism.size}"
    f.puts ""

    unless only_default.empty?
      f.puts "## Keys found by the default parser but NOT by Prism (#{only_default.size})"
      only_default.each do |k|
        f.puts "\n### #{k}"
        results[:default][k].first(5).each do |occ|
          src = (occ.raw_key || k).to_s
          line = (occ.line || "").strip
          highlighted = line.gsub(src) { |m| "`#{m}`" }
          f.puts "- #{occ.path}:#{occ.line_num} `#{src}` — #{highlighted}"
        end
      end
    end

    unless only_prism.empty?
      f.puts "## Keys found by Prism but NOT by the default parser (#{only_prism.size})"
      only_prism.each do |k|
        f.puts "\n### #{k}"
        results[:prism][k].each do |occ|
          src = (occ.raw_key || k).to_s
          line = (occ.line || "").strip
          highlighted = line.gsub(src) { |m| "`#{m}`" }
          f.puts "- #{occ.path}:#{occ.line_num} `#{src}` — #{highlighted}"
        end
      end
    end

    f.puts "\n## Notes"
    f.puts "- This report compares keys discovered by the project default parser and by Prism (rails mode)."
  end

  log_stderr "Wrote check_prism report: #{report_path}"
  puts File.read(report_path)
end