interpret 0.2.0 → 0.2.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.
Files changed (54) hide show
  1. data/.rspec +1 -0
  2. data/.travis.yml +14 -0
  3. data/README.md +2 -0
  4. data/app/controllers/interpret/base_controller.rb +10 -14
  5. data/app/controllers/interpret/missing_translations_controller.rb +41 -10
  6. data/app/controllers/interpret/search_controller.rb +15 -3
  7. data/app/controllers/interpret/tools_controller.rb +2 -2
  8. data/app/controllers/interpret/translations_controller.rb +15 -12
  9. data/app/models/interpret/ability.rb +9 -0
  10. data/app/models/interpret/translation.rb +38 -3
  11. data/app/views/interpret/missing_translations/blank.html.erb +35 -0
  12. data/app/views/interpret/missing_translations/index.html.erb +25 -14
  13. data/app/views/interpret/missing_translations/stale.html.erb +43 -0
  14. data/app/views/interpret/missing_translations/unused.html.erb +27 -0
  15. data/app/views/interpret/tools/index.html.erb +15 -25
  16. data/app/views/interpret/translations/_listing.html.erb +3 -15
  17. data/app/views/interpret/translations/index.html.erb +3 -0
  18. data/app/views/layouts/interpret.html.erb +26 -6
  19. data/config/environment.rb +0 -0
  20. data/config/routes.rb +4 -1
  21. data/interpret.gemspec +4 -1
  22. data/lib/generators/interpret/templates/migration.rb +1 -1
  23. data/lib/interpret.rb +23 -2
  24. data/lib/interpret/controller_filter.rb +0 -10
  25. data/lib/interpret/helpers.rb +2 -2
  26. data/lib/interpret/version.rb +1 -1
  27. data/public/javascripts/interpret.js +0 -3
  28. data/public/stylesheets/interpret_style.css +0 -6
  29. data/spec/integration/missing_translations_spec.rb +61 -0
  30. data/spec/integration/search_spec.rb +88 -0
  31. data/spec/integration/stale_translations_spec.rb +28 -0
  32. data/spec/integration/tools_spec.rb +86 -0
  33. data/spec/integration/translations_spec.rb +26 -0
  34. data/spec/models/translation_spec.rb +58 -25
  35. data/spec/observers/expiration_observer_spec.rb +2 -0
  36. data/spec/spec_helper.rb +3 -15
  37. data/spec/support/selenium_db_hack.rb +19 -0
  38. data/spec/support/utils.rb +89 -0
  39. data/test_app/Gemfile +1 -1
  40. data/test_app/app/controllers/application_controller.rb +2 -4
  41. data/test_app/app/models/interpret_ability.rb +7 -0
  42. data/test_app/app/models/user.rb +0 -3
  43. data/test_app/app/views/layouts/application.html.erb +4 -7
  44. data/test_app/config/initializers/interpret.rb +2 -2
  45. data/test_app/config/initializers/rack_patch.rb +13 -0
  46. data/test_app/config/locales/es.yml +1 -1
  47. data/test_app/db/migrate/20110219173536_create_users.rb +0 -2
  48. data/test_app/db/migrate/{20110219143622_interpret_create_translations.rb → 20111021100344_interpret_create_translations.rb} +1 -1
  49. data/test_app/db/schema.rb +2 -3
  50. data/test_app/db/seeds.rb +1 -1
  51. data/test_app/public/javascripts/interpret.js +0 -3
  52. data/test_app/public/stylesheets/interpret_style.css +0 -6
  53. metadata +122 -119
  54. data/spec/database_helpers.rb +0 -15
@@ -0,0 +1,28 @@
1
+ # encoding: utf-8
2
+ require "spec_helper"
3
+
4
+ describe "Stale translations" do
5
+ before(:all) { User.create! }
6
+ before { load_integration_data }
7
+
8
+ it "should show me nothing when I'm in english language" do
9
+ visit interpret_stale_translations_path(:en)
10
+ page.should have_content("There can't be stale translations for the main language")
11
+ end
12
+
13
+ it "should show me the recently modified translations in english", :js => true do
14
+ visit interpret_root_path(:en)
15
+ change_translation("table#results tbody tr:first", "New comments text")
16
+
17
+ visit interpret_stale_translations_path(:es)
18
+ page.all("table#stale_translations tbody tr").size.should == 1
19
+ end
20
+
21
+ it "should not show anything if I update a 'es' translation", :js => true do
22
+ visit interpret_root_path(:es)
23
+ change_translation("table#results tbody tr:first", "New comments text")
24
+
25
+ visit interpret_stale_translations_path(:es)
26
+ page.all("table#stale_translations tbody tr").size.should == 0
27
+ end
28
+ end
@@ -0,0 +1,86 @@
1
+ # encoding: utf-8
2
+ require "spec_helper"
3
+
4
+ describe "Tools" do
5
+ before(:all) { User.create! }
6
+ before { load_integration_data }
7
+
8
+ describe "Download" do
9
+ it "should be able to download a .yml file for the current language" do
10
+ visit interpret_tools_path(:en)
11
+ page.should have_button("Download")
12
+
13
+ page.click_button "Download"
14
+ page.response_headers["Content-Type"].should == "text/plain"
15
+ end
16
+
17
+ it "should get a yaml file for the current language" do
18
+ visit interpret_tools_path(:en)
19
+ page.should have_button("Download")
20
+
21
+ page.click_button "Download"
22
+ hash = YAML.load(page.source)
23
+ hash.first.first.should == "en"
24
+ end
25
+
26
+ it "should get a yaml file with all the correct translations" do
27
+ visit interpret_tools_path(:en)
28
+ page.should have_button("Download")
29
+
30
+ page.click_button "Download"
31
+ hash = YAML.load(page.source)
32
+ source_hash = YAML.load(en_yml)
33
+
34
+ hash.sort.should == source_hash.sort
35
+ end
36
+ end
37
+
38
+ describe "Import" do
39
+ it "should be able to import a file" do
40
+ visit interpret_tools_path(:en)
41
+ path = create_tmp_file("""
42
+ en:
43
+ someky: somevalue
44
+ """)
45
+ page.attach_file("file", path)
46
+ page.click_button "Upload"
47
+ page.should have_content("Import successfully done.")
48
+ end
49
+
50
+ it "should not allow to be used with another language" do
51
+ path = create_tmp_file("""
52
+ it:
53
+ someky: somevalue
54
+ """)
55
+ visit interpret_tools_path(:en)
56
+ page.attach_file("file", path)
57
+ page.click_button "Upload"
58
+ page.should have_content("the language doesn't match")
59
+ end
60
+
61
+ it "should update existing translations" do
62
+ path = create_tmp_file(import_en_yml)
63
+ visit interpret_tools_path(:en)
64
+
65
+ page.attach_file("file", path)
66
+ page.click_button "Upload"
67
+
68
+ visit interpret_root_path(:en)
69
+ within("table#results tbody tr:nth-child(4)") do
70
+ page.should have_content("A new printer phrase")
71
+ end
72
+ end
73
+
74
+ it "should create non existant translations" do
75
+ path = create_tmp_file(import_en_yml)
76
+ visit interpret_tools_path(:en)
77
+
78
+ page.attach_file("file", path)
79
+ page.click_button "Upload"
80
+
81
+ visit interpret_root_path(:en)
82
+ page.should have_content("new_stuff")
83
+ page.should have_content("Something brand new")
84
+ end
85
+ end
86
+ end
@@ -0,0 +1,26 @@
1
+ # encoding: utf-8
2
+ require "spec_helper"
3
+
4
+ describe "Translations" do
5
+ before(:all) { User.create! }
6
+ before { load_integration_data }
7
+
8
+ it "should let me edit a translation", :js => true do
9
+ visit interpret_root_path(:en)
10
+
11
+ # We need this to identify the translation we want to change
12
+ bip_id = ""
13
+ within("table#results tbody tr:first") do
14
+ bip_id = page.all("span.best_in_place").first[:id]
15
+ end
16
+ bip_id = bip_id.scan(/translation_\d+/).first
17
+
18
+ bip_area bip_id, :value, "New value"
19
+
20
+
21
+ visit interpret_root_path(:en)
22
+ within("table#results tbody tr:first") do
23
+ page.should have_content("New value")
24
+ end
25
+ end
26
+ end
@@ -38,6 +38,16 @@ es:
38
38
  """
39
39
  }
40
40
 
41
+ let(:es_2_yml) {"""
42
+ es:
43
+ p1: Hola mundo!
44
+ """}
45
+
46
+ let(:pt_2_yml) {"""
47
+ pt:
48
+ p1: Olá mundo
49
+ """}
50
+
41
51
  let(:new_en_yml) {"""
42
52
  en:
43
53
  p1: Hello modified world! This new translation should not be copied into database
@@ -80,27 +90,6 @@ es:
80
90
  """
81
91
  }
82
92
 
83
- # Convert a locale file into database translations
84
- def file2db(string_file)
85
- def parse_hash(dict, locale, prefix = "")
86
- res = []
87
- dict.keys.each do |x|
88
- if dict[x].kind_of?(Hash)
89
- res += parse_hash(dict[x], locale, "#{prefix}#{x}.")
90
- else
91
- res << Interpret::Translation.create!(:locale => locale, :key => "#{prefix}#{x}", :value => dict[x])
92
- end
93
- end
94
- res
95
- end
96
-
97
- hash = YAML.load string_file
98
- lang = hash.keys.first
99
- Interpret::Translation.transaction do
100
- parse_hash(hash.first[1], lang).map{|x| x.save!}
101
- end
102
- end
103
-
104
93
  before do
105
94
  Interpret::Translation.delete_all
106
95
  I18n.stub!(:default_locale).and_return('en')
@@ -235,16 +224,17 @@ es:
235
224
  trans.value.should == "Hello modified world! This new translation should not be copied into database"
236
225
  end
237
226
 
238
- it "should not create new keys" do
227
+ it "should create new keys" do
239
228
  Interpret::Translation.delete_all
240
229
  file2db(en_yml)
241
- howm_before = Interpret::Translation.locale('en').count
230
+ Interpret::Translation.locale('en').count
242
231
 
243
232
  @file.stub!(:content_type).and_return("text/plain")
244
233
  Interpret::Translation.import(@file)
245
234
 
246
- howm_after = Interpret::Translation.locale('en').count
247
- howm_before.should == howm_after
235
+ howm = Interpret::Translation.locale('en').count
236
+ # It should create 2 new translations, from 8 to 10
237
+ howm.should == 10
248
238
  end
249
239
 
250
240
  it "should not touch translations not present in the file" do
@@ -269,4 +259,47 @@ es:
269
259
  Interpret::Translation.export(es_trans).should == YAML.load(es_yml)
270
260
  end
271
261
  end
262
+
263
+ describe "set stale" do
264
+ it "should mark sibling translations as stale after editing the one of the app's default_language" do
265
+ Interpret::Translation.delete_all
266
+ file2db(en_yml)
267
+ file2db(es_2_yml)
268
+ file2db(pt_2_yml)
269
+
270
+ tr = Interpret::Translation.locale("en").find_by_key("p1")
271
+ tr.value = "New value"
272
+ tr.save!
273
+
274
+ Interpret::Translation.locale("es").find_by_key("p1").stale?.should be_true
275
+ Interpret::Translation.locale("pt").find_by_key("p1").stale?.should be_true
276
+ end
277
+
278
+ it "should not mark as stale the translation that you're editing when it's in the app's default_language" do
279
+ Interpret::Translation.delete_all
280
+ file2db(en_yml)
281
+ file2db(es_2_yml)
282
+
283
+ tr = Interpret::Translation.locale("en").find_by_key("p1")
284
+ tr.value = "New value"
285
+ tr.save!
286
+
287
+ tr.stale?.should be_false
288
+ end
289
+
290
+ it "should not mark sibling translations as stale after editing some that is not in the app's default_language" do
291
+ Interpret::Translation.delete_all
292
+ file2db(en_yml)
293
+ file2db(es_2_yml)
294
+ file2db(pt_2_yml)
295
+
296
+ tr = Interpret::Translation.locale("es").find_by_key("p1")
297
+ tr.value = "New value"
298
+ tr.save!
299
+
300
+ Interpret::Translation.locale("en").find_by_key("p1").stale?.should be_false
301
+ Interpret::Translation.locale("es").find_by_key("p1").stale?.should be_false
302
+ Interpret::Translation.locale("pt").find_by_key("p1").stale?.should be_false
303
+ end
304
+ end
272
305
  end
@@ -10,8 +10,10 @@ describe Interpret::ExpirationObserver do
10
10
  it "should call run_expiration on observer" do
11
11
  backend = mock("A backend")
12
12
  backend.should_receive(:"reload!").once
13
+ old = Interpret.backend
13
14
  Interpret.backend = backend
14
15
  Interpret::Translation.create! :locale => "en", :key => "en.hello", :value => "Hello world"
16
+ Interpret.backend = old
15
17
  end
16
18
  end
17
19
 
data/spec/spec_helper.rb CHANGED
@@ -2,21 +2,8 @@
2
2
  ENV["RAILS_ENV"] = "test"
3
3
 
4
4
  require File.expand_path('../../test_app/config/environment', __FILE__)
5
- require "rails/test_help"
6
5
  require "rspec/rails"
7
- require "database_helpers"
8
-
9
- ActionMailer::Base.delivery_method = :test
10
- ActionMailer::Base.perform_deliveries = true
11
- ActionMailer::Base.default_url_options[:host] = "test.com"
12
-
13
- Rails.backtrace_cleaner.remove_silencers!
14
-
15
- include DatabaseHelpers
16
- # Run any available migration
17
- puts 'Setting up database...'
18
- drop_all_tables
19
- migrate_database
6
+ require 'yaml'
20
7
 
21
8
  # Load support files
22
9
  Dir["#{File.dirname(__FILE__)}/support/**/*.rb"].each{|f| require f}
@@ -27,7 +14,8 @@ RSpec.configure do |config|
27
14
  require 'rspec/expectations'
28
15
 
29
16
  config.include RSpec::Matchers
30
- config.include DatabaseHelpers
17
+ config.include BestInPlace::TestHelpers
18
+ config.use_transactional_fixtures = true
31
19
 
32
20
  # == Mock Framework
33
21
  config.mock_with :rspec
@@ -0,0 +1,19 @@
1
+ # Avoids using the database_cleaner gem and allow us to have faster
2
+ # integration specs with selenium. See https://github.com/jnicklas/capybara at
3
+ # transactional fixtures section.
4
+
5
+
6
+ class ActiveRecord::Base
7
+ mattr_accessor :shared_connection
8
+ @@shared_connection = nil
9
+
10
+ def self.connection
11
+ @@shared_connection || retrieve_connection
12
+ end
13
+ end
14
+
15
+ # Forces all threads to share the same connection. This works on
16
+ # Capybara because it starts the web server in a thread.
17
+ ActiveRecord::Base.shared_connection = ActiveRecord::Base.connection
18
+
19
+
@@ -0,0 +1,89 @@
1
+ # encoding: utf-8
2
+ # Convert a locale file into database translations
3
+ def file2db(string_file)
4
+ def parse_hash(dict, locale, prefix = "")
5
+ res = []
6
+ dict.keys.each do |x|
7
+ if dict[x].kind_of?(Hash)
8
+ res += parse_hash(dict[x], locale, "#{prefix}#{x}.")
9
+ else
10
+ res << Interpret::Translation.create!(:locale => locale, :key => "#{prefix}#{x}", :value => dict[x])
11
+ end
12
+ end
13
+ res
14
+ end
15
+
16
+ hash = YAML.load string_file
17
+ lang = hash.keys.first
18
+ parse_hash(hash.first[1], lang).map{|x| x.save!}
19
+ end
20
+
21
+ def en_yml
22
+ """
23
+ en:
24
+ printer: Printer Friendly
25
+ comments: Comments
26
+ read_more: Read more
27
+ phrase: This is a rare phrase with non ascii chars
28
+
29
+ section1:
30
+ printer: Another printer
31
+
32
+ blacklist:
33
+ black_p1: A forbidden phrase
34
+
35
+ missings:
36
+ p1: Missing one
37
+ p2: Missing two
38
+ black: A one blacklisted
39
+ """
40
+ end
41
+
42
+ def import_en_yml
43
+ """
44
+ en:
45
+ printer: A new printer phrase
46
+ new_stuff: Something brand new
47
+
48
+ section1:
49
+ printer: Other change
50
+ """
51
+ end
52
+
53
+ def load_integration_data
54
+ #en_yml =
55
+ es_yml = """
56
+ es:
57
+ printer: Para imprimir
58
+ comments: Comentarios
59
+ read_more: Leer mas
60
+ phrase: Esta és una extraña frase con carácteres no ascii
61
+
62
+ section1:
63
+ printer: Otra impresora
64
+
65
+ blacklist:
66
+ black_p1: Una frase prohibida
67
+ """
68
+
69
+ file2db en_yml
70
+ file2db es_yml
71
+ end
72
+
73
+ def change_translation(scope, new_value)
74
+ bip_id = ""
75
+ within(scope) do
76
+ bip_id = page.all("span.best_in_place").first[:id]
77
+ end
78
+ bip_id = bip_id.scan(/translation_\d+/).first
79
+
80
+ bip_area bip_id, :value, new_value
81
+ end
82
+
83
+ def create_tmp_file(content)
84
+ file = Tempfile.new("interpret_test")
85
+ file.write(content)
86
+ path = file.path
87
+ file.close
88
+ path
89
+ end
data/test_app/Gemfile CHANGED
@@ -6,7 +6,7 @@ gem 'capistrano'
6
6
 
7
7
  group :development, :test do
8
8
  gem 'sqlite3-ruby', :require => 'sqlite3'
9
- gem 'ruby-debug'
10
9
  end
11
10
 
12
11
  gem 'interpret', :path => ".."
12
+ gem 'mysql2', "~> 0.2.7"
@@ -5,13 +5,11 @@ class ApplicationController < ActionController::Base
5
5
  before_filter :set_locale
6
6
 
7
7
  def current_user
8
- session[:user_id] ? User.find(session[:user_id]) : User.where(:admin => true).first
8
+ session[:user_id] ? User.find(session[:user_id]) : User.first
9
9
  end
10
10
 
11
11
  def set_current_user
12
- if params[:admin]
13
- session[:user_id] = params[:admin] == "true" ? User.where(:admin => true).first : User.where(:admin => false).first
14
- end
12
+ session[:user_id] = User.first
15
13
  end
16
14
 
17
15
  def toggle_edition_mode
@@ -0,0 +1,7 @@
1
+ class InterpretAbility
2
+ include CanCan::Ability
3
+
4
+ def initialize(user)
5
+ can :manage, :all
6
+ end
7
+ end