rails_translation_manager 0.0.2 → 1.1.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +5 -5
- data/.gitignore +1 -1
- data/.ruby-version +1 -1
- data/CHANGELOG.md +20 -0
- data/Jenkinsfile +9 -0
- data/README.md +1 -1
- data/Rakefile +12 -13
- data/config/locales/plurals.rb +49 -0
- data/lib/rails_translation_manager/cleaner.rb +14 -0
- data/lib/rails_translation_manager/i18n_tasks_option_parser.rb +10 -0
- data/lib/rails_translation_manager/importer.rb +32 -14
- data/lib/rails_translation_manager/locale_checker/all_locales.rb +61 -0
- data/lib/rails_translation_manager/locale_checker/base_checker.rb +13 -0
- data/lib/rails_translation_manager/locale_checker/incompatible_plurals.rb +79 -0
- data/lib/rails_translation_manager/locale_checker/locale_checker_helper.rb +23 -0
- data/lib/rails_translation_manager/locale_checker/missing_english_locales.rb +31 -0
- data/lib/rails_translation_manager/locale_checker/missing_foreign_locales.rb +31 -0
- data/lib/rails_translation_manager/locale_checker/plural_forms.rb +16 -0
- data/lib/rails_translation_manager/locale_checker.rb +50 -0
- data/lib/rails_translation_manager/version.rb +1 -1
- data/lib/rails_translation_manager.rb +21 -3
- data/lib/tasks/translation.rake +43 -43
- data/rails_translation_manager.gemspec +4 -2
- data/spec/locales/cleaner/clean.yml +5 -0
- data/spec/locales/cleaner/with_whitespace.yml +5 -0
- data/spec/locales/importer/fr.csv +8 -0
- data/spec/locales/in_sync/cy/browse.yml +12 -0
- data/spec/locales/in_sync/en/browse.yml +8 -0
- data/spec/locales/out_of_sync/cy.yml +3 -0
- data/spec/locales/out_of_sync/en.yml +6 -0
- data/spec/rails_translation_manager/cleaner_spec.rb +13 -0
- data/spec/rails_translation_manager/importer_spec.rb +81 -0
- data/spec/rails_translation_manager/locale_checker/all_locales_spec.rb +24 -0
- data/spec/rails_translation_manager/locale_checker/incompatible_plurals_spec.rb +94 -0
- data/spec/rails_translation_manager/locale_checker/locale_checker_helper_spec.rb +61 -0
- data/spec/rails_translation_manager/locale_checker/missing_english_locales_spec.rb +72 -0
- data/spec/rails_translation_manager/locale_checker/missing_foreign_locales_spec.rb +80 -0
- data/spec/rails_translation_manager/locale_checker/plural_forms_spec.rb +27 -0
- data/spec/rails_translation_manager/locale_checker_spec.rb +68 -0
- data/spec/spec_helper.rb +19 -0
- data/spec/support/tasks.rb +7 -0
- data/spec/tasks/translation_spec.rb +123 -0
- data/test/rails_translation_manager/yaml_writer_test.rb +2 -0
- data/tmp/.gitkeep +0 -0
- metadata +93 -24
- data/jenkins.sh +0 -9
- data/lib/rails_translation_manager/stealer.rb +0 -85
- data/lib/rails_translation_manager/validator.rb +0 -92
- data/test/rails_translation_manager/importer_test.rb +0 -132
- data/test/rails_translation_manager/stealer_test.rb +0 -251
- data/test/rails_translation_manager/validator_test.rb +0 -51
@@ -0,0 +1,68 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "spec_helper"
|
4
|
+
|
5
|
+
RSpec.describe RailsTranslationManager::LocaleChecker do
|
6
|
+
context "when the locales are valid" do
|
7
|
+
it "calls each checker class" do
|
8
|
+
described_class::CHECKER_CLASSES.each do |checker|
|
9
|
+
expect_any_instance_of(checker).to receive(:report)
|
10
|
+
end
|
11
|
+
|
12
|
+
described_class.new("spec/locales/in_sync/**/*.yml").validate_locales
|
13
|
+
end
|
14
|
+
|
15
|
+
it "outputs a confirmation" do
|
16
|
+
expect { described_class.new("spec/locales/in_sync/**/*.yml").validate_locales }
|
17
|
+
.to output("Locale files are in sync, nice job!\n").to_stdout
|
18
|
+
end
|
19
|
+
|
20
|
+
it "returns true" do
|
21
|
+
expect(described_class.new("spec/locales/in_sync/**/*.yml").validate_locales)
|
22
|
+
.to eq(true)
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
context "when the locales are not valid" do
|
27
|
+
it "calls each checker class" do
|
28
|
+
described_class::CHECKER_CLASSES.each do |checker|
|
29
|
+
expect_any_instance_of(checker).to receive(:report)
|
30
|
+
end
|
31
|
+
|
32
|
+
described_class.new("spec/locales/out_of_sync/*.yml").validate_locales
|
33
|
+
end
|
34
|
+
|
35
|
+
it "outputs the report" do
|
36
|
+
printed = capture_stdout do
|
37
|
+
described_class.new("spec/locales/out_of_sync/*.yml").validate_locales
|
38
|
+
end
|
39
|
+
|
40
|
+
expect(printed.scan(/\[ERROR\]/).count).to eq(3)
|
41
|
+
end
|
42
|
+
|
43
|
+
it "returns false" do
|
44
|
+
expect(described_class.new("spec/locales/out_of_sync/*.yml").validate_locales)
|
45
|
+
.to eq(false)
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
context "when the locale path doesn't relate to any YAML files" do
|
50
|
+
it "doesn't call any checker classes" do
|
51
|
+
described_class::CHECKER_CLASSES.each do |checker|
|
52
|
+
expect_any_instance_of(checker).to_not receive(:report)
|
53
|
+
end
|
54
|
+
|
55
|
+
described_class.new("some/random/path").validate_locales
|
56
|
+
end
|
57
|
+
|
58
|
+
it "outputs an error message" do
|
59
|
+
expect { described_class.new("some/random/path").validate_locales }
|
60
|
+
.to output("No locale files found for the supplied path\n").to_stdout
|
61
|
+
end
|
62
|
+
|
63
|
+
it "returns false" do
|
64
|
+
expect(described_class.new("some/random/path").validate_locales)
|
65
|
+
.to eq(false)
|
66
|
+
end
|
67
|
+
end
|
68
|
+
end
|
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,19 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "rails_translation_manager"
|
4
|
+
|
5
|
+
RSpec.configure do |config|
|
6
|
+
config.before do
|
7
|
+
I18n.available_locales = %i[en cy]
|
8
|
+
config.before { allow($stdout).to receive(:puts) }
|
9
|
+
end
|
10
|
+
|
11
|
+
def capture_stdout(&blk)
|
12
|
+
old = $stdout
|
13
|
+
$stdout = fake = StringIO.new
|
14
|
+
blk.call
|
15
|
+
fake.string
|
16
|
+
ensure
|
17
|
+
$stdout = old
|
18
|
+
end
|
19
|
+
end
|
@@ -0,0 +1,123 @@
|
|
1
|
+
require "spec_helper"
|
2
|
+
require_relative "../../spec/support/tasks"
|
3
|
+
|
4
|
+
describe "rake tasks" do
|
5
|
+
before do
|
6
|
+
fake_rails = double()
|
7
|
+
fake_rails.stub(:root) { Pathname.new("spec") }
|
8
|
+
stub_const("Rails", fake_rails)
|
9
|
+
end
|
10
|
+
|
11
|
+
describe "translation:import", type: :task do
|
12
|
+
let(:task) { Rake::Task["translation:import"] }
|
13
|
+
let(:csv_path) { "path/to/import/fr.csv" }
|
14
|
+
let!(:importer_instance) { stub_importer }
|
15
|
+
|
16
|
+
it "outputs to stdout" do
|
17
|
+
expect { task.execute(csv_path: csv_path) }
|
18
|
+
.to output("Imported CSV from: #{csv_path} to #{Rails.root.join("config", "locales")}\n")
|
19
|
+
.to_stdout
|
20
|
+
end
|
21
|
+
|
22
|
+
it "calls the Importer class with the csv and import paths" do
|
23
|
+
task.execute(csv_path: csv_path)
|
24
|
+
|
25
|
+
expect(RailsTranslationManager::Importer)
|
26
|
+
.to have_received(:new)
|
27
|
+
.with(locale: "fr",
|
28
|
+
csv_path: csv_path,
|
29
|
+
import_directory: Rails.root.join("config", "locales"),
|
30
|
+
multiple_files_per_language: false)
|
31
|
+
expect(importer_instance).to have_received(:import)
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
describe "translation:import:all", type: :task do
|
36
|
+
let(:task) { Rake::Task["translation:import:all"] }
|
37
|
+
let(:csv_directory) { "locales/importer" }
|
38
|
+
let!(:importer_instance) { stub_importer }
|
39
|
+
|
40
|
+
it "outputs to stdout" do
|
41
|
+
expect { task.execute(csv_directory: csv_directory) }
|
42
|
+
.to output("Imported all CSVs from: #{csv_directory} to #{Rails.root.join("config", "locales")}\n")
|
43
|
+
.to_stdout
|
44
|
+
end
|
45
|
+
|
46
|
+
it "calls the importer class for each target path" do
|
47
|
+
task.execute(csv_directory: csv_directory, multiple_files_per_language: true)
|
48
|
+
|
49
|
+
expect(RailsTranslationManager::Importer)
|
50
|
+
.to have_received(:new)
|
51
|
+
.with(locale: "fr",
|
52
|
+
csv_path: "spec/locales/importer/fr.csv",
|
53
|
+
import_directory: Rails.root.join("config", "locales"),
|
54
|
+
multiple_files_per_language: true)
|
55
|
+
expect(importer_instance).to have_received(:import)
|
56
|
+
end
|
57
|
+
end
|
58
|
+
|
59
|
+
describe "translation:add_missing", type: :task do
|
60
|
+
let(:task) { Rake::Task["translation:add_missing"] }
|
61
|
+
let!(:cleaner_instance) { stub_cleaner }
|
62
|
+
|
63
|
+
before do
|
64
|
+
allow(I18n::Tasks::CLI).to receive(:start)
|
65
|
+
end
|
66
|
+
|
67
|
+
it "triggers Cleaner and allows to receive the right arguments" do
|
68
|
+
task.execute
|
69
|
+
expect(RailsTranslationManager::Cleaner)
|
70
|
+
.to have_received(:new)
|
71
|
+
.with(Rails.root.join("config", "locales"))
|
72
|
+
expect(cleaner_instance).to have_received(:clean)
|
73
|
+
end
|
74
|
+
|
75
|
+
it "triggers i18n task and allows to receive the right arguments" do
|
76
|
+
task.execute(locale: "fr")
|
77
|
+
expect(I18n::Tasks::CLI).to have_received(:start).with(
|
78
|
+
["add-missing", "--nil-value", ["-l", "fr"]]
|
79
|
+
)
|
80
|
+
end
|
81
|
+
end
|
82
|
+
|
83
|
+
describe "translation:normalize", type: :task do
|
84
|
+
let(:task) { Rake::Task["translation:normalize"] }
|
85
|
+
let!(:cleaner_instance) { stub_cleaner }
|
86
|
+
|
87
|
+
before do
|
88
|
+
allow(I18n::Tasks::CLI).to receive(:start)
|
89
|
+
end
|
90
|
+
|
91
|
+
it "triggers Cleaner and allows to receive the right arguments" do
|
92
|
+
task.execute(locale_directory: "config/locales")
|
93
|
+
expect(RailsTranslationManager::Cleaner)
|
94
|
+
.to have_received(:new)
|
95
|
+
.with(Rails.root.join("config", "locales"))
|
96
|
+
expect(cleaner_instance).to have_received(:clean)
|
97
|
+
end
|
98
|
+
|
99
|
+
it "triggers i18n task and allows to receive the right arguments" do
|
100
|
+
task.execute
|
101
|
+
expect(I18n::Tasks::CLI).to have_received(:start).with(["normalize"])
|
102
|
+
end
|
103
|
+
end
|
104
|
+
|
105
|
+
def stub_importer
|
106
|
+
importer_instance = instance_double(RailsTranslationManager::Importer)
|
107
|
+
allow(RailsTranslationManager::Importer).to receive(:new)
|
108
|
+
.and_return(importer_instance)
|
109
|
+
allow(importer_instance).to receive(:import)
|
110
|
+
|
111
|
+
importer_instance
|
112
|
+
end
|
113
|
+
|
114
|
+
def stub_cleaner
|
115
|
+
cleaner_instance = instance_double(RailsTranslationManager::Cleaner)
|
116
|
+
allow(RailsTranslationManager::Cleaner)
|
117
|
+
.to receive(:new)
|
118
|
+
.and_return(cleaner_instance)
|
119
|
+
allow(cleaner_instance).to receive(:clean)
|
120
|
+
|
121
|
+
cleaner_instance
|
122
|
+
end
|
123
|
+
end
|
data/tmp/.gitkeep
ADDED
File without changes
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rails_translation_manager
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 1.1.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Edd Sowden
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2021-11-04 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rails-i18n
|
@@ -39,33 +39,33 @@ dependencies:
|
|
39
39
|
- !ruby/object:Gem::Version
|
40
40
|
version: '0'
|
41
41
|
- !ruby/object:Gem::Dependency
|
42
|
-
name:
|
42
|
+
name: i18n-tasks
|
43
43
|
requirement: !ruby/object:Gem::Requirement
|
44
44
|
requirements:
|
45
|
-
- - "
|
45
|
+
- - ">="
|
46
46
|
- !ruby/object:Gem::Version
|
47
|
-
version: '
|
48
|
-
type: :
|
47
|
+
version: '0'
|
48
|
+
type: :runtime
|
49
49
|
prerelease: false
|
50
50
|
version_requirements: !ruby/object:Gem::Requirement
|
51
51
|
requirements:
|
52
|
-
- - "
|
52
|
+
- - ">="
|
53
53
|
- !ruby/object:Gem::Version
|
54
|
-
version: '
|
54
|
+
version: '0'
|
55
55
|
- !ruby/object:Gem::Dependency
|
56
|
-
name:
|
56
|
+
name: bundler
|
57
57
|
requirement: !ruby/object:Gem::Requirement
|
58
58
|
requirements:
|
59
|
-
- - "
|
59
|
+
- - ">="
|
60
60
|
- !ruby/object:Gem::Version
|
61
|
-
version:
|
61
|
+
version: '0'
|
62
62
|
type: :development
|
63
63
|
prerelease: false
|
64
64
|
version_requirements: !ruby/object:Gem::Requirement
|
65
65
|
requirements:
|
66
|
-
- - "
|
66
|
+
- - ">="
|
67
67
|
- !ruby/object:Gem::Version
|
68
|
-
version:
|
68
|
+
version: '0'
|
69
69
|
- !ruby/object:Gem::Dependency
|
70
70
|
name: rake
|
71
71
|
requirement: !ruby/object:Gem::Requirement
|
@@ -94,6 +94,34 @@ dependencies:
|
|
94
94
|
- - ">="
|
95
95
|
- !ruby/object:Gem::Version
|
96
96
|
version: '0'
|
97
|
+
- !ruby/object:Gem::Dependency
|
98
|
+
name: rspec
|
99
|
+
requirement: !ruby/object:Gem::Requirement
|
100
|
+
requirements:
|
101
|
+
- - ">="
|
102
|
+
- !ruby/object:Gem::Version
|
103
|
+
version: '0'
|
104
|
+
type: :development
|
105
|
+
prerelease: false
|
106
|
+
version_requirements: !ruby/object:Gem::Requirement
|
107
|
+
requirements:
|
108
|
+
- - ">="
|
109
|
+
- !ruby/object:Gem::Version
|
110
|
+
version: '0'
|
111
|
+
- !ruby/object:Gem::Dependency
|
112
|
+
name: byebug
|
113
|
+
requirement: !ruby/object:Gem::Requirement
|
114
|
+
requirements:
|
115
|
+
- - ">="
|
116
|
+
- !ruby/object:Gem::Version
|
117
|
+
version: '0'
|
118
|
+
type: :development
|
119
|
+
prerelease: false
|
120
|
+
version_requirements: !ruby/object:Gem::Requirement
|
121
|
+
requirements:
|
122
|
+
- - ">="
|
123
|
+
- !ruby/object:Gem::Version
|
124
|
+
version: '0'
|
97
125
|
description: ''
|
98
126
|
email:
|
99
127
|
- edd.sowden@digital.cabinet-office.gov.uk
|
@@ -107,26 +135,52 @@ files:
|
|
107
135
|
- CHANGELOG.md
|
108
136
|
- CONTRIBUTING.md
|
109
137
|
- Gemfile
|
138
|
+
- Jenkinsfile
|
110
139
|
- LICENSE.txt
|
111
140
|
- README.md
|
112
141
|
- Rakefile
|
113
|
-
-
|
142
|
+
- config/locales/plurals.rb
|
114
143
|
- lib/rails_translation_manager.rb
|
144
|
+
- lib/rails_translation_manager/cleaner.rb
|
115
145
|
- lib/rails_translation_manager/exporter.rb
|
146
|
+
- lib/rails_translation_manager/i18n_tasks_option_parser.rb
|
116
147
|
- lib/rails_translation_manager/importer.rb
|
148
|
+
- lib/rails_translation_manager/locale_checker.rb
|
149
|
+
- lib/rails_translation_manager/locale_checker/all_locales.rb
|
150
|
+
- lib/rails_translation_manager/locale_checker/base_checker.rb
|
151
|
+
- lib/rails_translation_manager/locale_checker/incompatible_plurals.rb
|
152
|
+
- lib/rails_translation_manager/locale_checker/locale_checker_helper.rb
|
153
|
+
- lib/rails_translation_manager/locale_checker/missing_english_locales.rb
|
154
|
+
- lib/rails_translation_manager/locale_checker/missing_foreign_locales.rb
|
155
|
+
- lib/rails_translation_manager/locale_checker/plural_forms.rb
|
117
156
|
- lib/rails_translation_manager/railtie.rb
|
118
|
-
- lib/rails_translation_manager/stealer.rb
|
119
|
-
- lib/rails_translation_manager/validator.rb
|
120
157
|
- lib/rails_translation_manager/version.rb
|
121
158
|
- lib/rails_translation_manager/yaml_writer.rb
|
122
159
|
- lib/tasks/translation.rake
|
123
160
|
- rails_translation_manager.gemspec
|
161
|
+
- spec/locales/cleaner/clean.yml
|
162
|
+
- spec/locales/cleaner/with_whitespace.yml
|
163
|
+
- spec/locales/importer/fr.csv
|
164
|
+
- spec/locales/in_sync/cy/browse.yml
|
165
|
+
- spec/locales/in_sync/en/browse.yml
|
166
|
+
- spec/locales/out_of_sync/cy.yml
|
167
|
+
- spec/locales/out_of_sync/en.yml
|
168
|
+
- spec/rails_translation_manager/cleaner_spec.rb
|
169
|
+
- spec/rails_translation_manager/importer_spec.rb
|
170
|
+
- spec/rails_translation_manager/locale_checker/all_locales_spec.rb
|
171
|
+
- spec/rails_translation_manager/locale_checker/incompatible_plurals_spec.rb
|
172
|
+
- spec/rails_translation_manager/locale_checker/locale_checker_helper_spec.rb
|
173
|
+
- spec/rails_translation_manager/locale_checker/missing_english_locales_spec.rb
|
174
|
+
- spec/rails_translation_manager/locale_checker/missing_foreign_locales_spec.rb
|
175
|
+
- spec/rails_translation_manager/locale_checker/plural_forms_spec.rb
|
176
|
+
- spec/rails_translation_manager/locale_checker_spec.rb
|
177
|
+
- spec/spec_helper.rb
|
178
|
+
- spec/support/tasks.rb
|
179
|
+
- spec/tasks/translation_spec.rb
|
124
180
|
- test/rails_translation_manager/exporter_test.rb
|
125
|
-
- test/rails_translation_manager/importer_test.rb
|
126
|
-
- test/rails_translation_manager/stealer_test.rb
|
127
|
-
- test/rails_translation_manager/validator_test.rb
|
128
181
|
- test/rails_translation_manager/yaml_writer_test.rb
|
129
182
|
- test/test_helper.rb
|
183
|
+
- tmp/.gitkeep
|
130
184
|
homepage: ''
|
131
185
|
licenses:
|
132
186
|
- MIT
|
@@ -146,15 +200,30 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
146
200
|
- !ruby/object:Gem::Version
|
147
201
|
version: '0'
|
148
202
|
requirements: []
|
149
|
-
|
150
|
-
rubygems_version: 2.2.2
|
203
|
+
rubygems_version: 3.0.3
|
151
204
|
signing_key:
|
152
205
|
specification_version: 4
|
153
206
|
summary: Tasks to manage translation files
|
154
207
|
test_files:
|
208
|
+
- spec/locales/cleaner/clean.yml
|
209
|
+
- spec/locales/cleaner/with_whitespace.yml
|
210
|
+
- spec/locales/importer/fr.csv
|
211
|
+
- spec/locales/in_sync/cy/browse.yml
|
212
|
+
- spec/locales/in_sync/en/browse.yml
|
213
|
+
- spec/locales/out_of_sync/cy.yml
|
214
|
+
- spec/locales/out_of_sync/en.yml
|
215
|
+
- spec/rails_translation_manager/cleaner_spec.rb
|
216
|
+
- spec/rails_translation_manager/importer_spec.rb
|
217
|
+
- spec/rails_translation_manager/locale_checker/all_locales_spec.rb
|
218
|
+
- spec/rails_translation_manager/locale_checker/incompatible_plurals_spec.rb
|
219
|
+
- spec/rails_translation_manager/locale_checker/locale_checker_helper_spec.rb
|
220
|
+
- spec/rails_translation_manager/locale_checker/missing_english_locales_spec.rb
|
221
|
+
- spec/rails_translation_manager/locale_checker/missing_foreign_locales_spec.rb
|
222
|
+
- spec/rails_translation_manager/locale_checker/plural_forms_spec.rb
|
223
|
+
- spec/rails_translation_manager/locale_checker_spec.rb
|
224
|
+
- spec/spec_helper.rb
|
225
|
+
- spec/support/tasks.rb
|
226
|
+
- spec/tasks/translation_spec.rb
|
155
227
|
- test/rails_translation_manager/exporter_test.rb
|
156
|
-
- test/rails_translation_manager/importer_test.rb
|
157
|
-
- test/rails_translation_manager/stealer_test.rb
|
158
|
-
- test/rails_translation_manager/validator_test.rb
|
159
228
|
- test/rails_translation_manager/yaml_writer_test.rb
|
160
229
|
- test/test_helper.rb
|
data/jenkins.sh
DELETED
@@ -1,85 +0,0 @@
|
|
1
|
-
require "yaml"
|
2
|
-
require "i18n"
|
3
|
-
require_relative "yaml_writer"
|
4
|
-
|
5
|
-
class RailsTranslationManager::Stealer
|
6
|
-
include YAMLWriter
|
7
|
-
|
8
|
-
# locale is the locale name as a string.
|
9
|
-
# source_app_path is the path to the root of the app to steal from.
|
10
|
-
# mapping_file_path is the path to a YAML file mapping translation keys in
|
11
|
-
# the source app to those in the target app. For example:
|
12
|
-
# document.type: content_item.format
|
13
|
-
# document.published: content_item.metadata.published
|
14
|
-
# which will import everything under "document.type" and "document.published"
|
15
|
-
# in the source app, and write it to "content_item.format" and
|
16
|
-
# "content_item.metadata.published" in the target app.
|
17
|
-
# locales_path is the path to the locale files to output, which is usually
|
18
|
-
# Rails.root.join('config/locales').
|
19
|
-
# The process will preserve data already in the output file if it is not
|
20
|
-
# referenced in the mapping, but will always override data belonging to keys
|
21
|
-
# that are in the mapping.
|
22
|
-
def initialize(locale, source_app_path, mapping_file_path, locales_path)
|
23
|
-
@locale = locale
|
24
|
-
@source_app_path = source_app_path
|
25
|
-
@mapping_file_path = mapping_file_path
|
26
|
-
@locales_path = locales_path
|
27
|
-
end
|
28
|
-
|
29
|
-
def steal_locale
|
30
|
-
target_data = convert_locale(get_target_data)
|
31
|
-
write_yaml(target_locale_path, target_data)
|
32
|
-
end
|
33
|
-
|
34
|
-
def convert_locale(target_data)
|
35
|
-
mapping_data.each do |source, target|
|
36
|
-
data = source_data[@locale]
|
37
|
-
source.split('.').each { |key| data = data.fetch(key, {}) }
|
38
|
-
set_recursive(target_data[@locale], target.split("."), data)
|
39
|
-
end
|
40
|
-
target_data
|
41
|
-
end
|
42
|
-
|
43
|
-
private
|
44
|
-
|
45
|
-
def set_recursive(hash, keys, data)
|
46
|
-
if keys.empty?
|
47
|
-
data
|
48
|
-
else
|
49
|
-
key = keys.shift
|
50
|
-
hash.tap do |h|
|
51
|
-
h.merge!({ key => set_recursive(hash.fetch(key, {}), keys, data)})
|
52
|
-
end
|
53
|
-
end
|
54
|
-
end
|
55
|
-
|
56
|
-
def source_locale_path
|
57
|
-
File.join(@source_app_path, 'config', 'locales', "#{@locale}.yml")
|
58
|
-
end
|
59
|
-
|
60
|
-
def source_data
|
61
|
-
@source_data ||= YAML.load_file(source_locale_path)
|
62
|
-
end
|
63
|
-
|
64
|
-
def target_locale_path
|
65
|
-
File.join(@locales_path, "#{@locale}.yml")
|
66
|
-
end
|
67
|
-
|
68
|
-
def default_target_data
|
69
|
-
{ @locale => {} }
|
70
|
-
end
|
71
|
-
|
72
|
-
def get_target_data
|
73
|
-
if File.exist?(target_locale_path)
|
74
|
-
YAML.load_file(target_locale_path) || default_target_data
|
75
|
-
else
|
76
|
-
default_target_data
|
77
|
-
end
|
78
|
-
end
|
79
|
-
|
80
|
-
def mapping_data
|
81
|
-
@mapping_data ||= YAML.load_file(@mapping_file_path)
|
82
|
-
end
|
83
|
-
|
84
|
-
end
|
85
|
-
|
@@ -1,92 +0,0 @@
|
|
1
|
-
require 'yaml'
|
2
|
-
require 'logger'
|
3
|
-
|
4
|
-
class RailsTranslationManager::Validator
|
5
|
-
def initialize(translation_file_path, logger = Logger.new(nil))
|
6
|
-
@translation_file_path = translation_file_path
|
7
|
-
@logger = logger
|
8
|
-
end
|
9
|
-
|
10
|
-
def check!
|
11
|
-
@logger.info "Checking translation files in '#{@translation_file_path}' for unexpected interpolation keys"
|
12
|
-
@logger.info "Loading reference file (#{reference_file_name})"
|
13
|
-
@logger.info "Checking..."
|
14
|
-
reference = load_translation_file("#{@translation_file_path}/#{reference_file_name}")
|
15
|
-
Dir["#{@translation_file_path}/*.yml"].reject do |entry|
|
16
|
-
File.basename(entry) == reference_file_name
|
17
|
-
end.inject([]) do |errors, entry|
|
18
|
-
translation_file = load_translation_file(entry)
|
19
|
-
errors + unexpected_substitution_keys(reference, translation_file)
|
20
|
-
end
|
21
|
-
end
|
22
|
-
|
23
|
-
def unexpected_substitution_keys(reference, translation_file)
|
24
|
-
reference_substitutions = substitutions_in(reference)
|
25
|
-
target_substitutions = substitutions_in(translation_file)
|
26
|
-
|
27
|
-
targets_by_path = target_substitutions.each_with_object({}) do |target, hash|
|
28
|
-
hash[exclude_locale_from_path(target.path)] = target
|
29
|
-
end
|
30
|
-
|
31
|
-
reference_substitutions.each_with_object([]) do |reference, unexpected_substitutions|
|
32
|
-
target = targets_by_path[exclude_locale_from_path(reference.path)]
|
33
|
-
next if target.nil? || reference.has_all_substitutions?(target)
|
34
|
-
unexpected_substitutions << UnexpectedSubstition.new(target, reference)
|
35
|
-
end
|
36
|
-
end
|
37
|
-
|
38
|
-
def substitutions_in(translation_file)
|
39
|
-
flatten(translation_file).reject do |translation|
|
40
|
-
translation.substitutions.empty?
|
41
|
-
end
|
42
|
-
end
|
43
|
-
|
44
|
-
class TranslationEntry < Struct.new(:path, :value)
|
45
|
-
def substitutions
|
46
|
-
@substitutions ||= self.value.scan(/%{([^}]*)}/)
|
47
|
-
end
|
48
|
-
|
49
|
-
def has_all_substitutions?(other)
|
50
|
-
(other.substitutions - self.substitutions).empty?
|
51
|
-
end
|
52
|
-
end
|
53
|
-
|
54
|
-
class UnexpectedSubstition < Struct.new(:target, :reference)
|
55
|
-
def to_s
|
56
|
-
missing = (self.reference.substitutions - self.target.substitutions)
|
57
|
-
extras = (self.target.substitutions - self.reference.substitutions)
|
58
|
-
message = %Q{Key "#{target.path.join('.')}":}
|
59
|
-
if extras.any?
|
60
|
-
message << %Q{ Extra substitutions: ["#{extras.join('", "')}"].}
|
61
|
-
end
|
62
|
-
if missing.any?
|
63
|
-
message << %Q{ Missing substitutions: ["#{missing.join('", "')}"].}
|
64
|
-
end
|
65
|
-
message
|
66
|
-
end
|
67
|
-
end
|
68
|
-
|
69
|
-
def flatten(translation_file, path = [])
|
70
|
-
translation_file.map do |key, value|
|
71
|
-
case value
|
72
|
-
when Hash
|
73
|
-
flatten(value, path + [key])
|
74
|
-
else
|
75
|
-
TranslationEntry.new(path + [key], value || "")
|
76
|
-
end
|
77
|
-
end.flatten
|
78
|
-
end
|
79
|
-
|
80
|
-
def load_translation_file(filename)
|
81
|
-
YAML.load_file(filename)
|
82
|
-
end
|
83
|
-
|
84
|
-
def reference_file_name
|
85
|
-
"en.yml"
|
86
|
-
end
|
87
|
-
|
88
|
-
private
|
89
|
-
def exclude_locale_from_path(path)
|
90
|
-
path[1..-1]
|
91
|
-
end
|
92
|
-
end
|