Module: AbAdmin::Models::Locator::ClassMethods

Defined in:
lib/ab_admin/models/locator.rb

Constant Summary collapse

INTERPOLATION_REGEXP =
/%{[^}]+}/

Instance Method Summary collapse

Instance Method Details

#csv_errors(csv) ⇒ Object



68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
# File 'lib/ab_admin/models/locator.rb', line 68

def csv_errors(csv)
  return ['CSV blank'] if csv.blank?
  csv_data = CSV.parse(csv)
  errors = []
  csv_data.shift.each_with_index do |l, i|
    next if i.zero?
    unless I18n.available_locales.include?(l.to_sym)
      errors << "Unknown locale #{l}"
      next
    end
    csv_data.each do |d|
      key = d[0]
      next if d[i].blank?
      if translations.dig(I18n.default_locale, key)
        unless translations.dig(I18n.default_locale, key).scan(INTERPOLATION_REGEXP).sort == d[i].scan(INTERPOLATION_REGEXP).sort
          errors << "Wrong interpolations #{I18n.default_locale}:'#{translations.dig(I18n.default_locale, key)}' #{l}:#{d[i]}"
        end
      else
        errors << "Extra interpolations #{l}:#{d[i]}" if d[i].scan(INTERPOLATION_REGEXP).present?
      end
    end
  end
  errors
end

#export_csv(*keys, locales: nil, files: nil) ⇒ Object



33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
# File 'lib/ab_admin/models/locator.rb', line 33

def export_csv(*keys, locales: nil, files: nil)
  return if keys.blank?
  sources = files.present? ? translations_for_files(files) : translations
  locales = locales.present? ? (I18n.available_locales & locales.map(&:to_sym)) : (sources.keys || I18n.available_locales)
  I18n.backend.available_locales # Force load translations
  filter_keys = keys.map {|k| k.include?('*') ? Regexp.new("\\A#{k.gsub('.', '\.').gsub('*', '.*')}\\z") : k}
  data = filter_keys.each_with_object(Hash.new { |h, k| h[k] = [] }) do |key, res|
    locales.each_with_index do |l, i|
      next unless sources[l]
      sources[l].find_all{|k, _| key.is_a?(Regexp) ? k =~ key : k == key }.each{|k, v| res[k][i] = v}
    end
  end
  for_csv = [['DO NOT EDIT THIS COLUMN!', *locales]] + data.map{|k, v| [k, *v] }
  for_csv.map(&:to_csv).join
end

#find_filesObject



17
18
19
# File 'lib/ab_admin/models/locator.rb', line 17

def find_files
  Dir[Rails.root.join('config', 'locales', '*.yml')]
end

#import_csv(csv, locales: nil) ⇒ Object



49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
# File 'lib/ab_admin/models/locator.rb', line 49

def import_csv(csv, locales: nil)
  return if csv.blank?
  locales = locales.present? ? (I18n.available_locales & locales.map(&:to_sym)) : I18n.available_locales
  csv_data = CSV.parse(csv)
  csv_data.shift.each_with_index do |l, i|
    next if i.zero? || !locales.include?(l.to_sym)
    path = Rails.root.join('config', 'locales', "#{l}.yml")
    raise "Missing file #{path}" unless File.file?(path)
    data = YAML.load_file(path)
    csv_data.each do |d|
      key_parts = [l.to_s] + d[0].split('.')
      raise "Invalid key #{d[0]}" unless data.dig(*key_parts)
      data.dig_store(d[i], *key_parts)
    end
    save path, data
  end
end

#prepare_data(path) ⇒ Object



26
27
28
29
30
31
# File 'lib/ab_admin/models/locator.rb', line 26

def prepare_data(path)
  data = YAML.load_file(path)
  locale = data.keys.first
  OpenStruct.new({locale: locale.to_sym, data: data[locale], flat_data: data[locale].flatten_hash,
                  filename: File.basename(path), path: path, dir: File.dirname(path)})
end

#save(path, data) ⇒ Object



21
22
23
24
# File 'lib/ab_admin/models/locator.rb', line 21

def save(path, data)
  data.deep_transform_values! { |v| AbAdmin.normalize_html(v) }
  File.write path, data.deep_stringify_keys.to_yaml(line_width: YAML_LINE_WIDTH).sub(/\A---\s+/, '').gsub(/:\s+$/, ':').gsub(/^(\s+)(yes|no):/, '\1"\2":')
end

#translationsObject



93
94
95
# File 'lib/ab_admin/models/locator.rb', line 93

def translations
  @translations ||= I18n.backend.send(:translations).slice(*I18n.available_locales).transform_values{|v| v.flatten_hash.transform_keys{|k| k.join('.') } }
end

#translations_for_files(files) ⇒ Object



97
98
99
100
101
102
103
104
105
# File 'lib/ab_admin/models/locator.rb', line 97

def translations_for_files(files)
  data = {}
  files.each do |file|
    path = Rails.root.join('config', 'locales', file)
    puts path
    data.deep_merge!(YAML.load_file(path))
  end
  data.symbolize_keys.slice(*I18n.available_locales).transform_values{|v| v.flatten_hash.transform_keys{|k| k.join('.') } }
end