vocab 0.0.2 → 0.0.3
Sign up to get free protection for your applications and to get access to all the features.
- data/.gitignore +2 -1
- data/CHANGELOG.md +4 -0
- data/MIT-LICENSE +7 -0
- data/README.md +66 -14
- data/bin/vocab +1 -1
- data/lib/vocab/application.rb +7 -5
- data/lib/vocab/extractor/android.rb +31 -14
- data/lib/vocab/extractor/base.rb +27 -11
- data/lib/vocab/extractor/rails.rb +16 -6
- data/lib/vocab/merger/android.rb +48 -15
- data/lib/vocab/merger/base.rb +0 -6
- data/lib/vocab/translator/android.rb +67 -9
- data/lib/vocab/validator/android.rb +2 -2
- data/lib/vocab/validator/base.rb +7 -1
- data/lib/vocab/validator/rails.rb +1 -1
- data/lib/vocab/version.rb +1 -1
- data/spec/data/android/locales/values/strings.xml +11 -0
- data/spec/data/android/locales/values-es/strings.xml +5 -0
- data/spec/data/android/translations/values-es/es-string-file.xml +11 -0
- data/spec/data/android/write.xml +1 -0
- data/spec/data/android/write_plurals.xml +14 -0
- data/spec/data/rails/locales/en.yml +4 -0
- data/spec/extractor/android_spec.rb +47 -26
- data/spec/extractor/base_spec.rb +25 -8
- data/spec/extractor/rails_spec.rb +23 -20
- data/spec/merger/android_spec.rb +78 -25
- data/spec/merger/base_spec.rb +0 -1
- data/spec/merger/rails_spec.rb +1 -2
- data/spec/spec_helper.rb +8 -5
- data/spec/support/matchers.rb +25 -0
- data/spec/translator/android_spec.rb +45 -2
- data/spec/translator/rails_spec.rb +28 -24
- data/spec/validator/android_spec.rb +2 -2
- data/spec/validator/base_spec.rb +23 -0
- data/spec/validator/rails_spec.rb +6 -6
- data/vocab.gemspec +1 -0
- metadata +23 -8
@@ -4,4 +4,15 @@
|
|
4
4
|
<string name="delete">La función Child Lock</string>
|
5
5
|
<string name="pd_app_name">el Panel para padres bien</string>
|
6
6
|
<string name="translator_cruft">Malo</string>
|
7
|
+
<string name="apostrophe">Translator's evil apostrophe don\'t care</string>
|
8
|
+
|
9
|
+
<plurals name="user_count">
|
10
|
+
<item quantity="one">1 usuario</item>
|
11
|
+
<item quantity="many">%d usuarios</item>
|
12
|
+
</plurals>
|
13
|
+
|
14
|
+
<plurals name="fish_count">
|
15
|
+
<item quantity="one">1 pescado</item>
|
16
|
+
<item quantity="many">%d peces</item>
|
17
|
+
</plurals>
|
7
18
|
</resources>
|
data/spec/data/android/write.xml
CHANGED
@@ -1,5 +1,6 @@
|
|
1
1
|
<?xml version="1.0" encoding="UTF-8"?>
|
2
2
|
<resources>
|
3
|
+
<string name="apostrophe">Translator\'s evil apostrophe don\'t care</string>
|
3
4
|
<string name="app_name">Kid Mode</string>
|
4
5
|
<string name="delete">La funci&#xF3;n Child Lock</string>
|
5
6
|
<string name="pd_app_name">Parent Dashboard</string>
|
@@ -0,0 +1,14 @@
|
|
1
|
+
<?xml version="1.0" encoding="UTF-8"?>
|
2
|
+
<resources>
|
3
|
+
<string name="app_name">Kid Mode</string>
|
4
|
+
<string name="delete">La funci&#xF3;n Child Lock</string>
|
5
|
+
<string name="pd_app_name">Parent Dashboard</string>
|
6
|
+
<plurals name="deer">
|
7
|
+
<item quantity="one">1 deer</item>
|
8
|
+
<item quantity="other">2 deer</item>
|
9
|
+
</plurals>
|
10
|
+
<plurals name="users">
|
11
|
+
<item quantity="one">1 user</item>
|
12
|
+
<item quantity="other">2 users</item>
|
13
|
+
</plurals>
|
14
|
+
</resources>
|
@@ -6,21 +6,22 @@ describe "Vocab::Extractor::Android" do
|
|
6
6
|
@locale = "#{vocab_root}/spec/data/android/locales/values/strings.xml"
|
7
7
|
end
|
8
8
|
|
9
|
-
describe '
|
9
|
+
describe 'current_strings' do
|
10
10
|
|
11
11
|
it "extracts hash of current string translations" do
|
12
|
-
actual = Vocab::Extractor::Android.
|
12
|
+
actual = Vocab::Extractor::Android.current_strings( @locale )
|
13
13
|
actual.should eql( { "app_name" =>"Kid Mode",
|
14
14
|
"delete" =>"Delete",
|
15
15
|
"cancel" =>"Cancel",
|
16
16
|
"app_current"=>"current",
|
17
17
|
"pd_app_name"=>"Parent Dashboard",
|
18
|
-
"not_in_es" =>"This key not in spanish",
|
18
|
+
"not_in_es" =>"This key not in spanish",
|
19
|
+
"debug_key" =>"Should be ignored" } )
|
19
20
|
end
|
20
21
|
|
21
22
|
end
|
22
23
|
|
23
|
-
describe '
|
24
|
+
describe 'previous_strings' do
|
24
25
|
|
25
26
|
before( :each ) do
|
26
27
|
Dir.chdir( vocab_root )
|
@@ -32,7 +33,7 @@ describe "Vocab::Extractor::Android" do
|
|
32
33
|
end
|
33
34
|
|
34
35
|
it "extracts hash of previous string translations" do
|
35
|
-
actual = Vocab::Extractor::Android.
|
36
|
+
actual = Vocab::Extractor::Android.previous_strings( @locale )
|
36
37
|
actual.should eql( { 'app_name' => 'Kid Mode',
|
37
38
|
'pd_app_name' => 'Parent Dashboard',
|
38
39
|
'app_current' => 'current' } )
|
@@ -40,13 +41,46 @@ describe "Vocab::Extractor::Android" do
|
|
40
41
|
|
41
42
|
end
|
42
43
|
|
44
|
+
describe 'current_plurals' do
|
45
|
+
|
46
|
+
it "extracts the plural definitions from the strings file" do
|
47
|
+
expected = { "user_count" => { "one" => "1 user",
|
48
|
+
"many" => "%d users" },
|
49
|
+
"fish_count" => { "one" => "1 fish",
|
50
|
+
"many" => "%d fish" } }
|
51
|
+
Vocab::Extractor::Android.current_plurals( @locale ).should eql( expected )
|
52
|
+
end
|
53
|
+
|
54
|
+
end
|
55
|
+
|
56
|
+
describe 'previous_plurals' do
|
57
|
+
|
58
|
+
before( :each ) do
|
59
|
+
Dir.chdir( vocab_root )
|
60
|
+
end
|
61
|
+
|
62
|
+
before( :each ) do
|
63
|
+
@sha = '618e87b6a53e8fc216f046e51b1606313052bf75'
|
64
|
+
Vocab.settings.stub!( :last_translation ).and_return( @sha )
|
65
|
+
end
|
66
|
+
|
67
|
+
it "extracts hash of previous string translations" do
|
68
|
+
actual = Vocab::Extractor::Android.previous_plurals( @locale )
|
69
|
+
actual.should eql( { "fish_count" => { "one" => "1 fishes",
|
70
|
+
"many" => "%d fish" } } )
|
71
|
+
end
|
72
|
+
|
73
|
+
end
|
74
|
+
|
43
75
|
describe 'write_full' do
|
44
76
|
|
45
77
|
it 'writes the full translation to the correct xml file' do
|
46
|
-
|
78
|
+
strings = { 'foo' => 'bar' }
|
79
|
+
plurals = { 'users' => { 'one' => '1 user',
|
80
|
+
'other' => '2 users' } }
|
47
81
|
Vocab::Translator::Android.should_receive( :write ).
|
48
|
-
with(
|
49
|
-
Vocab::Extractor::Android.write_full(
|
82
|
+
with( strings, plurals, "#{vocab_root}/strings.full.xml" )
|
83
|
+
Vocab::Extractor::Android.write_full( strings, plurals )
|
50
84
|
end
|
51
85
|
|
52
86
|
end
|
@@ -54,25 +88,12 @@ describe "Vocab::Extractor::Android" do
|
|
54
88
|
describe 'write_diff' do
|
55
89
|
|
56
90
|
it 'writes the diff translation to the correct xml file' do
|
57
|
-
|
91
|
+
strings = { 'foo' => 'bar' }
|
92
|
+
plurals = { 'users' => { 'one' => '1 user',
|
93
|
+
'other' => '2 users' } }
|
58
94
|
Vocab::Translator::Android.should_receive( :write ).
|
59
|
-
with(
|
60
|
-
Vocab::Extractor::Android.write_diff(
|
61
|
-
end
|
62
|
-
|
63
|
-
end
|
64
|
-
|
65
|
-
describe 'write' do
|
66
|
-
|
67
|
-
it 'writes the translation to a xml file' do
|
68
|
-
translation = { 'app_name' => 'Kid Mode',
|
69
|
-
'pd_app_name' => 'Parent Dashboard',
|
70
|
-
'delete' => "La función Child Lock" }
|
71
|
-
path = "#{vocab_root}/spec/tmp/strings.xml"
|
72
|
-
Vocab::Translator::Android.write( translation, path )
|
73
|
-
should_eql_file( File.open( path ) { |f| f.read },
|
74
|
-
"spec/data/android/write.xml" )
|
75
|
-
File.delete( path )
|
95
|
+
with( strings, plurals, "#{vocab_root}/strings.diff.xml" )
|
96
|
+
Vocab::Extractor::Android.write_diff( strings, plurals )
|
76
97
|
end
|
77
98
|
|
78
99
|
end
|
data/spec/extractor/base_spec.rb
CHANGED
@@ -36,6 +36,20 @@ describe "Vocab::Extractor::Base" do
|
|
36
36
|
:"en.models.product.id_126.name"=>"This is new"}
|
37
37
|
end
|
38
38
|
|
39
|
+
it "finds new plural definitions" do
|
40
|
+
@current = { 'users' => {}, 'fish' => {} }
|
41
|
+
@previous = { 'users' => {} }
|
42
|
+
diff = Vocab::Extractor::Base.diff( @previous, @current )
|
43
|
+
diff.should == { 'fish' => {} }
|
44
|
+
end
|
45
|
+
|
46
|
+
it "finds updated plural definitions" do
|
47
|
+
@current = { 'users' => { 'one' => '1 user', 'other' => '%d users' }, 'fish' => {} }
|
48
|
+
@previous = { 'users' => { 'one' => '1 person', 'other' => '%d users' }, 'fish' => {} }
|
49
|
+
diff = Vocab::Extractor::Base.diff( @previous, @current )
|
50
|
+
diff.should == { 'users' => { 'one' => '1 user', 'other' => '%d users' } }
|
51
|
+
end
|
52
|
+
|
39
53
|
end
|
40
54
|
|
41
55
|
describe "extract" do
|
@@ -49,11 +63,14 @@ describe "Vocab::Extractor::Base" do
|
|
49
63
|
it "extracts the strings that need to be translated into a yml file" do
|
50
64
|
current = { 1 => 5, 3 => 4 }
|
51
65
|
previous = { 1 => 2 }
|
52
|
-
Vocab::Extractor::Base.should_receive( :
|
53
|
-
Vocab::Extractor::Base.should_receive( :
|
54
|
-
Vocab::Extractor::Base.should_receive( :
|
55
|
-
Vocab::Extractor::Base.should_receive( :
|
66
|
+
Vocab::Extractor::Base.should_receive( :current_strings ).and_return( current )
|
67
|
+
Vocab::Extractor::Base.should_receive( :previous_strings ).and_return( previous )
|
68
|
+
Vocab::Extractor::Base.should_receive( :current_plurals ).and_return( {} )
|
69
|
+
Vocab::Extractor::Base.should_receive( :previous_plurals ).and_return( {} )
|
70
|
+
Vocab::Extractor::Base.should_receive( :write_diff ).with( { 1 => 5, 3 => 4 }, {}, @diff_path )
|
71
|
+
Vocab::Extractor::Base.should_receive( :write_full ).with( current, {}, @full_path )
|
56
72
|
Vocab::Extractor::Base.should_receive( :mkdir_examples )
|
73
|
+
Vocab::Extractor::Base.should_receive( :update_settings )
|
57
74
|
Vocab::Extractor::Base.extract( @diff_path, @full_path )
|
58
75
|
end
|
59
76
|
|
@@ -68,22 +85,22 @@ describe "Vocab::Extractor::Base" do
|
|
68
85
|
|
69
86
|
it "returns the contents of a file from a specific git version" do
|
70
87
|
contents = Vocab::Extractor::Base.previous_file( @path, 'a19f7c5c28c1158792a966c0d2153a04490dd35e' )
|
71
|
-
|
88
|
+
contents.should eql_file( 'spec/data/android/previous.xml' )
|
72
89
|
|
73
90
|
contents = Vocab::Extractor::Base.previous_file( @path, '0533bcd9a304cd6e74d6a56959dbcabd57b2f1b9' )
|
74
|
-
|
91
|
+
contents.should eql_file( 'spec/data/android/current.xml' )
|
75
92
|
end
|
76
93
|
|
77
94
|
it "returns the correct contents when a full path is specified" do
|
78
95
|
contents = Vocab::Extractor::Base.previous_file( "#{vocab_root}/#{@path}", 'a19f7c5c28c1158792a966c0d2153a04490dd35e' )
|
79
|
-
|
96
|
+
contents.should eql_file( 'spec/data/android/previous.xml' )
|
80
97
|
end
|
81
98
|
|
82
99
|
it "returns the contents of a file when in a subdir of the git directory" do
|
83
100
|
Dir.chdir( "spec" )
|
84
101
|
@path = "data/android/locales/strings.xml"
|
85
102
|
contents = Vocab::Extractor::Base.previous_file( @path, 'a19f7c5c28c1158792a966c0d2153a04490dd35e' )
|
86
|
-
|
103
|
+
contents.should eql_file( 'spec/data/android/previous.xml' )
|
87
104
|
end
|
88
105
|
|
89
106
|
end
|
@@ -7,7 +7,7 @@ describe "Vocab::Extractor::Rails" do
|
|
7
7
|
it 'writes the full en translation to a file' do
|
8
8
|
translation = { :en => { :full => 'translation' } }
|
9
9
|
path = "#{vocab_root}/spec/tmp/en.full.yml"
|
10
|
-
Vocab::Extractor::Rails.write_full( translation, path )
|
10
|
+
Vocab::Extractor::Rails.write_full( translation, {}, path )
|
11
11
|
YAML.load_file( path ).should eql( translation )
|
12
12
|
File.delete( path )
|
13
13
|
end
|
@@ -27,7 +27,7 @@ describe "Vocab::Extractor::Rails" do
|
|
27
27
|
|
28
28
|
end
|
29
29
|
|
30
|
-
describe "
|
30
|
+
describe "previous_strings" do
|
31
31
|
|
32
32
|
before( :each ) do
|
33
33
|
@last_translation = '5ab8cf4d081d7ba1d5f020118dd00c3ea2d0437a'
|
@@ -37,7 +37,7 @@ describe "Vocab::Extractor::Rails" do
|
|
37
37
|
end
|
38
38
|
|
39
39
|
it "creates a hash of the english translation strings from the last translation" do
|
40
|
-
actual = Vocab::Extractor::Rails.
|
40
|
+
actual = Vocab::Extractor::Rails.previous_strings( @locales_root )
|
41
41
|
expected = { :"en.models.product.id_36.description" =>"Polarized and lazer resistant",
|
42
42
|
:"en.marketing.banner" =>"This product is so good",
|
43
43
|
:"en.models.product.id_36.name" =>"This nested value has changed",
|
@@ -54,13 +54,13 @@ describe "Vocab::Extractor::Rails" do
|
|
54
54
|
it 'creates a tmp folder if one does not exist' do
|
55
55
|
dir = "#{vocab_root}/tmp/last_translation"
|
56
56
|
FileUtils.rm_rf( "#{vocab_root}/tmp/last_translation" )
|
57
|
-
Vocab::Extractor::Rails.
|
57
|
+
Vocab::Extractor::Rails.previous_strings( @locales_root )
|
58
58
|
File.exists?( dir ).should be_true
|
59
59
|
end
|
60
60
|
|
61
61
|
end
|
62
62
|
|
63
|
-
describe "
|
63
|
+
describe "current_strings" do
|
64
64
|
|
65
65
|
before( :each ) do
|
66
66
|
Dir.chdir( vocab_root )
|
@@ -68,19 +68,21 @@ describe "Vocab::Extractor::Rails" do
|
|
68
68
|
end
|
69
69
|
|
70
70
|
it "creates a hash of the english translation strings currently in the config" do
|
71
|
-
actual = Vocab::Extractor::Rails.
|
72
|
-
expected = {
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
78
|
-
|
79
|
-
|
80
|
-
|
81
|
-
|
82
|
-
|
83
|
-
|
71
|
+
actual = Vocab::Extractor::Rails.current_strings( @locales_root )
|
72
|
+
expected = {:"en.marketing.banner"=>"This product is so good",
|
73
|
+
:"en.dashboard.chart"=>"This value has changed",
|
74
|
+
:"en.dashboard.details"=>"This key/value has been added",
|
75
|
+
:"en.menu.first"=>"First menu item",
|
76
|
+
:"en.menu.second"=>"Second menu item",
|
77
|
+
:"en.not_in_es"=>"This key not in spanish",
|
78
|
+
:"en.users.one"=>"1 user",
|
79
|
+
:"en.users.other"=>"%{count} users",
|
80
|
+
:"en.models.product.id_125.description"=>"Green with megawatts",
|
81
|
+
:"en.models.product.id_125.name"=>"Lazer",
|
82
|
+
:"en.models.product.id_36.description"=>"Polarized and lazer resistant",
|
83
|
+
:"en.models.product.id_36.name"=>"This nested value has changed",
|
84
|
+
:"en.models.product.id_55.description"=>"A new nested description",
|
85
|
+
:"en.models.product.id_55.name"=>"a new nested name"}
|
84
86
|
actual.should eql( expected )
|
85
87
|
end
|
86
88
|
|
@@ -94,8 +96,9 @@ describe "Vocab::Extractor::Rails" do
|
|
94
96
|
end
|
95
97
|
|
96
98
|
it "extracts the strings that need to be translated into a yml file" do
|
97
|
-
Vocab::Extractor::Rails.should_receive( :
|
98
|
-
Vocab::Extractor::Rails.should_receive( :
|
99
|
+
Vocab::Extractor::Rails.should_receive( :current_strings ).and_return( { :en => { 1 => 5, 3 => 4 } } )
|
100
|
+
Vocab::Extractor::Rails.should_receive( :previous_strings ).and_return( { :en => { 1 => 2 } } )
|
101
|
+
Vocab.settings.should_receive( :update_translation )
|
99
102
|
Vocab::Extractor::Rails.extract( @diff_path, @full_path )
|
100
103
|
YAML.load_file( @diff_path ).should == { :en => { 1 => 5, 3 => 4 } }
|
101
104
|
|
data/spec/merger/android_spec.rb
CHANGED
@@ -27,7 +27,6 @@ describe "Vocab::Merger::Android" do
|
|
27
27
|
describe "merge" do
|
28
28
|
|
29
29
|
before( :each ) do
|
30
|
-
Vocab.settings.should_receive( :update_translation )
|
31
30
|
@merger = Vocab::Merger::Android.new( @merge_dir, @update_dir )
|
32
31
|
@merger.merge
|
33
32
|
end
|
@@ -47,66 +46,120 @@ describe "Vocab::Merger::Android" do
|
|
47
46
|
@file = "#{@merge_dir}/values-es/strings.xml"
|
48
47
|
@merger = Vocab::Merger::Android.new( @merge_dir, @update_dir )
|
49
48
|
@merger.merge_file( @file )
|
50
|
-
@merged = Vocab::Translator::Android.hash_from_xml( @file )
|
51
49
|
end
|
52
50
|
|
53
|
-
|
54
|
-
@merged['pd_app_name'].should eql( 'el Panel para padres bien' )
|
55
|
-
end
|
51
|
+
context "strings" do
|
56
52
|
|
57
|
-
|
58
|
-
|
59
|
-
|
53
|
+
before( :each ) do
|
54
|
+
@merged = Vocab::Translator::Android.hash_from_xml( @file )
|
55
|
+
end
|
60
56
|
|
61
|
-
|
62
|
-
|
63
|
-
|
57
|
+
it "merges updated android translations" do
|
58
|
+
@merged['pd_app_name'].should eql( 'el Panel para padres bien' )
|
59
|
+
end
|
64
60
|
|
65
|
-
|
66
|
-
|
67
|
-
|
61
|
+
it "integrates new android translations" do
|
62
|
+
@merged['cancel'].should eql( 'Cancelar' )
|
63
|
+
end
|
64
|
+
|
65
|
+
it "properly encodes html entities" do
|
66
|
+
@merged['delete'].should eql( "La función Child Lock" )
|
67
|
+
end
|
68
|
+
|
69
|
+
it "ignores key accidentally introduced by the translators into android translations" do
|
70
|
+
@merged['translator_cruft'].should be( nil )
|
71
|
+
end
|
72
|
+
|
73
|
+
it "retains unchanged android translations" do
|
74
|
+
@merged['app_name'].should eql( 'Modo Niños' )
|
75
|
+
end
|
76
|
+
|
77
|
+
it 'does not include keys where there is no translation' do
|
78
|
+
@merged['not_in_es'].should be( nil )
|
79
|
+
end
|
68
80
|
|
69
|
-
it "retains unchanged android translations" do
|
70
|
-
@merged['app_name'].should eql( 'Modo Niños' )
|
71
81
|
end
|
72
82
|
|
73
|
-
|
74
|
-
|
83
|
+
context "strings" do
|
84
|
+
|
85
|
+
before( :each ) do
|
86
|
+
@merged = Vocab::Translator::Android.plurals_from_xml( @file )
|
87
|
+
end
|
88
|
+
|
89
|
+
it "includes plurals where an item is updated" do
|
90
|
+
@merged[ 'fish_count' ].should eql( { 'one' => '1 pescado', 'many' => '%d peces' } )
|
91
|
+
end
|
92
|
+
|
93
|
+
it "includes new plural definition" do
|
94
|
+
@merged[ 'user_count' ].should eql( {"one"=>"1 usuario", "many"=>"%d usuarios"} )
|
95
|
+
end
|
75
96
|
end
|
76
97
|
|
77
98
|
end
|
78
99
|
|
79
|
-
describe '
|
100
|
+
describe 'string_keys' do
|
80
101
|
|
81
102
|
it 'fetches the english keys' do
|
82
103
|
merger = Vocab::Merger::Android.new( @merge_dir )
|
83
104
|
keys = ["app_name", "delete", "cancel", "app_current", "not_in_es", "pd_app_name"]
|
84
|
-
merger.
|
105
|
+
merger.string_keys.should =~ keys
|
106
|
+
end
|
107
|
+
|
108
|
+
end
|
109
|
+
|
110
|
+
describe 'plural_keys' do
|
111
|
+
|
112
|
+
it 'fetches the plural definition keys from the english file' do
|
113
|
+
merger = Vocab::Merger::Android.new( @merge_dir )
|
114
|
+
keys = ["fish_count", "user_count"]
|
115
|
+
merger.plural_keys.should =~ keys
|
85
116
|
end
|
86
117
|
|
87
118
|
end
|
88
119
|
|
89
|
-
describe '
|
120
|
+
describe 'current_strings_for_locale' do
|
90
121
|
|
91
122
|
it 'returns hash of the current translations that match a locale file' do
|
92
123
|
merger = Vocab::Merger::Android.new( @merge_dir )
|
93
124
|
expected = { "app_name" =>"Modo Niños",
|
94
125
|
"app_current"=>"actual",
|
95
126
|
"pd_app_name"=>"el Panel para padres"}
|
96
|
-
merger.
|
127
|
+
merger.current_strings_for_locale( "#{@merge_dir}/values-es/strings.xml" ).should == expected
|
97
128
|
end
|
98
129
|
|
99
130
|
end
|
100
131
|
|
101
|
-
describe '
|
132
|
+
describe 'update_strings_for_locale' do
|
102
133
|
|
103
134
|
it 'returns hash of the updates that match a locale file' do
|
104
135
|
merger = Vocab::Merger::Android.new( @merge_dir, @update_dir )
|
105
136
|
expected = { 'cancel' => 'Cancelar',
|
106
137
|
'delete' => "La función Child Lock",
|
107
138
|
'pd_app_name' => 'el Panel para padres bien',
|
108
|
-
'translator_cruft' => 'Malo'
|
109
|
-
|
139
|
+
'translator_cruft' => 'Malo',
|
140
|
+
'apostrophe' => "Translator\\'s evil apostrophe don\\'t care" }
|
141
|
+
merger.update_strings_for_locale( "#{@merge_dir}/values-es/strings.xml" ).should == expected
|
142
|
+
end
|
143
|
+
|
144
|
+
end
|
145
|
+
|
146
|
+
describe 'current_plurals_for_locale' do
|
147
|
+
|
148
|
+
it 'returns hash of the current translations that match a locale file' do
|
149
|
+
merger = Vocab::Merger::Android.new( @merge_dir )
|
150
|
+
expected = { "fish_count" => { "one" => "1 pescado", "many" => "%d peces" } }
|
151
|
+
merger.current_plurals_for_locale( "#{@merge_dir}/values-es/strings.xml" ).should == expected
|
152
|
+
end
|
153
|
+
|
154
|
+
end
|
155
|
+
|
156
|
+
describe 'update_plurals_for_locale' do
|
157
|
+
|
158
|
+
it 'returns hash of the updates that match a locale file' do
|
159
|
+
merger = Vocab::Merger::Android.new( @merge_dir, @update_dir )
|
160
|
+
expected = { "user_count" => { "one" => "1 usuario", "many" => "%d usuarios" },
|
161
|
+
"fish_count" => { "one" => "1 pescado", "many" => "%d peces" } }
|
162
|
+
merger.update_plurals_for_locale( "#{@merge_dir}/values-es/strings.xml" ).should == expected
|
110
163
|
end
|
111
164
|
|
112
165
|
end
|
data/spec/merger/base_spec.rb
CHANGED
data/spec/merger/rails_spec.rb
CHANGED
@@ -89,7 +89,6 @@ describe "Vocab::Merger::Rails" do
|
|
89
89
|
before( :each ) do
|
90
90
|
init_merge_dir
|
91
91
|
@update_dir = "#{vocab_root}/spec/data/rails/translations"
|
92
|
-
Vocab.settings.should_receive( :update_translation )
|
93
92
|
@merger = Vocab::Merger::Rails.new( @merge_dir, @update_dir )
|
94
93
|
@merger.merge
|
95
94
|
end
|
@@ -116,7 +115,7 @@ describe "Vocab::Merger::Rails" do
|
|
116
115
|
it "returns the keys that should be in a file" do
|
117
116
|
path = "#{vocab_root}/spec/data/rails/locales/es.yml"
|
118
117
|
actual = Vocab::Merger::Rails.keys_for_file( path )
|
119
|
-
expected = [:"dashboard.details", :"menu.first", :"dashboard.chart", :"menu.second", :"marketing.banner", :"not_in_es"]
|
118
|
+
expected = [:"dashboard.details", :"menu.first", :"dashboard.chart", :"menu.second", :"marketing.banner", :"not_in_es", :"users.one", :"users.other"]
|
120
119
|
actual.each { |key| expected.should include( key ) }
|
121
120
|
actual.size.should eql( expected.size )
|
122
121
|
end
|
data/spec/spec_helper.rb
CHANGED
@@ -6,6 +6,13 @@ require "vocab"
|
|
6
6
|
require "support/matchers"
|
7
7
|
require "support/shared"
|
8
8
|
|
9
|
+
require 'simplecov'
|
10
|
+
|
11
|
+
SimpleCov.start do
|
12
|
+
coverage_dir 'coverage'
|
13
|
+
add_filter "/spec/"
|
14
|
+
end
|
15
|
+
|
9
16
|
Vocab.ui.silent = true
|
10
17
|
|
11
18
|
RSpec.configure do |config|
|
@@ -16,8 +23,4 @@ def vocab_root
|
|
16
23
|
return File.expand_path( '../..', __FILE__ )
|
17
24
|
end
|
18
25
|
|
19
|
-
|
20
|
-
@tmp = File.open( "#{vocab_root}/#{path}.tmp","wb") { |io| io.write actual }
|
21
|
-
@expected = File.open("#{vocab_root}/#{path}","rb") {|io| io.read }
|
22
|
-
actual.chomp.strip.should eql( @expected.chomp.strip )
|
23
|
-
end
|
26
|
+
|
data/spec/support/matchers.rb
CHANGED
@@ -10,4 +10,29 @@ module Vocab
|
|
10
10
|
#end
|
11
11
|
end
|
12
12
|
end
|
13
|
+
end
|
14
|
+
|
15
|
+
# Matcher to compare an in-memory string with a ground truth file.
|
16
|
+
# Exports the actual value as a .tmp file as a side effect.
|
17
|
+
|
18
|
+
RSpec::Matchers.define :eql_file do |expected|
|
19
|
+
|
20
|
+
description do
|
21
|
+
"match the contents of #{expected}"
|
22
|
+
end
|
23
|
+
|
24
|
+
match do |actual|
|
25
|
+
File.open( "#{vocab_root}/#{expected}.tmp","wb" ) { |io| io.write actual }
|
26
|
+
slurped = File.open( "#{vocab_root}/#{expected}","rb" ) {|io| io.read }
|
27
|
+
actual == slurped
|
28
|
+
end
|
29
|
+
|
30
|
+
failure_message_for_should do |actual|
|
31
|
+
"expected that #{actual} would match the contents of #{expected}"
|
32
|
+
end
|
33
|
+
|
34
|
+
failure_message_for_should_not do |actual|
|
35
|
+
"expected that #{actual} would not match the contents of #{expected}"
|
36
|
+
end
|
37
|
+
|
13
38
|
end
|
@@ -2,12 +2,12 @@ require "spec_helper"
|
|
2
2
|
|
3
3
|
describe 'Vocab::Translator::Android' do
|
4
4
|
|
5
|
-
describe '
|
5
|
+
describe 'string_keys' do
|
6
6
|
|
7
7
|
it 'returns the english keys for a locales dir' do
|
8
8
|
locales_dir = "#{vocab_root}/spec/data/android/locales"
|
9
9
|
expected = ["app_name", "delete", "cancel", "app_current", "not_in_es", "pd_app_name"]
|
10
|
-
Vocab::Translator::Android.
|
10
|
+
Vocab::Translator::Android.string_keys( locales_dir ).should =~ expected
|
11
11
|
end
|
12
12
|
|
13
13
|
end
|
@@ -21,4 +21,47 @@ describe 'Vocab::Translator::Android' do
|
|
21
21
|
|
22
22
|
end
|
23
23
|
|
24
|
+
describe 'write' do
|
25
|
+
|
26
|
+
it 'writes the strings to a xml file' do
|
27
|
+
strings = { 'app_name' => 'Kid Mode',
|
28
|
+
'pd_app_name' => 'Parent Dashboard',
|
29
|
+
'delete' => "La función Child Lock",
|
30
|
+
'apostrophe' => "Translator\\'s evil apostrophe don\\'t care"}
|
31
|
+
plurals = {}
|
32
|
+
path = "#{vocab_root}/spec/tmp/strings.xml"
|
33
|
+
Vocab::Translator::Android.write( strings, plurals, path )
|
34
|
+
strings = File.open( path ) { |f| f.read }
|
35
|
+
strings.should eql_file( "spec/data/android/write.xml" )
|
36
|
+
File.delete( path )
|
37
|
+
end
|
38
|
+
|
39
|
+
it 'writes the strings and plurals to a xml file' do
|
40
|
+
strings = { 'app_name' => 'Kid Mode',
|
41
|
+
'pd_app_name' => 'Parent Dashboard',
|
42
|
+
'delete' => "La función Child Lock" }
|
43
|
+
plurals = { 'users' => { 'one' => '1 user',
|
44
|
+
'other' => '2 users' },
|
45
|
+
'deer' => { 'one' => '1 deer',
|
46
|
+
'other' => '2 deer' } }
|
47
|
+
path = "#{vocab_root}/spec/tmp/strings.xml"
|
48
|
+
Vocab::Translator::Android.write( strings, plurals, path )
|
49
|
+
strings = File.open( path ) { |f| f.read }
|
50
|
+
strings.should eql_file( "spec/data/android/write_plurals.xml" )
|
51
|
+
File.delete( path )
|
52
|
+
end
|
53
|
+
|
54
|
+
end
|
55
|
+
|
56
|
+
describe 'android resource special cases' do
|
57
|
+
|
58
|
+
it "escapes apostrophes to be compatible with android resources" do
|
59
|
+
hash = Vocab::Translator::Android.hash_from_xml( "#{vocab_root}/spec/data/android/translations/values-es/es-string-file.xml" )
|
60
|
+
hash['apostrophe'].should eql( %q[Translator\'s evil apostrophe don\'t care] )
|
61
|
+
|
62
|
+
|
63
|
+
end
|
64
|
+
|
65
|
+
end
|
66
|
+
|
24
67
|
end
|