From ed701490f875c7e250d0ef2370826f974547908c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Fri, 15 Jan 2021 11:24:19 +0100 Subject: [PATCH 01/92] Fix #41 ArgumentError: comparison of Pathname with String failed --- lib/translation_io/config.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/translation_io/config.rb b/lib/translation_io/config.rb index 6c21a53..19eca14 100644 --- a/lib/translation_io/config.rb +++ b/lib/translation_io/config.rb @@ -124,7 +124,7 @@ def pot_path end def yaml_file_paths - I18n.load_path.select do |p| + I18n.load_path.collect(&:to_s).uniq.select do |p| File.exist?(p) && (File.extname(p) == '.yml' || File.extname(p) == '.yaml') end end From afce75b90f06d78d8dc8d5e597e7206c27772a0b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Sun, 17 Jan 2021 15:00:43 +0100 Subject: [PATCH 02/92] Bump version to 1.23 + Changelog --- CHANGELOG.md | 6 ++++++ translation.gemspec | 2 +- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 2d5f0cf..4e8a7ec 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## [v1.23](https://github.com/translation/rails/releases/tag/v1.23) (2021-01-17) + +#### Fixes (bugs & defects): + + * Fix `ArgumentError: comparison of Pathname with String failed` if `I18n.load_path` contains a Pathname instead of a String ([#41](https://github.com/translation/rails/issues/41)). Thanks @11mdlow! + ## [v1.22](https://github.com/translation/rails/releases/tag/v1.22) (2020-07-27) #### Fixes (bugs & defects): diff --git a/translation.gemspec b/translation.gemspec index 2176221..fbb029e 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.22' + s.version = '1.23' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] From 5064a407f80b243ccb84d6b83799e4507292c0f7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 15 Feb 2021 17:29:02 +0100 Subject: [PATCH 03/92] Chapter on frontend localization --- README.md | 66 +++++++++++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 62 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index da3dd6a..1dd7020 100644 --- a/README.md +++ b/README.md @@ -39,6 +39,7 @@ Table of contents * [Change the current locale](#change-the-current-locale) * [Globally](#globally) * [Locally](#locally) + * [Frontend Localization](#frontend-localization) * [Continuous Integration](#continuous-integration) * [Advanced Configuration Options](#advanced-configuration-options) * [Disable GetText or YAML](#disable-gettext-or-yaml) @@ -267,7 +268,8 @@ end The `set_locale` code is [here](https://github.com/translation/rails/blob/master/lib/translation_io/controller.rb#L3), feel free to override it with your own locale management. -Don't forget to define your available locales with [I18n.available_locales](http://guides.rubyonrails.org/i18n.html#setup-the-rails-application-for-internationalization). +Don't forget to define your available locales with +[I18n.available_locales](http://guides.rubyonrails.org/i18n.html#setup-the-rails-application-for-internationalization). More examples here: https://translation.io/blog/set-current-locale-in-your-rails-app @@ -283,17 +285,73 @@ You can call it several times in the same page if you want to switch between lan More examples here: https://translation.io/blog/rails-i18n-with-locale +## Frontend Localization + +This gem is also able to cover frontend localization (React, Vue, ...). + +There are several ways to pass the translation strings from the backend +to the frontend: JavaScript serialization, `data-` HTML attributes, JSON files etc. + +The easiest strategy when dealing with React/Vue would be to pass the corresponding +translations as props when mounting the components. + +Assuming that you use [reactjs/react-rails](https://github.com/reactjs/react-rails), +it would look like this if you want to use [I18n (YAML)](#i18n-yaml) syntax: + +```erb +<%= react_component('MyComponent", { + :user_id => current_user.id, + :i18n => YAML.load_file("config/locales/#{I18n.locale}.yml")[I18n.locale.to_s]["my_component"] +}) %> +``` + +And `en.yml` looks like this: + +```yaml +en: + my_component: + your_name: Your name + title: Title +``` + +You can also directly use the [GetText](#gettext) syntax: + +```erb +<%= react_component('MyComponent", { + :user_id => current_user.id, + :i18n => { + :your_name => _('Your name'), + :title => _('Title') + } +}) %> +``` + +In both case, in your React component, you can simply call +`this.props.i18n.yourName` and it will be localized with the current locale. + +**Notes:** + + * You can also structure the i18n props with different levels of depth and pass the subtree as props to each of your sub-components. + * It works great with server-side rendering too! + ## Continuous Integration -If you want fresh translations in your Continuous Integration workflow, you may find yourself calling `bundle exec rake translation:sync` very frequently. +If you want fresh translations in your Continuous Integration workflow, you may +find yourself calling `bundle exec rake translation:sync` very frequently. -Since this task can't be concurrently executed (we have a [mutex](https://en.wikipedia.org/wiki/Mutual_exclusion) strategy with a queue but it returns an error under heavy load), we implemented this threadsafe readonly task: +Since this task can't be concurrently executed +(we have a [mutex](https://en.wikipedia.org/wiki/Mutual_exclusion) strategy with +a queue but it returns an error under heavy load), we implemented this +threadsafe readonly task: ```bash $ bundle exec rake translation:sync_readonly ``` -This task will prevent your CI to fail and still provide new translations. But be aware that it won't send new keys from your code to Translation.io so you still need to call `bundle exec rake translation:sync` at some point during development. +This task will prevent your CI to fail and still provide new translations. But +be aware that it won't send new keys from your code to Translation.io so you +still need to call `bundle exec rake translation:sync` at some point during +development. ## Advanced Configuration Options From 1c615304911c3eddf1ae01f568e6763e36d3ad90 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 15 Feb 2021 17:36:30 +0100 Subject: [PATCH 04/92] Improve README (frontend localization) --- README.md | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index 1dd7020..3cb4dc5 100644 --- a/README.md +++ b/README.md @@ -305,7 +305,7 @@ it would look like this if you want to use [I18n (YAML)](#i18n-yaml) syntax: }) %> ``` -And `en.yml` looks like this: +Your `en.yml` should look like this: ```yaml en: @@ -327,12 +327,12 @@ You can also directly use the [GetText](#gettext) syntax: ``` In both case, in your React component, you can simply call -`this.props.i18n.yourName` and it will be localized with the current locale. +`this.props.i18n.yourName` and your text will be localized with the current locale. **Notes:** - * You can also structure the i18n props with different levels of depth and pass the subtree as props to each of your sub-components. - * It works great with server-side rendering too! + * You can also structure the i18n props with multiple levels of depth and pass the subtree as props to each of your sub-components. + * It also works great with server-side rendering of your components (`:prerender => true`). ## Continuous Integration From cf82e9f101f4f1991d3259f4b970d5348513bf18 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 10 Mar 2021 14:44:56 +0100 Subject: [PATCH 05/92] Try "dist: focal" and jruby-head to fix error between jruby and lowest.gemfile --- .travis.yml | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index 9959231..12a8e21 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,3 +1,5 @@ +dist: focal + env: global: - CC_TEST_REPORTER_ID=1ec0e82ac7a13e879f71d36abbf09c7c691c71ec58a8b7f74beef6086e3b65db @@ -15,7 +17,7 @@ rvm: - 2.6 - 2.7 - 3.0 - - jruby + - jruby-head gemfile: - gemfiles/lowest.gemfile From 5bfb87df4d7d8936ba3544115e173e4f864cc7a0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 10 Mar 2021 14:56:01 +0100 Subject: [PATCH 06/92] Use bionic to try to be compatible with Ruby < 2.4 (openssl issue) --- .travis.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index 12a8e21..ede7b9e 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,4 +1,4 @@ -dist: focal +dist: bionic env: global: From 2e40507a5c197a71cdd9c22e85379a6ed7c4152e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 10 Mar 2021 15:21:03 +0100 Subject: [PATCH 07/92] Remove 2.1 (not compatible in Travis on Bionic), add "ruby --version" to debug more easily (what version is jruby-head !?) --- .travis.yml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index ede7b9e..a9f1754 100644 --- a/.travis.yml +++ b/.travis.yml @@ -8,8 +8,8 @@ language: ruby # 2.0 has only one test not passing # (TranslationIO::YAMLConversion#get_yaml_data_from_flat_translations works with weird not-escaped code) +# 2.1 passes but is not compatible with Travis on Bionic rvm: - - 2.1 - 2.2 - 2.3 - 2.4 @@ -46,6 +46,7 @@ before_script: - curl -L https://codeclimate.com/downloads/test-reporter/test-reporter-latest-linux-amd64 > ./cc-test-reporter - chmod +x ./cc-test-reporter - ./cc-test-reporter before-build + - ruby --version script: - bundle _1.17.3_ exec rspec From cbd4e10f20f4580d16154d7cea202edafbc9bcc5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 10 Mar 2021 15:52:41 +0100 Subject: [PATCH 08/92] Remove failing test on travis with JRuby (but works in dev) --- .travis.yml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.travis.yml b/.travis.yml index a9f1754..b7e8d20 100644 --- a/.travis.yml +++ b/.travis.yml @@ -30,6 +30,8 @@ matrix: gemfile: gemfiles/lowest.gemfile - rvm: 3.0 gemfile: gemfiles/lowest.gemfile + - rvm: jruby-head + gemfile: gemfiles/lowest.gemfile # Work on dev but error "no such file to load -- racc/info" on Travis (jruby 9.3.0.0-SNAPSHOT) sudo: false From 35ad1b3a2054652f0c91cd71101f9781aa2a0752 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 24 Mar 2021 16:27:20 +0100 Subject: [PATCH 09/92] Fix "custom language" alphanumeric => alphabetic --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 3cb4dc5..eb73bef 100644 --- a/README.md +++ b/README.md @@ -216,7 +216,7 @@ Its structure should be like: "#{existing_language_code}-#{custom_text}" ``` -where `custom_text` can only contain alphanumeric characters and `-`. +where `custom_text` can only contain alphabetic characters and `-`. Examples: `en-microsoft` or `fr-BE-custom`. From 0ab57899f629b789a1b258a6425622d1ad43aced Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Fri, 7 May 2021 15:21:33 +0200 Subject: [PATCH 10/92] Remove special code that added missing locales was corrected on Translation.io-side with correct Lower/Upper Sorbian codes: https://translation.io/docs/languages --- lib/translation.rb | 7 ------- 1 file changed, 7 deletions(-) diff --git a/lib/translation.rb b/lib/translation.rb index b2fb887..051e888 100644 --- a/lib/translation.rb +++ b/lib/translation.rb @@ -33,7 +33,6 @@ def configure(&block) if !@config.disable_gettext require_gettext_dependencies - add_missing_locales add_parser_for_erb_source_formats(@config.erb_source_formats) if Rails.env.development? @@ -71,12 +70,6 @@ def require_gettext_dependencies require 'gettext/tools/xgettext' end - # Missing languages from Locale that are in Translation.io - def add_missing_locales - Locale::Info.three_languages['wee'] = Locale::Info::Language.new('', 'wee', 'I', 'L', 'Lower Sorbian') - Locale::Info.three_languages['wen'] = Locale::Info::Language.new('', 'wen', 'I', 'L', 'Upper Sorbian') - end - def add_parser_for_erb_source_formats(new_erb_formats) existing_extensions = GetText::ErbParser.instance_variable_get("@config")[:extnames] new_extensions = new_erb_formats.collect { |ext| ".#{ext}" } From 972734c8f7ff2d10fc2fde998b416870eed7db71 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Tue, 15 Jun 2021 18:34:44 +0200 Subject: [PATCH 11/92] Better warnings for wrong locales in config file + specs, bump Rspec, Force version of GetText to avoid dependency to external online request: https://github.com/ruby-gettext/gettext/issues/85#issuecomment-861462382 --- lib/translation_io/client/base_operation.rb | 32 ++++++++ lib/translation_io/client/init_operation.rb | 2 + lib/translation_io/client/sync_operation.rb | 2 + spec/spec_helper.rb | 8 +- .../translation/client/base_operation_spec.rb | 80 +++++++++++++++++-- translation.gemspec | 5 +- 6 files changed, 121 insertions(+), 8 deletions(-) diff --git a/lib/translation_io/client/base_operation.rb b/lib/translation_io/client/base_operation.rb index ce533c1..11edc0a 100644 --- a/lib/translation_io/client/base_operation.rb +++ b/lib/translation_io/client/base_operation.rb @@ -17,6 +17,38 @@ def initialize(client) private + def warn_wrong_locales(source_locale, target_locales) + if target_locales.uniq != target_locales + duplicate_locale = target_locales.detect { |locale| target_locales.count(locale) > 1 } + + puts + puts "----------" + puts "Your `config.target_locales` has a duplicate locale (#{duplicate_locale})." + puts "Please clean your configuration file and execute this command again." + puts "----------" + exit(true) + end + + if target_locales.include?(source_locale) + puts + puts "----------" + puts "The `config.source_locale` (#{source_locale}) can't be included in the `config.target_locales`." + puts "If you want to customize your source locale, check this link: https://github.com/translation/rails#custom-languages" + puts "Please clean your configuration file and execute this command again." + puts "----------" + exit(true) + end + + if target_locales.empty? + puts + puts "----------" + puts "Your `config.target_locales` is empty." + puts "Please clean your configuration file and execute this command again." + puts "----------" + exit(true) + end + end + def self.perform_request(uri, params) begin params.merge!({ diff --git a/lib/translation_io/client/init_operation.rb b/lib/translation_io/client/init_operation.rb index 8c21e77..d0e2d79 100644 --- a/lib/translation_io/client/init_operation.rb +++ b/lib/translation_io/client/init_operation.rb @@ -19,6 +19,8 @@ def run yaml_locales_path = config.yaml_locales_path yaml_file_paths = config.yaml_file_paths + warn_wrong_locales(source_locale, target_locales) + if !config.disable_gettext BaseOperation::DumpMarkupGettextKeysStep.new(haml_source_files, :haml).run BaseOperation::DumpMarkupGettextKeysStep.new(slim_source_files, :slim).run diff --git a/lib/translation_io/client/sync_operation.rb b/lib/translation_io/client/sync_operation.rb index d32702f..5b6c6ea 100644 --- a/lib/translation_io/client/sync_operation.rb +++ b/lib/translation_io/client/sync_operation.rb @@ -22,6 +22,8 @@ def run(options = {}) yaml_locales_path = config.yaml_locales_path yaml_file_paths = config.yaml_file_paths + warn_wrong_locales(source_locale, target_locales) + if !config.disable_yaml ApplyYamlSourceEditsStep.new(yaml_file_paths, source_locale).run(params) end diff --git a/spec/spec_helper.rb b/spec/spec_helper.rb index 4fe2930..9d45724 100644 --- a/spec/spec_helper.rb +++ b/spec/spec_helper.rb @@ -6,7 +6,13 @@ require 'translation' RSpec.configure do |config| - config.expect_with(:rspec) { |c| c.syntax = [:should, :expect] } + config.expect_with :rspec do |c| + c.syntax = [:should, :expect] + end + + config.mock_with :rspec do |c| + c.syntax = [:should, :expect] + end config.before :each do TranslationIO.configure do |config| diff --git a/spec/translation/client/base_operation_spec.rb b/spec/translation/client/base_operation_spec.rb index 09ecc04..00582e0 100644 --- a/spec/translation/client/base_operation_spec.rb +++ b/spec/translation/client/base_operation_spec.rb @@ -1,16 +1,86 @@ require 'spec_helper' describe TranslationIO::Client::BaseOperation do - before :each do + it 'has default values initialized' do TranslationIO.configure do |config| config.target_locales = ['fr', 'nl'] end - @client = TranslationIO::Client.new('4242', 'bidule.com/api') - @operation = TranslationIO::Client::BaseOperation.new(@client) + client = TranslationIO::Client.new('4242', 'bidule.com/api') + operation = TranslationIO::Client::BaseOperation.new(client) + + operation.client.should == client end - it 'has default values initialized' do - @operation.client.should == @client + describe 'Locale inconsistency warnings' do + it 'triggers error if config.target_locales has duplicate locale' do + TranslationIO.configure do |config| + config.source_locale = :en + config.target_locales = [:fr, :nl, :fr] + end + + client = TranslationIO::Client.new('4242', 'https://translation.io') + + randomOperation = [ + TranslationIO::Client::InitOperation, + TranslationIO::Client::SyncOperation + ].sample + + expect { randomOperation.new(client).run}.to raise_error(SystemExit).and output(< "https://github.com/translation/rails" } - s.add_dependency 'gettext', '~> 3.2', '>= 3.2.5' + s.add_dependency 'gettext', '~> 3.2', '>= 3.2.5', '<= 3.3.7' # 3.3.8 adds many dependencies and depends on an online resource, we don't want it + # more here: https://github.com/ruby-gettext/gettext/issues/85#issuecomment-861462382 s.add_development_dependency 'rake', '~> 12.0' s.add_development_dependency 'simplecov', '~> 0.11' - s.add_development_dependency 'rspec', '~> 2.14' + s.add_development_dependency 'rspec', '~> 3.0' s.add_development_dependency 'rails', '>= 4.1' end From 994f01c3fddd7556cf580173057ac871e9fafac2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Tue, 15 Jun 2021 18:42:08 +0200 Subject: [PATCH 12/92] Trigger travis build after migration --- translation.gemspec | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/translation.gemspec b/translation.gemspec index 122a2c1..f4a2a1a 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -19,7 +19,7 @@ Gem::Specification.new do |s| } s.add_dependency 'gettext', '~> 3.2', '>= 3.2.5', '<= 3.3.7' # 3.3.8 adds many dependencies and depends on an online resource, we don't want it - # more here: https://github.com/ruby-gettext/gettext/issues/85#issuecomment-861462382 + # More here: https://github.com/ruby-gettext/gettext/issues/85#issuecomment-861462382 s.add_development_dependency 'rake', '~> 12.0' s.add_development_dependency 'simplecov', '~> 0.11' From 8eb2e3fa710da527b3b66b2b7443ad7f58c6ab65 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Tue, 15 Jun 2021 18:52:32 +0200 Subject: [PATCH 13/92] Bump rspec lowest dependency --- gemfiles/lowest.gemfile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gemfiles/lowest.gemfile b/gemfiles/lowest.gemfile index 120fb08..f8daf21 100644 --- a/gemfiles/lowest.gemfile +++ b/gemfiles/lowest.gemfile @@ -2,7 +2,7 @@ source "https://rubygems.org" gem 'gettext', '3.2.5' gem 'simplecov', '0.12' -gem 'rspec', '2.14' +gem 'rspec', '3.0' gem 'rails', '4.1' gemspec :path => "../" From 490d1932e3a38502687520976e8f262847b42298 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Tue, 15 Jun 2021 19:02:05 +0200 Subject: [PATCH 14/92] Fix lowest rspec dependency --- gemfiles/lowest.gemfile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gemfiles/lowest.gemfile b/gemfiles/lowest.gemfile index f8daf21..68ab8de 100644 --- a/gemfiles/lowest.gemfile +++ b/gemfiles/lowest.gemfile @@ -2,7 +2,7 @@ source "https://rubygems.org" gem 'gettext', '3.2.5' gem 'simplecov', '0.12' -gem 'rspec', '3.0' +gem 'rspec', '3.1' gem 'rails', '4.1' gemspec :path => "../" From 0ea3294224166c6dbdd7f12941a1130acdfa7fce Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Tue, 15 Jun 2021 19:27:53 +0200 Subject: [PATCH 15/92] Update travis-ci.org to travis-ci.com build image --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index eb73bef..7bdb490 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # [Translation.io](https://translation.io) client for Ruby on Rails [![Software License](https://img.shields.io/badge/license-MIT-brightgreen.svg?style=flat-square)](LICENSE) -[![Build Status](https://travis-ci.org/translation/rails.svg?branch=master)](https://travis-ci.org/translation/rails) +[![Build Status](https://travis-ci.com/translation/rails.svg?branch=master)](https://travis-ci.org/translation/rails) [![Test Coverage](https://codeclimate.com/github/translation/rails/badges/coverage.svg)](https://codeclimate.com/github/translation/rails/test_coverage) [![Gem Version](https://badgen.net/rubygems/v/translation)](https://rubygems.org/gems/translation) [![Downloads](https://img.shields.io/gem/dt/translation.svg)](https://rubygems.org/gems/translation) From a59ed68e23d5364138a85542e51f5bf33466d503 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Tue, 15 Jun 2021 19:51:04 +0200 Subject: [PATCH 16/92] Bump version to 1.24 + changelog --- CHANGELOG.md | 10 ++++++++++ README.md | 2 +- translation.gemspec | 2 +- 3 files changed, 12 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 4e8a7ec..ef8b1a7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,15 @@ # Changelog +## [v1.24](https://github.com/translation/rails/releases/tag/v1.24) (2021-06-15) + +#### Fixes (bugs & defects): + + * Force max version of GetText (3.3.7) to avoid dependency to external online request (see [here](https://github.com/ruby-gettext/gettext/issues/85#issuecomment-861462382) for discussion). + +#### New features: + + * Warnings when trying to init/sync with duplicate or empty `target_locales` in the configuration file. + ## [v1.23](https://github.com/translation/rails/releases/tag/v1.23) (2021-01-17) #### Fixes (bugs & defects): diff --git a/README.md b/README.md index 7bdb490..c2e37e9 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # [Translation.io](https://translation.io) client for Ruby on Rails [![Software License](https://img.shields.io/badge/license-MIT-brightgreen.svg?style=flat-square)](LICENSE) -[![Build Status](https://travis-ci.com/translation/rails.svg?branch=master)](https://travis-ci.org/translation/rails) +[![Build Status](https://travis-ci.com/translation/rails.svg?branch=master)](https://travis-ci.com/translation/rails) [![Test Coverage](https://codeclimate.com/github/translation/rails/badges/coverage.svg)](https://codeclimate.com/github/translation/rails/test_coverage) [![Gem Version](https://badgen.net/rubygems/v/translation)](https://rubygems.org/gems/translation) [![Downloads](https://img.shields.io/gem/dt/translation.svg)](https://rubygems.org/gems/translation) diff --git a/translation.gemspec b/translation.gemspec index f4a2a1a..dd60ed5 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.23' + s.version = '1.24' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] From 6e5403483b15a5b998428691c5a8e1b9ec7179a6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 14 Jul 2021 16:44:42 +0200 Subject: [PATCH 17/92] Fix issue with empty values in localization.xx.yml files that were removed when `config.yaml_remove_empty_keys = true` + Bump version to 1.25 --- CHANGELOG.md | 6 ++++ .../save_special_yaml_files_step.rb | 4 ++- lib/translation_io/yaml_conversion.rb | 11 +++++-- spec/translation/yaml_conversion_spec.rb | 31 +++++++++++++++++++ translation.gemspec | 2 +- 5 files changed, 49 insertions(+), 5 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index ef8b1a7..7db3ccc 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## [v1.25](https://github.com/translation/rails/releases/tag/v1.25) (2021-07-14) + +#### Fixes (bugs & defects): + + * Don't remove empty keys in `localization.xx.yml` files when `config.yaml_remove_empty_keys = true`, they may be useful for delimiters, etc. + ## [v1.24](https://github.com/translation/rails/releases/tag/v1.24) (2021-06-15) #### Fixes (bugs & defects): diff --git a/lib/translation_io/client/base_operation/save_special_yaml_files_step.rb b/lib/translation_io/client/base_operation/save_special_yaml_files_step.rb index 68303a8..2db9231 100644 --- a/lib/translation_io/client/base_operation/save_special_yaml_files_step.rb +++ b/lib/translation_io/client/base_operation/save_special_yaml_files_step.rb @@ -35,7 +35,9 @@ def run YamlEntry.from_locale?(key, target_locale) && !YamlEntry.ignored?(key) end - yaml_data = YAMLConversion.get_yaml_data_from_flat_translations(target_flat_special_translations) + yaml_data = YAMLConversion.get_yaml_data_from_flat_translations(target_flat_special_translations, + :force_keep_empty_keys => true # We want to keep empty keys from localization.xx.yml files (sometimes needed for delimiters!) + ) params["yaml_data_#{target_locale}"] = yaml_data diff --git a/lib/translation_io/yaml_conversion.rb b/lib/translation_io/yaml_conversion.rb index f667745..0215fd3 100644 --- a/lib/translation_io/yaml_conversion.rb +++ b/lib/translation_io/yaml_conversion.rb @@ -35,9 +35,14 @@ def get_flat_translations_for_yaml_data(yaml_data) end end - def get_yaml_data_from_flat_translations(flat_translations) - remove_empty_keys = TranslationIO.config.yaml_remove_empty_keys - translations = FlatHash.to_hash(flat_translations, remove_empty_keys) + def get_yaml_data_from_flat_translations(flat_translations, force_keep_empty_keys: false) + if force_keep_empty_keys + remove_empty_keys = false + else + remove_empty_keys = TranslationIO.config.yaml_remove_empty_keys + end + + translations = FlatHash.to_hash(flat_translations, remove_empty_keys) if TranslationIO.config.yaml_line_width data = translations.to_yaml(:line_width => TranslationIO.config.yaml_line_width) diff --git a/spec/translation/yaml_conversion_spec.rb b/spec/translation/yaml_conversion_spec.rb index 1d1fb64..aef8d42 100644 --- a/spec/translation/yaml_conversion_spec.rb +++ b/spec/translation/yaml_conversion_spec.rb @@ -187,6 +187,37 @@ result.should eql(expected_result) end + it 'does not drops empty keys if special "force_keep_empty_keys" parameter is passed' do + TranslationIO.config.yaml_remove_empty_keys = true + + flat_data = { + "en.hello" => "Hello world", + "en.main.menu.stuff" => "This is stuff", + "en.bye" => "Good bye world", + "en.empty" => nil, + "en.empty_string" => '', + "en.space" => ' ' + } + + result = subject.get_yaml_data_from_flat_translations(flat_data, { + :force_keep_empty_keys => true + }) + + expected_result = <<-EOS +--- +en: + hello: Hello world + main: + menu: + stuff: This is stuff + bye: Good bye world + empty: + empty_string: '' + space: " " +EOS + result.should eql(expected_result) + end + it 'works with weird not-escaped code' do flat_data = { "en.architects.seo.image" => "<%= AController::Base.h.path('a/b.png') %>", diff --git a/translation.gemspec b/translation.gemspec index dd60ed5..84a95f1 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.24' + s.version = '1.25' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] From 215f87bb9daf6d9374c3a55b10587d5080831f46 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 14 Jul 2021 16:59:46 +0200 Subject: [PATCH 18/92] use double splat operator (**) to pass hash as keyword argument (for Ruby 3.0) --- .../client/base_operation/save_special_yaml_files_step.rb | 4 ++-- spec/translation/yaml_conversion_spec.rb | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/lib/translation_io/client/base_operation/save_special_yaml_files_step.rb b/lib/translation_io/client/base_operation/save_special_yaml_files_step.rb index 2db9231..d541ff2 100644 --- a/lib/translation_io/client/base_operation/save_special_yaml_files_step.rb +++ b/lib/translation_io/client/base_operation/save_special_yaml_files_step.rb @@ -35,9 +35,9 @@ def run YamlEntry.from_locale?(key, target_locale) && !YamlEntry.ignored?(key) end - yaml_data = YAMLConversion.get_yaml_data_from_flat_translations(target_flat_special_translations, + yaml_data = YAMLConversion.get_yaml_data_from_flat_translations(target_flat_special_translations, **{ :force_keep_empty_keys => true # We want to keep empty keys from localization.xx.yml files (sometimes needed for delimiters!) - ) + }) params["yaml_data_#{target_locale}"] = yaml_data diff --git a/spec/translation/yaml_conversion_spec.rb b/spec/translation/yaml_conversion_spec.rb index aef8d42..a678163 100644 --- a/spec/translation/yaml_conversion_spec.rb +++ b/spec/translation/yaml_conversion_spec.rb @@ -199,7 +199,7 @@ "en.space" => ' ' } - result = subject.get_yaml_data_from_flat_translations(flat_data, { + result = subject.get_yaml_data_from_flat_translations(flat_data, **{ :force_keep_empty_keys => true }) From c3cdfb2b115143b1e6f1617ff4ec177c0ea77c90 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 14 Jul 2021 17:06:46 +0200 Subject: [PATCH 19/92] bump version to 1.26 --- CHANGELOG.md | 6 ++++++ translation.gemspec | 2 +- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 7db3ccc..dc766f6 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## [v1.26](https://github.com/translation/rails/releases/tag/v1.26) (2021-07-14) + +#### Fixes (bugs & defects): + + * Fix issue with Ruby 3.0 and release v1.25 (that is now yanked!) + ## [v1.25](https://github.com/translation/rails/releases/tag/v1.25) (2021-07-14) #### Fixes (bugs & defects): diff --git a/translation.gemspec b/translation.gemspec index 84a95f1..36e6950 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.25' + s.version = '1.26' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] From f6ddb7f069b0108a3af16eaafd45a36be576f21b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 14 Jul 2021 17:09:48 +0200 Subject: [PATCH 20/92] missing word changelog --- CHANGELOG.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index dc766f6..ab38faa 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,7 +4,7 @@ #### Fixes (bugs & defects): - * Fix issue with Ruby 3.0 and release v1.25 (that is now yanked!) + * Fix syntax issue with Ruby 3.0 and release v1.25 (that is now yanked!) ## [v1.25](https://github.com/translation/rails/releases/tag/v1.25) (2021-07-14) From ea68764c784ba0038d55c3a64acc00c022993597 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 8 Sep 2021 17:01:04 +0200 Subject: [PATCH 21/92] Small update README --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index c2e37e9..c25192a 100644 --- a/README.md +++ b/README.md @@ -6,7 +6,7 @@ [![Gem Version](https://badgen.net/rubygems/v/translation)](https://rubygems.org/gems/translation) [![Downloads](https://img.shields.io/gem/dt/translation.svg)](https://rubygems.org/gems/translation) -Add this gem to localize your Ruby on Rails application. +Add this gem to localize your **Ruby on Rails** application. Use the official Rails syntax (with [YAML](#i18n-yaml) files) or use the [GetText](#gettext) syntax. From a449a7e6b95d32632870fe0aaa4d364d882dedac Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 8 Sep 2021 17:06:05 +0200 Subject: [PATCH 22/92] Newlines in README --- README.md | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index c25192a..6a527e6 100644 --- a/README.md +++ b/README.md @@ -299,10 +299,12 @@ Assuming that you use [reactjs/react-rails](https://github.com/reactjs/react-rai it would look like this if you want to use [I18n (YAML)](#i18n-yaml) syntax: ```erb -<%= react_component('MyComponent", { +<%= +react_component('MyComponent", { :user_id => current_user.id, :i18n => YAML.load_file("config/locales/#{I18n.locale}.yml")[I18n.locale.to_s]["my_component"] -}) %> +}) +%> ``` Your `en.yml` should look like this: @@ -317,13 +319,15 @@ en: You can also directly use the [GetText](#gettext) syntax: ```erb -<%= react_component('MyComponent", { +<%= +react_component('MyComponent", { :user_id => current_user.id, :i18n => { :your_name => _('Your name'), :title => _('Title') } -}) %> +}) +%> ``` In both case, in your React component, you can simply call From 5346f1e7c2e8872abe3873ac43f1d5f0afbf5b93 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 27 Sep 2021 14:48:46 +0200 Subject: [PATCH 23/92] Better pointers for frontend localization --- README.md | 32 +++++++++++++++++++++++++------- 1 file changed, 25 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index 6a527e6..ac50d39 100644 --- a/README.md +++ b/README.md @@ -55,7 +55,7 @@ Table of contents * [List of clients for Translation.io](#list-of-clients-for-translationio) * [Ruby on Rails (Ruby)](#ruby-on-rails-ruby) * [Laravel (PHP)](#laravel-php) - * [React and React-Intl (JavaScript)](#react-and-react-intl-javascript) + * [React, React Native and JavaScript](#react-react-native-and-javasript) * [Others](#others) * [License](#license) @@ -145,7 +145,7 @@ end $ bundle exec rake translation:init ``` -If you later need to add/remove target languages, please read our +If you need to add or remove languages in the future, please read our [documentation](https://translation.io/blog/adding-target-languages) about that. ## Usage @@ -178,7 +178,8 @@ $ bundle exec rake translation:sync_and_purge As the name says, this operation will also perform a sync at the same time. -Warning: all keys that are not present in the current branch will be **permanently deleted from Translation.io**. +Warning: all keys that are not present in the current local branch +will be **permanently deleted from Translation.io**. ## Manage Languages @@ -287,6 +288,8 @@ More examples here: https://translation.io/blog/rails-i18n-with-locale ## Frontend Localization +### With this Gem + This gem is also able to cover frontend localization (React, Vue, ...). There are several ways to pass the translation strings from the backend @@ -338,6 +341,18 @@ In both case, in your React component, you can simply call * You can also structure the i18n props with multiple levels of depth and pass the subtree as props to each of your sub-components. * It also works great with server-side rendering of your components (`:prerender => true`). +### With our React & JavaScript official package + +As Translation.io is directly integrated in the great +[Lingui](https://lingui.js.org/) internationalization framework, +you can also consider frontend localization as a completely different +localization project. + +Please read more about this on: + + * [https://translation.io/lingui](https://translation.io/lingui) + * [https://github.com/translation/lingui](https://github.com/translation/lingui) + ## Continuous Integration If you want fresh translations in your Continuous Integration workflow, you may @@ -601,12 +616,15 @@ Officially Supported on [https://translation.io/laravel](https://translation.io/ Credits: [@armandsar](https://github.com/armandsar), [@michaelhoste](https://github.com/michaelhoste) -### React and React-Intl (JavaScript) +### React, React Native and JavaScript + +Officially Supported on [https://translation.io/lingui](https://translation.io/lingui) - * GitHub: https://github.com/deecewan/translation-io - * NPM: https://www.npmjs.com/package/translation-io +Translation.io is directly integrated in the great +[Lingui](https://lingui.js.org/) internationalization project. -Credits: [@deecewan](https://github.com/deecewan) + * GitHub: https://github.com/translation/lingui + * NPM: https://www.npmjs.com/package/@translation/lingui ### Others From eff4e77dd3b7e2bce9cc2654e24046edfde4d78d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 27 Sep 2021 14:52:55 +0200 Subject: [PATCH 24/92] Small improvements --- README.md | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index ac50d39..5494f66 100644 --- a/README.md +++ b/README.md @@ -40,6 +40,8 @@ Table of contents * [Globally](#globally) * [Locally](#locally) * [Frontend Localization](#frontend-localization) + * [With this Gem](#with-this-gem) + * [With our official React & JavaScript package](#with-our-official-react--javascript-package) * [Continuous Integration](#continuous-integration) * [Advanced Configuration Options](#advanced-configuration-options) * [Disable GetText or YAML](#disable-gettext-or-yaml) @@ -341,7 +343,7 @@ In both case, in your React component, you can simply call * You can also structure the i18n props with multiple levels of depth and pass the subtree as props to each of your sub-components. * It also works great with server-side rendering of your components (`:prerender => true`). -### With our React & JavaScript official package +### With our official React & JavaScript package As Translation.io is directly integrated in the great [Lingui](https://lingui.js.org/) internationalization framework, @@ -350,8 +352,8 @@ localization project. Please read more about this on: - * [https://translation.io/lingui](https://translation.io/lingui) - * [https://github.com/translation/lingui](https://github.com/translation/lingui) + * [Translation.io/lingui](https://translation.io/lingui) + * [github.com/translation/lingui](https://github.com/translation/lingui) ## Continuous Integration From ce74575974a0deaacf6ec9771b4ccb545edc4148 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 27 Sep 2021 14:56:28 +0200 Subject: [PATCH 25/92] Small improvement --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 5494f66..bbb66a3 100644 --- a/README.md +++ b/README.md @@ -352,8 +352,8 @@ localization project. Please read more about this on: - * [Translation.io/lingui](https://translation.io/lingui) - * [github.com/translation/lingui](https://github.com/translation/lingui) + * Website: [translation.io/lingui](https://translation.io/lingui) + * GitHub page: [github.com/translation/lingui](https://github.com/translation/lingui) ## Continuous Integration From 028ab933bd7cf436a7bf31c55d33068d7fdd7226 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 27 Sep 2021 14:57:39 +0200 Subject: [PATCH 26/92] wording --- README.md | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index bbb66a3..0b58dc9 100644 --- a/README.md +++ b/README.md @@ -40,8 +40,8 @@ Table of contents * [Globally](#globally) * [Locally](#locally) * [Frontend Localization](#frontend-localization) - * [With this Gem](#with-this-gem) - * [With our official React & JavaScript package](#with-our-official-react--javascript-package) + * [Using this Gem](#using-this-gem) + * [Using our official React & JavaScript package](#using-our-official-react--javascript-package) * [Continuous Integration](#continuous-integration) * [Advanced Configuration Options](#advanced-configuration-options) * [Disable GetText or YAML](#disable-gettext-or-yaml) @@ -290,7 +290,7 @@ More examples here: https://translation.io/blog/rails-i18n-with-locale ## Frontend Localization -### With this Gem +### Using this Gem This gem is also able to cover frontend localization (React, Vue, ...). @@ -343,7 +343,7 @@ In both case, in your React component, you can simply call * You can also structure the i18n props with multiple levels of depth and pass the subtree as props to each of your sub-components. * It also works great with server-side rendering of your components (`:prerender => true`). -### With our official React & JavaScript package +### Using our official React & JavaScript package As Translation.io is directly integrated in the great [Lingui](https://lingui.js.org/) internationalization framework, From 3595ec095cc094cd174f56aca02322a345e3bef9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 27 Sep 2021 14:58:22 +0200 Subject: [PATCH 27/92] fix links --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 0b58dc9..1a58941 100644 --- a/README.md +++ b/README.md @@ -352,8 +352,8 @@ localization project. Please read more about this on: - * Website: [translation.io/lingui](https://translation.io/lingui) - * GitHub page: [github.com/translation/lingui](https://github.com/translation/lingui) + * Website: [https://translation.io/lingui](https://translation.io/lingui) + * GitHub page: [https://github.com/translation/lingui](https://github.com/translation/lingui) ## Continuous Integration From c4c9eeb224bf2802cce1c1f625f1ac6ee3d159e3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 27 Sep 2021 15:05:23 +0200 Subject: [PATCH 28/92] Fix bad anchor --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 1a58941..116abe5 100644 --- a/README.md +++ b/README.md @@ -57,7 +57,7 @@ Table of contents * [List of clients for Translation.io](#list-of-clients-for-translationio) * [Ruby on Rails (Ruby)](#ruby-on-rails-ruby) * [Laravel (PHP)](#laravel-php) - * [React, React Native and JavaScript](#react-react-native-and-javasript) + * [React, React Native and JavaScript](#react-react-native-and-javascript) * [Others](#others) * [License](#license) From db4f6ef5599f6a9612e9314c0d0d11a3e91d3cab Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 6 Oct 2021 15:10:16 +0200 Subject: [PATCH 29/92] Improve symbol/string consistency of `source_locale` and `target_locales` --- lib/translation_io/client/init_operation.rb | 4 ++-- lib/translation_io/client/sync_operation.rb | 4 ++-- spec/translation/client/base_operation_spec.rb | 10 +++++----- spec/translation/config_spec.rb | 8 ++++---- 4 files changed, 13 insertions(+), 13 deletions(-) diff --git a/lib/translation_io/client/init_operation.rb b/lib/translation_io/client/init_operation.rb index d0e2d79..f7f9ec6 100644 --- a/lib/translation_io/client/init_operation.rb +++ b/lib/translation_io/client/init_operation.rb @@ -13,8 +13,8 @@ def run haml_source_files = config.haml_source_files slim_source_files = config.slim_source_files pot_path = config.pot_path - source_locale = config.source_locale - target_locales = config.target_locales + source_locale = config.source_locale.to_s + target_locales = config.target_locales.map(&:to_s) locales_path = config.locales_path yaml_locales_path = config.yaml_locales_path yaml_file_paths = config.yaml_file_paths diff --git a/lib/translation_io/client/sync_operation.rb b/lib/translation_io/client/sync_operation.rb index 5b6c6ea..42d51d2 100644 --- a/lib/translation_io/client/sync_operation.rb +++ b/lib/translation_io/client/sync_operation.rb @@ -16,8 +16,8 @@ def run(options = {}) haml_source_files = config.haml_source_files slim_source_files = config.slim_source_files pot_path = config.pot_path - source_locale = config.source_locale - target_locales = config.target_locales + source_locale = config.source_locale.to_s + target_locales = config.target_locales.map(&:to_s) locales_path = config.locales_path yaml_locales_path = config.yaml_locales_path yaml_file_paths = config.yaml_file_paths diff --git a/spec/translation/client/base_operation_spec.rb b/spec/translation/client/base_operation_spec.rb index 00582e0..3b65ef1 100644 --- a/spec/translation/client/base_operation_spec.rb +++ b/spec/translation/client/base_operation_spec.rb @@ -15,8 +15,8 @@ describe 'Locale inconsistency warnings' do it 'triggers error if config.target_locales has duplicate locale' do TranslationIO.configure do |config| - config.source_locale = :en - config.target_locales = [:fr, :nl, :fr] + config.source_locale = 'en' + config.target_locales = ['fr', 'nl', 'fr'] end client = TranslationIO::Client.new('4242', 'https://translation.io') @@ -38,8 +38,8 @@ it 'triggers error if config.source_locale in included in config.target_locales' do TranslationIO.configure do |config| - config.source_locale = :en - config.target_locales = [:fr, :en, :nl] + config.source_locale = 'en' + config.target_locales = ['fr', 'en', 'nl'] end client = TranslationIO::Client.new('4242', 'https://translation.io') @@ -62,7 +62,7 @@ it 'triggers error if config.target_locales is empty' do TranslationIO.configure do |config| - config.source_locale = :en + config.source_locale = 'en' config.target_locales = [] end diff --git a/spec/translation/config_spec.rb b/spec/translation/config_spec.rb index 235b702..7a1898b 100644 --- a/spec/translation/config_spec.rb +++ b/spec/translation/config_spec.rb @@ -4,8 +4,8 @@ it "stores the configuration options" do TranslationIO.configure do |config| config.api_key = '424242' - config.source_locale = :en - config.target_locales = [:fr, :nl] + config.source_locale = 'en' + config.target_locales = ['fr', 'nl'] config.endpoint = 'http://localhost:3001/api' config.ignored_key_prefixes = ['world.streets'] config.ignored_source_paths << 'spec/translation/' @@ -14,8 +14,8 @@ end TranslationIO.config.api_key.should == '424242' - TranslationIO.config.source_locale.should == :en - TranslationIO.config.target_locales.should == [:fr, :nl] + TranslationIO.config.source_locale.should == 'en' + TranslationIO.config.target_locales.should == ['fr', 'nl'] TranslationIO.config.endpoint.should == 'http://localhost:3001/api' TranslationIO.config.ignored_key_prefixes.should == ['world.streets'] TranslationIO.config.localization_key_prefixes.should == ['date.first_day_of_week_in_english'] From d0a48d21594e940ad0c7c7965b382fe5daa3dd6f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 6 Oct 2021 15:20:38 +0200 Subject: [PATCH 30/92] Bump version to 1.27 --- CHANGELOG.md | 6 ++++++ translation.gemspec | 2 +- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index ab38faa..c6729f8 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## [v1.27](https://github.com/translation/rails/releases/tag/v1.27) (2021-10-06) + +#### Fixes (bugs & defects): + + * Improve symbol/string consistency of `source_locale` and `target_locales`. + ## [v1.26](https://github.com/translation/rails/releases/tag/v1.26) (2021-07-14) #### Fixes (bugs & defects): diff --git a/translation.gemspec b/translation.gemspec index 36e6950..dad2e39 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.26' + s.version = '1.27' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] From d643be9f524430719ae58d9dfbb0067788582b35 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 17 Jan 2022 15:42:01 +0100 Subject: [PATCH 31/92] Bump GetText to `3.3.7` to `3.4.2` (Ruby 3.1 compatibility and locale fallbacks) --- CHANGELOG.md | 10 +++++++++- README.md | 2 +- translation.gemspec | 5 ++--- 3 files changed, 12 insertions(+), 5 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index c6729f8..e175a80 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,4 +1,12 @@ -# Changelog +# Changelog + +## [v1.28](https://github.com/translation/rails/releases/tag/v1.28) (2021-01-17) + +#### New features: + + * Bump GetText dependency to 3.4.2 to support: + * Automatic locale fallbacks `fr_BE_Foo` -> `fr_BE` -> `fr` (cf. [ruby-gettext/gettext#89](https://github.com/ruby-gettext/gettext/issues/89)) + * Ruby 3.1 (cf. [ruby-gettext/gettext#92](https://github.com/ruby-gettext/gettext/issues/92)) ## [v1.27](https://github.com/translation/rails/releases/tag/v1.27) (2021-10-06) diff --git a/README.md b/README.md index 116abe5..e532c36 100644 --- a/README.md +++ b/README.md @@ -98,7 +98,7 @@ You can keep your source YAML file automatically updated using [i18n-tasks](http This gem adds the GetText support to Rails. We [strongly suggest](https://translation.io/blog/gettext-is-better-than-rails-i18n) that you use GetText to translate your application since it allows an easier and more complete syntax. -Also, you won't need to create and manage any YAML file since your code will be +Moreover, you won't need to create and manage any YAML file since your code will be automatically scanned for any string to translate. ```ruby diff --git a/translation.gemspec b/translation.gemspec index dad2e39..13db8dd 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.27' + s.version = '1.28' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] @@ -18,8 +18,7 @@ Gem::Specification.new do |s| "source_code_uri" => "https://github.com/translation/rails" } - s.add_dependency 'gettext', '~> 3.2', '>= 3.2.5', '<= 3.3.7' # 3.3.8 adds many dependencies and depends on an online resource, we don't want it - # More here: https://github.com/ruby-gettext/gettext/issues/85#issuecomment-861462382 + s.add_dependency 'gettext', '~> 3.2', '>= 3.2.5', '<= 3.4.2' s.add_development_dependency 'rake', '~> 12.0' s.add_development_dependency 'simplecov', '~> 0.11' From 051bf7342cc851c1661c012892e8647ee1c99602 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 17 Jan 2022 15:59:50 +0100 Subject: [PATCH 32/92] Add Ruby 3.1 to Travis + red-datasets to have correct plurals --- .travis.yml | 3 +++ .../init_operation/update_and_collect_po_files_step_spec.rb | 2 +- translation.gemspec | 3 ++- 3 files changed, 6 insertions(+), 2 deletions(-) diff --git a/.travis.yml b/.travis.yml index b7e8d20..6663cef 100644 --- a/.travis.yml +++ b/.travis.yml @@ -17,6 +17,7 @@ rvm: - 2.6 - 2.7 - 3.0 + - 3.1 - jruby-head gemfile: @@ -30,6 +31,8 @@ matrix: gemfile: gemfiles/lowest.gemfile - rvm: 3.0 gemfile: gemfiles/lowest.gemfile + - rvm: 3.1 + gemfile: gemfiles/lowest.gemfile - rvm: jruby-head gemfile: gemfiles/lowest.gemfile # Work on dev but error "no such file to load -- racc/info" on Travis (jruby 9.3.0.0-SNAPSHOT) diff --git a/spec/translation/client/init_operation/update_and_collect_po_files_step_spec.rb b/spec/translation/client/init_operation/update_and_collect_po_files_step_spec.rb index 3db7619..c65c011 100644 --- a/spec/translation/client/init_operation/update_and_collect_po_files_step_spec.rb +++ b/spec/translation/client/init_operation/update_and_collect_po_files_step_spec.rb @@ -49,7 +49,7 @@ "MIME-Version: 1.0\\n" "Content-Type: text/plain; charset=UTF-8\\n" "Content-Transfer-Encoding: 8bit\\n" -"Plural-Forms: nplurals=2; plural=n>1;\\n" +"Plural-Forms: nplurals=2; plural=n > 1;\\n" "\\n" msgid "Hi kids, do you like violence ?" diff --git a/translation.gemspec b/translation.gemspec index 13db8dd..87503fe 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -18,7 +18,8 @@ Gem::Specification.new do |s| "source_code_uri" => "https://github.com/translation/rails" } - s.add_dependency 'gettext', '~> 3.2', '>= 3.2.5', '<= 3.4.2' + s.add_runtime_dependency 'gettext', '~> 3.2', '>= 3.2.5', '<= 3.4.2' + s.add_runtime_dependency 'red-datasets' s.add_development_dependency 'rake', '~> 12.0' s.add_development_dependency 'simplecov', '~> 0.11' From 4693f650dacafaba40a031c6e07f8a418c431246 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 17 Jan 2022 16:43:53 +0100 Subject: [PATCH 33/92] Fix test with different plural forms depending on GetText versions --- .travis.yml | 6 +++--- .../update_and_collect_po_files_step_spec.rb | 15 +++++++++++++-- 2 files changed, 16 insertions(+), 5 deletions(-) diff --git a/.travis.yml b/.travis.yml index 6663cef..46e8fea 100644 --- a/.travis.yml +++ b/.travis.yml @@ -17,8 +17,8 @@ rvm: - 2.6 - 2.7 - 3.0 - - 3.1 - jruby-head +# - 3.1 (uncomment when ready on travis) gemfile: - gemfiles/lowest.gemfile @@ -31,10 +31,10 @@ matrix: gemfile: gemfiles/lowest.gemfile - rvm: 3.0 gemfile: gemfiles/lowest.gemfile - - rvm: 3.1 - gemfile: gemfiles/lowest.gemfile - rvm: jruby-head gemfile: gemfiles/lowest.gemfile # Work on dev but error "no such file to load -- racc/info" on Travis (jruby 9.3.0.0-SNAPSHOT) + # - rvm: 3.1 + # gemfile: gemfiles/lowest.gemfile sudo: false diff --git a/spec/translation/client/init_operation/update_and_collect_po_files_step_spec.rb b/spec/translation/client/init_operation/update_and_collect_po_files_step_spec.rb index c65c011..ba3686d 100644 --- a/spec/translation/client/init_operation/update_and_collect_po_files_step_spec.rb +++ b/spec/translation/client/init_operation/update_and_collect_po_files_step_spec.rb @@ -37,6 +37,17 @@ operation_step = TranslationIO::Client::InitOperation::UpdateAndCollectPoFilesStep.new(target_locales, pot_path, locales_path) operation_step.run(params) + # Starting with 3.3.9, `red-datasets` must be included as dependency to get plural forms. + # We don't include it with this gem since plural forms are generated by Translation.io with + # its own plural database updates from CLDR, and then correct PO files are sent back to client. + if Gem::Version.new(GetText::VERSION) >= Gem::Version.new('3.3.9') + fr_plural_forms = 'nplurals=; plural=;' + nl_plural_forms = 'nplurals=; plural=;' + else + fr_plural_forms = 'nplurals=2; plural=n>1;' + nl_plural_forms = 'nplurals=2; plural=n != 1;' + end + po_data_fr = <<-EOS msgid "" msgstr "" @@ -49,7 +60,7 @@ "MIME-Version: 1.0\\n" "Content-Type: text/plain; charset=UTF-8\\n" "Content-Transfer-Encoding: 8bit\\n" -"Plural-Forms: nplurals=2; plural=n > 1;\\n" +"Plural-Forms: #{fr_plural_forms}\\n" "\\n" msgid "Hi kids, do you like violence ?" @@ -71,7 +82,7 @@ "MIME-Version: 1.0\\n" "Content-Type: text/plain; charset=UTF-8\\n" "Content-Transfer-Encoding: 8bit\\n" -"Plural-Forms: nplurals=2; plural=n != 1;\\n" +"Plural-Forms: #{nl_plural_forms}\\n" "\\n" msgid "Hi kids, do you like violence ?" From 482e31d66efb57fd9d752060d827fc5bcd629732 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 17 Jan 2022 16:49:18 +0100 Subject: [PATCH 34/92] Remove `red-datasets` dependency --- translation.gemspec | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/translation.gemspec b/translation.gemspec index 87503fe..996f1cc 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -18,8 +18,7 @@ Gem::Specification.new do |s| "source_code_uri" => "https://github.com/translation/rails" } - s.add_runtime_dependency 'gettext', '~> 3.2', '>= 3.2.5', '<= 3.4.2' - s.add_runtime_dependency 'red-datasets' + s.add_runtime_dependency 'gettext', '~> 3.2', '>= 3.2.5', '<= 3.4.2' s.add_development_dependency 'rake', '~> 12.0' s.add_development_dependency 'simplecov', '~> 0.11' From 251ebc2011d1e3af684655dea8776a8888f20914 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 17 Jan 2022 18:01:02 +0100 Subject: [PATCH 35/92] fix date changelog --- CHANGELOG.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index e175a80..b8397d8 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,6 +1,6 @@ # Changelog -## [v1.28](https://github.com/translation/rails/releases/tag/v1.28) (2021-01-17) +## [v1.28](https://github.com/translation/rails/releases/tag/v1.28) (2022-01-17) #### New features: From 65203093f3dc88a92d2d99cfd1d5cafcde6e04dc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 17 Jan 2022 18:41:41 +0100 Subject: [PATCH 36/92] Better text for Fallback (and that works with GetText now) --- README.md | 18 ++++++++++-------- 1 file changed, 10 insertions(+), 8 deletions(-) diff --git a/README.md b/README.md index e532c36..90f8ecc 100644 --- a/README.md +++ b/README.md @@ -225,10 +225,16 @@ Examples: `en-microsoft` or `fr-BE-custom`. ### Fallbacks -Using [I18n (YAML)](#i18n-yaml) syntax, fallbacks will work as expected for any regional or custom -language. It means that if the `en-microsoft.example` key is missing, -then it will fallback to `en.example`. So you only need to translate keys that -are different from the main language. +If a translation is missing for a regional (`fr-BE`) or custom (`fr-microsoft`) +language, then it will fallback to the main language (`fr`). + +Locale fallbacks will work as expected with both [I18n (YAML)](#i18n-yaml) +and [GetText](#gettext) syntaxes. + +A good way to leverage this feature is to ignore sentences from a regional language +that would have the same translation as the main language (usually most of them). +It's way easier to maintain the project over time if only 10% of the regional sentences +need to be adapted. Note that fallbacks are chained, so `fr-BE-custom` will fallback to `fr-BE` that will fallback to `fr`. @@ -237,10 +243,6 @@ Just make sure to add `config.i18n.fallbacks = true` to your `config/application You can find more information about this [here](https://guides.rubyonrails.org/configuring.html#configuring-i18n). -Using [GetText](#gettext) syntax, it will only fallback to the source language. -So either you create a fallback mechanism by yourself or you avoid fallbacking -by translating everything in Translation.io for the regional or custom language. - ## Change the current locale ### Globally From de95a883d66700bff025f25821e87ab49ef133a7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 31 Jan 2022 16:39:56 +0100 Subject: [PATCH 37/92] Set default GetText/Locale locale (last fallback) as config.source_locale instead of "en" (default) --- lib/translation.rb | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/lib/translation.rb b/lib/translation.rb index 051e888..3613393 100644 --- a/lib/translation.rb +++ b/lib/translation.rb @@ -39,6 +39,10 @@ def configure(&block) GetText::TextDomainManager.cached = false end + # Set default GetText locale (last fallback) as config.source_locale instead of "en" (default) + gettext_locale = @config.source_locale.to_s.gsub('-', '_').to_sym + Locale.set_default(gettext_locale) + # include is private until Ruby 2.1 Proxy.send(:include, GetText) From e1b7cdca1e4457f609c3d95d41b515a8253a1a6e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Tue, 1 Feb 2022 12:03:49 +0100 Subject: [PATCH 38/92] Bump to 1.29 --- CHANGELOG.md | 6 ++++++ README.md | 2 +- translation.gemspec | 2 +- 3 files changed, 8 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index b8397d8..c4ed7f1 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## [v1.29](https://github.com/translation/rails/releases/tag/v1.29) (2022-02-01) + +#### Fixes (bugs & defects): + + * Use `source_locale` as last fallback for GetText (instead of default "en"). + ## [v1.28](https://github.com/translation/rails/releases/tag/v1.28) (2022-01-17) #### New features: diff --git a/README.md b/README.md index 90f8ecc..e693785 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # [Translation.io](https://translation.io) client for Ruby on Rails [![Software License](https://img.shields.io/badge/license-MIT-brightgreen.svg?style=flat-square)](LICENSE) -[![Build Status](https://travis-ci.com/translation/rails.svg?branch=master)](https://travis-ci.com/translation/rails) +[![Build Status](https://travis-ci.com/translation/rails.svg?branch=master)](https://app.travis-ci.com/github/translation/rails) [![Test Coverage](https://codeclimate.com/github/translation/rails/badges/coverage.svg)](https://codeclimate.com/github/translation/rails/test_coverage) [![Gem Version](https://badgen.net/rubygems/v/translation)](https://rubygems.org/gems/translation) [![Downloads](https://img.shields.io/gem/dt/translation.svg)](https://rubygems.org/gems/translation) diff --git a/translation.gemspec b/translation.gemspec index 996f1cc..cbcdc8e 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.28' + s.version = '1.29' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] From cb9b4d87ec60fb2a4e0fa19763f6db9d95f2c5e9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Tue, 1 Feb 2022 12:09:35 +0100 Subject: [PATCH 39/92] Add RELEASE.md to gitignore --- .gitignore | 1 + 1 file changed, 1 insertion(+) diff --git a/.gitignore b/.gitignore index d1efd75..f1ea31c 100644 --- a/.gitignore +++ b/.gitignore @@ -7,3 +7,4 @@ coverage Gemfile.lock .ruby-version .bundle +RELEASE.md From 8c00ae81c0989953f9bee2897b0f694b04d1078f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Thu, 17 Feb 2022 16:56:33 +0100 Subject: [PATCH 40/92] Migrate from Travis to GitHub Actions (#46) Travis is not free for Open-Source anymore, and very slow to bump Ruby versions. GitHub Actions is free for Open-Source and quick to bump Ruby versions. --- .github/workflows/test.yml | 54 +++++++++++++++++++++++++++ .travis.yml | 65 --------------------------------- README.md | 2 +- spec/translation/config_spec.rb | 8 ++-- 4 files changed, 59 insertions(+), 70 deletions(-) create mode 100644 .github/workflows/test.yml delete mode 100644 .travis.yml diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml new file mode 100644 index 0000000..9d87e84 --- /dev/null +++ b/.github/workflows/test.yml @@ -0,0 +1,54 @@ +name: Translation/Rails Gem CI + +on: [push, pull_request] + +jobs: + test: + runs-on: ubuntu-latest + strategy: + fail-fast: false + matrix: + ruby: + - 2.2 + - 2.3 + - 2.4 + - 2.5 + - 2.6 + - 2.7 + - 3.0 + - 3.1 + - jruby-9.1.17.0 + gemfile: + - lowest + - latest + exclude: + # Ruby > 2.6 removed BigDecimal.new which was used on Rails 4.1 (removed with Rails 4.2 though) + - ruby: 2.7 + gemfile: lowest + - ruby: 3.0 + gemfile: lowest + - ruby: 3.1 + gemfile: lowest + env: + BUNDLE_GEMFILE: ${{ github.workspace }}/gemfiles/${{ matrix.gemfile }}.gemfile + CC_TEST_REPORTER_ID: 945dfb58a832d233a3caeb84e3e6d3be212e8c7abcb48117fce63b9adcb43647 + steps: + - uses: actions/checkout@v2 + - name: Setup Bundler 1.x for Rails 4.x + if: ${{ matrix.gemfile == 'lowest' }} + run: echo "BUNDLER_VERSION=1.17.3" >> $GITHUB_ENV + - uses: ruby/setup-ruby@v1 + with: + ruby-version: ${{ matrix.ruby }} + bundler-cache: true # runs bundle install and caches installed gems automatically + bundler: ${{ env.BUNDLER_VERSION || 'latest' }} + - run: ruby --version + - name: Run specs + run: bundle exec rspec + - name: Publish code coverage + if: ${{ matrix.ruby == '3.1' && matrix.gemfile == 'latest' }} # only one is needed! + uses: paambaati/codeclimate-action@v3.0.0 + with: + debug: true + verifyDownload: true + diff --git a/.travis.yml b/.travis.yml deleted file mode 100644 index 46e8fea..0000000 --- a/.travis.yml +++ /dev/null @@ -1,65 +0,0 @@ -dist: bionic - -env: - global: - - CC_TEST_REPORTER_ID=1ec0e82ac7a13e879f71d36abbf09c7c691c71ec58a8b7f74beef6086e3b65db - -language: ruby - -# 2.0 has only one test not passing -# (TranslationIO::YAMLConversion#get_yaml_data_from_flat_translations works with weird not-escaped code) -# 2.1 passes but is not compatible with Travis on Bionic -rvm: - - 2.2 - - 2.3 - - 2.4 - - 2.5 - - 2.6 - - 2.7 - - 3.0 - - jruby-head -# - 3.1 (uncomment when ready on travis) - -gemfile: - - gemfiles/lowest.gemfile - - gemfiles/latest.gemfile - -matrix: - exclude: - # Ruby > 2.6 removed BigDecimal.new which was used on Rails 4.1 (removed with Rails 4.2 though) - - rvm: 2.7 - gemfile: gemfiles/lowest.gemfile - - rvm: 3.0 - gemfile: gemfiles/lowest.gemfile - - rvm: jruby-head - gemfile: gemfiles/lowest.gemfile # Work on dev but error "no such file to load -- racc/info" on Travis (jruby 9.3.0.0-SNAPSHOT) - # - rvm: 3.1 - # gemfile: gemfiles/lowest.gemfile - -sudo: false - -# https://docs.travis-ci.com/user/languages/ruby/ -# To stay on bundler 1 for compatibility with rails 4.1 -before_install: - - gem uninstall -v '>= 2' -i $(rvm gemdir)@global -ax bundler || true - - gem install bundler -v '1.17.3' - -# Override to be able to force bundler 1, needed for lowest.gemfile -install: bundle _1.17.3_ install --jobs=3 --retry=3 - -before_script: - - curl -L https://codeclimate.com/downloads/test-reporter/test-reporter-latest-linux-amd64 > ./cc-test-reporter - - chmod +x ./cc-test-reporter - - ./cc-test-reporter before-build - - ruby --version - -script: - - bundle _1.17.3_ exec rspec - -after_script: - - ./cc-test-reporter after-build -t simplecov --exit-code $TRAVIS_TEST_RESULT - -notifications: - email: - recipients: - - contact@translation.io diff --git a/README.md b/README.md index e693785..d65b105 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # [Translation.io](https://translation.io) client for Ruby on Rails [![Software License](https://img.shields.io/badge/license-MIT-brightgreen.svg?style=flat-square)](LICENSE) -[![Build Status](https://travis-ci.com/translation/rails.svg?branch=master)](https://app.travis-ci.com/github/translation/rails) +[![Build Status](https://github.com/translation/rails/actions/workflows/test.yml/badge.svg)](https://github.com/translation/rails/actions/workflows/test.yml) [![Test Coverage](https://codeclimate.com/github/translation/rails/badges/coverage.svg)](https://codeclimate.com/github/translation/rails/test_coverage) [![Gem Version](https://badgen.net/rubygems/v/translation)](https://rubygems.org/gems/translation) [![Downloads](https://img.shields.io/gem/dt/translation.svg)](https://rubygems.org/gems/translation) diff --git a/spec/translation/config_spec.rb b/spec/translation/config_spec.rb index 7a1898b..d126225 100644 --- a/spec/translation/config_spec.rb +++ b/spec/translation/config_spec.rb @@ -30,7 +30,7 @@ it '#source_files_for_formats - classic path naming' do TranslationIO.configure do |config| - config.ignored_source_paths = ['spec/translation/', 'lib/', 'gemfiles/', '.git/'] + config.ignored_source_paths = ['spec/translation/', 'lib/', 'vendor/', 'gemfiles/', '.git/'] config.ignored_source_files = ['spec/spec_helper.rb'] end @@ -42,7 +42,7 @@ it '#source_files_for_formats - second path naming ("./")' do TranslationIO.configure do |config| - config.ignored_source_paths = ['./spec/translation/', './lib/', './gemfiles/', './.git/'] + config.ignored_source_paths = ['./spec/translation/', './lib/', './vendor/', './gemfiles/', './.git/'] config.ignored_source_files = ['./spec/spec_helper.rb'] end @@ -54,7 +54,7 @@ it '#source_files_for_formats - third path naming ("no ending /")' do TranslationIO.configure do |config| - config.ignored_source_paths = ['spec/translation', 'lib', 'gemfiles', '.git'] + config.ignored_source_paths = ['spec/translation', 'lib', 'vendor', 'gemfiles', '.git'] config.ignored_source_files = ['spec/spec_helper.rb'] end @@ -66,7 +66,7 @@ it '#source_files_for_formats' do TranslationIO.configure do |config| - config.ignored_source_paths = ['spec', 'lib', 'gemfiles'] + config.ignored_source_paths = ['spec', 'lib', 'vendor', 'gemfiles'] config.parsed_gems = [] end From b3b36af8268fc8372c2c4be7487c4b2c81db0b58 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Thu, 17 Feb 2022 17:09:58 +0100 Subject: [PATCH 41/92] Rename tests to "Build Status" to name badge and force reference branch to master --- .github/workflows/test.yml | 3 +-- README.md | 2 +- 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 9d87e84..f8f7572 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -1,4 +1,4 @@ -name: Translation/Rails Gem CI +name: Build Status on: [push, pull_request] @@ -51,4 +51,3 @@ jobs: with: debug: true verifyDownload: true - diff --git a/README.md b/README.md index d65b105..557676d 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # [Translation.io](https://translation.io) client for Ruby on Rails [![Software License](https://img.shields.io/badge/license-MIT-brightgreen.svg?style=flat-square)](LICENSE) -[![Build Status](https://github.com/translation/rails/actions/workflows/test.yml/badge.svg)](https://github.com/translation/rails/actions/workflows/test.yml) +[![Build Status](https://github.com/translation/rails/actions/workflows/test.yml/badge.svg?branch=master)](https://github.com/translation/rails/actions/workflows/test.yml) [![Test Coverage](https://codeclimate.com/github/translation/rails/badges/coverage.svg)](https://codeclimate.com/github/translation/rails/test_coverage) [![Gem Version](https://badgen.net/rubygems/v/translation)](https://rubygems.org/gems/translation) [![Downloads](https://img.shields.io/gem/dt/translation.svg)](https://rubygems.org/gems/translation) From 3c7fabb04e25d3fe6806230e1af9d43fcb81e67f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 23 Mar 2022 16:21:27 +0100 Subject: [PATCH 42/92] Don't raise an issue for a conflicted `.translation_io` file anymore, but fix it directly --- .../apply_yaml_source_edits_step.rb | 18 +++++++++++---- .../apply_yaml_source_edits_step_spec.rb | 23 ++++++++++++++++--- 2 files changed, 34 insertions(+), 7 deletions(-) diff --git a/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb b/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb index 46c2842..1a29ea2 100644 --- a/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb +++ b/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb @@ -21,7 +21,7 @@ def run(params) reload_or_reuse_yaml_sources - @yaml_sources.each do |yaml_source| + @yaml_sources.to_a.each do |yaml_source| yaml_file_path = yaml_source[:yaml_file_path] yaml_flat_hash = yaml_source[:yaml_flat_hash] @@ -55,7 +55,7 @@ def reload_or_reuse_yaml_sources } end else - @yaml_sources + @yaml_source end end @@ -133,9 +133,10 @@ def metadata_timestamp if File.exist?(TranslationIO.config.metadata_path) metadata_content = File.read(TranslationIO.config.metadata_path) + # If any conflicts in file, take the lowest timestamp and potentially reapply some source edits if metadata_content.include?('>>>>') || metadata_content.include?('<<<<') - TranslationIO.info "[Error] #{TranslationIO.config.metadata_path} file is corrupted and seems to have unresolved versioning conflicts. Please resolve them and try again." - exit(false) + timestamps = metadata_content.scan(/timestamp: (\d*)/).flatten.uniq.collect(&:to_i) + return timestamps.min || 0 else return YAML::load(metadata_content)['timestamp'] rescue 0 end @@ -146,6 +147,15 @@ def metadata_timestamp def update_metadata_timestamp File.open(TranslationIO.config.metadata_path, 'w') do |f| + f.puts '####' + f.puts '# This file is used in the context of Translation.io source editions.' + f.puts '# Please see: https://translation.io/blog/new-feature-copywriting' + f.puts '#' + f.puts '# If you have any git conflicts, either keep the smaller timestamp or' + f.puts '# ignore the conflicts and "sync" again, it will fix this file for you.' + f.puts '####' + f.puts + f.write({ 'timestamp' => Time.now.utc.to_i }.to_yaml) end end diff --git a/spec/translation/client/sync_operation/apply_yaml_source_edits_step_spec.rb b/spec/translation/client/sync_operation/apply_yaml_source_edits_step_spec.rb index d7b146a..539540c 100644 --- a/spec/translation/client/sync_operation/apply_yaml_source_edits_step_spec.rb +++ b/spec/translation/client/sync_operation/apply_yaml_source_edits_step_spec.rb @@ -1,7 +1,7 @@ require 'spec_helper' describe TranslationIO::Client::SyncOperation::ApplyYamlSourceEditsStep do - it "doesn't accept a corrupted .translation_io file" do + it "Fix a conflicted .translation_io file by taking the lowest timestamp" do yaml_locales_path = TranslationIO.config.yaml_locales_path FileUtils.mkdir_p(yaml_locales_path) @@ -10,7 +10,7 @@ <<<<<<< HEAD timestamp: 1474639179 ======= -timestamp: 1474629510 +timestamp: 1574629510 >>>>>>> master EOS end @@ -34,8 +34,25 @@ } end + # Check that the lowest timestamp from the corrupted file is used! + step_operation.send(:metadata_timestamp).should == 1474639179 + params = {} - expect { step_operation.run(params) }.to raise_error(SystemExit) + step_operation.run(params) + + # Comment must be present in new timestamp + File.read("#{yaml_locales_path}/.translation_io").should == <<-EOS +#### +# This file is used in the context of Translation.io source editions. +# Please see: https://translation.io/blog/new-feature-copywriting +# +# If you have any git conflicts, either keep the smaller timestamp or +# ignore the conflicts and "sync" again, it will fix this file for you. +#### + +--- +timestamp: #{Time.now.to_i} +EOS end it 'applies remote changes locally' do From a15f3b0e2744e94819b32e8d24578f262297f5f8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 23 Mar 2022 16:39:00 +0100 Subject: [PATCH 43/92] Cleaner comments in `.translation_io` file --- .../client/sync_operation/apply_yaml_source_edits_step.rb | 2 -- .../client/sync_operation/apply_yaml_source_edits_step_spec.rb | 2 -- 2 files changed, 4 deletions(-) diff --git a/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb b/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb index 1a29ea2..68db547 100644 --- a/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb +++ b/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb @@ -147,13 +147,11 @@ def metadata_timestamp def update_metadata_timestamp File.open(TranslationIO.config.metadata_path, 'w') do |f| - f.puts '####' f.puts '# This file is used in the context of Translation.io source editions.' f.puts '# Please see: https://translation.io/blog/new-feature-copywriting' f.puts '#' f.puts '# If you have any git conflicts, either keep the smaller timestamp or' f.puts '# ignore the conflicts and "sync" again, it will fix this file for you.' - f.puts '####' f.puts f.write({ 'timestamp' => Time.now.utc.to_i }.to_yaml) diff --git a/spec/translation/client/sync_operation/apply_yaml_source_edits_step_spec.rb b/spec/translation/client/sync_operation/apply_yaml_source_edits_step_spec.rb index 539540c..bddbd59 100644 --- a/spec/translation/client/sync_operation/apply_yaml_source_edits_step_spec.rb +++ b/spec/translation/client/sync_operation/apply_yaml_source_edits_step_spec.rb @@ -42,13 +42,11 @@ # Comment must be present in new timestamp File.read("#{yaml_locales_path}/.translation_io").should == <<-EOS -#### # This file is used in the context of Translation.io source editions. # Please see: https://translation.io/blog/new-feature-copywriting # # If you have any git conflicts, either keep the smaller timestamp or # ignore the conflicts and "sync" again, it will fix this file for you. -#### --- timestamp: #{Time.now.to_i} From 5cb556d420bc7d203c4933e9ae7e909d16637c27 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 23 Mar 2022 16:46:28 +0100 Subject: [PATCH 44/92] Bump version to 1.30 + CHANGELOG --- CHANGELOG.md | 6 ++++++ translation.gemspec | 2 +- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index c4ed7f1..7216315 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## [v1.30](https://github.com/translation/rails/releases/tag/v1.30) (2022-03-23) + +#### New features: + + * Don't raise an issue for a conflicted `.translation_io` file anymore, but fix it directly. + ## [v1.29](https://github.com/translation/rails/releases/tag/v1.29) (2022-02-01) #### Fixes (bugs & defects): diff --git a/translation.gemspec b/translation.gemspec index cbcdc8e..ae563aa 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.29' + s.version = '1.30' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] From ce89ec5fea5169fbedbfd587198b427355f79339 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Thu, 24 Mar 2022 16:06:03 +0100 Subject: [PATCH 45/92] Create limitations section to explain the issue with `case`/`when` and ERB --- README.md | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) diff --git a/README.md b/README.md index 557676d..6ec1314 100644 --- a/README.md +++ b/README.md @@ -52,6 +52,7 @@ Table of contents * [Paths where locales are stored (not recommended)](#paths-where-locales-are-stored-not-recommended) * [GetText Object Class Monkey-Patching](#gettext-object-class-monkey-patching) * [Pure Ruby (without Rails)](#pure-ruby-without-rails) + * [Limitations](#limitations) * [Testing](#testing) * [Contributing](#contributing) * [List of clients for Translation.io](#list-of-clients-for-translationio) @@ -582,6 +583,33 @@ This gem was created specifically for Rails, but you can also use it in a pure R (Thanks [@kubaw](https://github.com/kubaw) for this snippet!) +## Limitations + +If you localize `.erb` files with the [GetText syntax](#gettext), please avoid +the use of `case` and `when` that are not correctly parsed by ERB. + +This syntax will break and your file will be ignored: + +```erb +<% case @state %> +<% when 'received' %> +``` + +Instead, use `if`/`elsif` or this `case` syntax: + +```erb +<% +case @state +when 'received' +%> +``` + +These are the related discussions: [ruby/erb#4](https://github.com/ruby/erb/issues/4) and [translation/rails#44](https://github.com/translation/rails/issues/44). + +There is an open Pull Request ([ruby-gettext/gettext#91](https://github.com/ruby-gettext/gettext/pull/91)), switching ERB for Erubi, +that is waiting to be merged into GetText, but it may have unknown indesirable +side effects. + ## Testing To run the specs: From bb1a4bddb0c07b8dd0ebc3149d2645f334bc5d1e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Thu, 24 Mar 2022 16:08:25 +0100 Subject: [PATCH 46/92] Typo / improvement README --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 6ec1314..170d277 100644 --- a/README.md +++ b/README.md @@ -606,7 +606,7 @@ when 'received' These are the related discussions: [ruby/erb#4](https://github.com/ruby/erb/issues/4) and [translation/rails#44](https://github.com/translation/rails/issues/44). -There is an open Pull Request ([ruby-gettext/gettext#91](https://github.com/ruby-gettext/gettext/pull/91)), switching ERB for Erubi, +There is currently an open PR ([ruby-gettext/gettext#91](https://github.com/ruby-gettext/gettext/pull/91)), switching ERB for [Erubi](https://github.com/jeremyevans/erubi), that is waiting to be merged into GetText, but it may have unknown indesirable side effects. From b8764269287c64442bc26aa88b3b7c11b8b8c13b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Thu, 24 Mar 2022 16:23:58 +0100 Subject: [PATCH 47/92] Typo README --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 170d277..29c4697 100644 --- a/README.md +++ b/README.md @@ -607,7 +607,7 @@ when 'received' These are the related discussions: [ruby/erb#4](https://github.com/ruby/erb/issues/4) and [translation/rails#44](https://github.com/translation/rails/issues/44). There is currently an open PR ([ruby-gettext/gettext#91](https://github.com/ruby-gettext/gettext/pull/91)), switching ERB for [Erubi](https://github.com/jeremyevans/erubi), -that is waiting to be merged into GetText, but it may have unknown indesirable +that is waiting to be merged into GetText, but it may have unknown undesirable side effects. ## Testing From b0c56d9a007905893d9464ec3cfd2502007f769b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 4 Apr 2022 15:10:31 +0200 Subject: [PATCH 48/92] Add alias in YAML for new spec --- spec/support/data/en.yml | 4 +++- spec/translation/yaml_conversion_spec.rb | 1 + 2 files changed, 4 insertions(+), 1 deletion(-) diff --git a/spec/support/data/en.yml b/spec/support/data/en.yml index f26b417..2e16054 100644 --- a/spec/support/data/en.yml +++ b/spec/support/data/en.yml @@ -1,6 +1,6 @@ en: hello: "Hello world" - main: + main: &main_alias menu: stuff: "This is stuff" bye: "Good bye world" @@ -21,3 +21,5 @@ en: - sub_test: hello: hello no: "N°" + other_main: + *main_alias diff --git a/spec/translation/yaml_conversion_spec.rb b/spec/translation/yaml_conversion_spec.rb index a678163..efe4221 100644 --- a/spec/translation/yaml_conversion_spec.rb +++ b/spec/translation/yaml_conversion_spec.rb @@ -96,6 +96,7 @@ result.should == { "en.hello" => "Hello world", "en.main.menu.stuff" => "This is stuff", + "en.other_main.menu.stuff" => "This is stuff", # alias in origin YAML "en.bye" => "Good bye world", "en.empty" => nil, "en.empty_string" => "", From 1bde6efc35ceb7936121d8f652bf577bdd45df91 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 4 Apr 2022 16:14:28 +0200 Subject: [PATCH 49/92] Create `TranslationIO.yaml_load()` method to load YAML with aliases using Psych 3 or 4 (cf. #47) --- lib/translation.rb | 9 +++++++++ .../base_operation/save_special_yaml_files_step.rb | 4 ++-- .../client/init_operation/cleanup_yaml_files_step.rb | 2 +- .../client/init_operation/create_yaml_po_files_step.rb | 2 +- .../sync_operation/apply_yaml_source_edits_step.rb | 4 ++-- .../client/sync_operation/create_yaml_pot_file_step.rb | 2 +- lib/translation_io/yaml_conversion.rb | 2 +- spec/translation/yaml_conversion_spec.rb | 2 +- 8 files changed, 18 insertions(+), 9 deletions(-) diff --git a/lib/translation.rb b/lib/translation.rb index 3613393..25f6b4e 100644 --- a/lib/translation.rb +++ b/lib/translation.rb @@ -93,6 +93,15 @@ def normalize_path(relative_or_absolute_path) File.expand_path(relative_or_absolute_path).gsub("#{Dir.pwd}/", '') end + # Cf. https://github.com/translation/rails/issues/47 + def yaml_load(source) + begin + YAML.load(source, :aliases => true) || {} + rescue ArgumentError + YAML.load(source) || {} + end + end + def version Gem::Specification::find_by_name('translation').version.to_s end diff --git a/lib/translation_io/client/base_operation/save_special_yaml_files_step.rb b/lib/translation_io/client/base_operation/save_special_yaml_files_step.rb index d541ff2..7ae7fbd 100644 --- a/lib/translation_io/client/base_operation/save_special_yaml_files_step.rb +++ b/lib/translation_io/client/base_operation/save_special_yaml_files_step.rb @@ -43,7 +43,7 @@ def run # To have a localization.xx.yml file during tests (without call to backend) if TranslationIO.config.test - if YAML::load(yaml_data).present? + if TranslationIO.yaml_load(yaml_data).present? File.open(yaml_path, 'wb') do |file| file.write(self.class.top_comment) file.write(yaml_data) @@ -64,7 +64,7 @@ def run yaml_path = File.join(@yaml_locales_path, "localization.#{target_locale}.yml") yaml_data = parsed_response["yaml_data_#{target_locale}"] - if yaml_data.present? && YAML::load(yaml_data).present? + if yaml_data.present? && TranslationIO.yaml_load(yaml_data).present? File.open(yaml_path, 'wb') do |file| file.write(self.class.top_comment) file.write(yaml_data) diff --git a/lib/translation_io/client/init_operation/cleanup_yaml_files_step.rb b/lib/translation_io/client/init_operation/cleanup_yaml_files_step.rb index 5b053e6..13ec831 100644 --- a/lib/translation_io/client/init_operation/cleanup_yaml_files_step.rb +++ b/lib/translation_io/client/init_operation/cleanup_yaml_files_step.rb @@ -13,7 +13,7 @@ def run @yaml_file_paths.each do |locale_file_path| if locale_file_removable?(locale_file_path) if File.exist?(locale_file_path) - content_hash = YAML::load(File.read(locale_file_path)) || {} + content_hash = TranslationIO.yaml_load(File.read(locale_file_path)) || {} source_content_hash = content_hash.select { |k| k.to_s == @source_locale.to_s } if source_content_hash.empty? diff --git a/lib/translation_io/client/init_operation/create_yaml_po_files_step.rb b/lib/translation_io/client/init_operation/create_yaml_po_files_step.rb index 7a43058..e2ac079 100644 --- a/lib/translation_io/client/init_operation/create_yaml_po_files_step.rb +++ b/lib/translation_io/client/init_operation/create_yaml_po_files_step.rb @@ -18,7 +18,7 @@ def run(params) @yaml_file_paths.each do |file_path| TranslationIO.info file_path, 2, 2 - file_translations = YAML::load(File.read(file_path)) + file_translations = TranslationIO.yaml_load(File.read(file_path)) unless file_translations.blank? all_translations = all_translations.deep_merge(file_translations) diff --git a/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb b/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb index 68db547..d6ed93c 100644 --- a/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb +++ b/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb @@ -46,7 +46,7 @@ def reload_or_reuse_yaml_sources if yaml_sources_reload_needed? @yaml_sources = sort_by_project_locales_first(@yaml_file_paths).collect do |yaml_file_path| yaml_content = File.read(yaml_file_path) - yaml_hash = YAML::load(yaml_content) + yaml_hash = TranslationIO.yaml_load(yaml_content) yaml_flat_hash = FlatHash.to_flat_hash(yaml_hash) { @@ -138,7 +138,7 @@ def metadata_timestamp timestamps = metadata_content.scan(/timestamp: (\d*)/).flatten.uniq.collect(&:to_i) return timestamps.min || 0 else - return YAML::load(metadata_content)['timestamp'] rescue 0 + return YAML.load(metadata_content)['timestamp'] rescue 0 end else return 0 diff --git a/lib/translation_io/client/sync_operation/create_yaml_pot_file_step.rb b/lib/translation_io/client/sync_operation/create_yaml_pot_file_step.rb index 35fefb5..4463858 100644 --- a/lib/translation_io/client/sync_operation/create_yaml_pot_file_step.rb +++ b/lib/translation_io/client/sync_operation/create_yaml_pot_file_step.rb @@ -14,7 +14,7 @@ def run(params) @yaml_file_paths.each do |file_path| TranslationIO.info file_path, 2, 2 - file_translations = YAML::load(File.read(file_path)) + file_translations = TranslationIO.yaml_load(File.read(file_path)) unless file_translations.blank? all_translations = all_translations.deep_merge(file_translations) diff --git a/lib/translation_io/yaml_conversion.rb b/lib/translation_io/yaml_conversion.rb index 0215fd3..34c9c4f 100644 --- a/lib/translation_io/yaml_conversion.rb +++ b/lib/translation_io/yaml_conversion.rb @@ -26,7 +26,7 @@ def get_flat_translations_for_yaml_file(file_path) end def get_flat_translations_for_yaml_data(yaml_data) - translations = YAML::load(yaml_data) + translations = TranslationIO.yaml_load(yaml_data) if translations return FlatHash.to_flat_hash(translations) diff --git a/spec/translation/yaml_conversion_spec.rb b/spec/translation/yaml_conversion_spec.rb index efe4221..ab24e5d 100644 --- a/spec/translation/yaml_conversion_spec.rb +++ b/spec/translation/yaml_conversion_spec.rb @@ -96,7 +96,7 @@ result.should == { "en.hello" => "Hello world", "en.main.menu.stuff" => "This is stuff", - "en.other_main.menu.stuff" => "This is stuff", # alias in origin YAML + "en.other_main.menu.stuff" => "This is stuff", # alias in YAML "en.bye" => "Good bye world", "en.empty" => nil, "en.empty_string" => "", From 336a8200a3925015765f6cf5ba92e16662002408 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 4 Apr 2022 17:12:28 +0200 Subject: [PATCH 50/92] Bump version to 1.31 + Changelog --- CHANGELOG.md | 6 ++++++ translation.gemspec | 2 +- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 7216315..13cc263 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## [v1.31](https://github.com/translation/rails/releases/tag/v1.31) (2022-04-04) + +#### Fixes (bugs & defects): + + * Fix Psych 4 breaking change when loading YAML files with aliases. See [issue #47](https://github.com/translation/rails/issues/47). + ## [v1.30](https://github.com/translation/rails/releases/tag/v1.30) (2022-03-23) #### New features: diff --git a/translation.gemspec b/translation.gemspec index ae563aa..67e08bb 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.30' + s.version = '1.31' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] From 78cc8928997fb53d1cd18d7250101cc3fdf1d289 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Fri, 20 May 2022 16:14:01 +0200 Subject: [PATCH 51/92] Fix ERB parsing bug with `case` in new GetText version (>= 3.4.3) + new tests. See https://github.com/ruby-gettext/gettext/pull/91 --- lib/translation.rb | 9 ++++- .../base_operation/update_pot_file_step.rb | 29 +++++++++++---- .../app/views/layouts/application.html.erb | 9 ++++- .../update_pot_file_step_spec.rb | 36 +++++++++++++++---- translation.gemspec | 2 +- 5 files changed, 70 insertions(+), 15 deletions(-) diff --git a/lib/translation.rb b/lib/translation.rb index 25f6b4e..8d58f57 100644 --- a/lib/translation.rb +++ b/lib/translation.rb @@ -72,13 +72,20 @@ def require_gettext_dependencies require 'gettext/tools' require 'gettext/text_domain_manager' require 'gettext/tools/xgettext' + require "gettext/tools/parser/erubi" end def add_parser_for_erb_source_formats(new_erb_formats) - existing_extensions = GetText::ErbParser.instance_variable_get("@config")[:extnames] new_extensions = new_erb_formats.collect { |ext| ".#{ext}" } + existing_extensions = GetText::ErbParser.instance_variable_get("@config")[:extnames] GetText::ErbParser.instance_variable_get("@config")[:extnames] = (existing_extensions + new_extensions).uniq + + # for gettext >= 3.4.3 (erubi compatibility) + if defined?(GetText::ErubiParser) + existing_extensions = GetText::ErubiParser.instance_variable_get("@config")[:extnames] + GetText::ErubiParser.instance_variable_get("@config")[:extnames] = (existing_extensions + new_extensions).uniq + end end def info(message, level = 0, verbose_level = 0) diff --git a/lib/translation_io/client/base_operation/update_pot_file_step.rb b/lib/translation_io/client/base_operation/update_pot_file_step.rb index fbadf9d..4f16bf2 100644 --- a/lib/translation_io/client/base_operation/update_pot_file_step.rb +++ b/lib/translation_io/client/base_operation/update_pot_file_step.rb @@ -16,12 +16,29 @@ def run(params) TranslationIO.info "Updating POT file." FileUtils.mkdir_p(File.dirname(@pot_path)) - GetText::Tools::XGetText.run(*@source_files, '-o', @pot_path, - '--msgid-bugs-address', TranslationIO.config.pot_msgid_bugs_address, - '--package-name', TranslationIO.config.pot_package_name, - '--package-version', TranslationIO.config.pot_package_version, - '--copyright-holder', TranslationIO.config.pot_copyright_holder, - '--copyright-year', TranslationIO.config.pot_copyright_year.to_s) + + # for gettext >= 3.4.3 (erubi compatibility) + if defined?(GetText::ErubiParser) + GetText::Tools::XGetText.run( + *@source_files, '-o', @pot_path, + '--msgid-bugs-address', TranslationIO.config.pot_msgid_bugs_address, + '--package-name', TranslationIO.config.pot_package_name, + '--package-version', TranslationIO.config.pot_package_version, + '--copyright-holder', TranslationIO.config.pot_copyright_holder, + '--copyright-year', TranslationIO.config.pot_copyright_year.to_s, + '--require', 'gettext/tools/parser/erubi', # Cf. (1) https://github.com/ruby-gettext/gettext/pull/91 + '--parser', 'GetText::ErubiParser' # (2) https://github.com/ruby-gettext/gettext/commit/0eb06a88323a5cc16065680ffe228d978fb87c88 + ) + else + GetText::Tools::XGetText.run( + *@source_files, '-o', @pot_path, + '--msgid-bugs-address', TranslationIO.config.pot_msgid_bugs_address, + '--package-name', TranslationIO.config.pot_package_name, + '--package-version', TranslationIO.config.pot_package_version, + '--copyright-holder', TranslationIO.config.pot_copyright_holder, + '--copyright-year', TranslationIO.config.pot_copyright_year.to_s + ) + end FileUtils.rm_f(@tmp_empty_file) if @tmp_empty_file.present? diff --git a/spec/support/rails_app/app/views/layouts/application.html.erb b/spec/support/rails_app/app/views/layouts/application.html.erb index 646d31e..7f1172a 100644 --- a/spec/support/rails_app/app/views/layouts/application.html.erb +++ b/spec/support/rails_app/app/views/layouts/application.html.erb @@ -1,2 +1,9 @@ <%= _("Let's get ready to rumble!") %> -<%= p_("contexte", "salut") %> +<%= p_("Eminem", "I'm Slim Shady, yes, I'm the real Shady") %> + +
+ <%= _('Before case') %> + <% case 1 %> + <% end %> + <%= _('After case') %> +
diff --git a/spec/translation/client/base_operation/update_pot_file_step_spec.rb b/spec/translation/client/base_operation/update_pot_file_step_spec.rb index 452861f..d9d1e63 100644 --- a/spec/translation/client/base_operation/update_pot_file_step_spec.rb +++ b/spec/translation/client/base_operation/update_pot_file_step_spec.rb @@ -19,8 +19,16 @@ msgstr "" #: ../spec/support/rails_app/app/views/layouts/application.html.erb:2 -msgctxt "contexte" -msgid "salut" +msgctxt "Eminem" +msgid "I'm Slim Shady, yes, I'm the real Shady" +msgstr "" + +#: ../spec/support/rails_app/app/views/layouts/application.html.erb:5 +msgid "Before case" +msgstr "" + +#: ../spec/support/rails_app/app/views/layouts/application.html.erb:8 +msgid "After case" msgstr "" #: ../spec/support/rails_app/app/views/mailer/greetings.inky:4 @@ -61,8 +69,16 @@ msgstr "" #: ../spec/support/rails_app/app/views/layouts/application.html.erb:2 -msgctxt "contexte" -msgid "salut" +msgctxt "Eminem" +msgid "I'm Slim Shady, yes, I'm the real Shady" +msgstr "" + +#: ../spec/support/rails_app/app/views/layouts/application.html.erb:5 +msgid "Before case" +msgstr "" + +#: ../spec/support/rails_app/app/views/layouts/application.html.erb:8 +msgid "After case" msgstr "" #: ../spec/support/rails_app/tmp/translation/haml-gettext-00000000.rb:1 @@ -99,8 +115,16 @@ msgstr "" #: ../spec/support/rails_app/app/views/layouts/application.html.erb:2 -msgctxt "contexte" -msgid "salut" +msgctxt "Eminem" +msgid "I'm Slim Shady, yes, I'm the real Shady" +msgstr "" + +#: ../spec/support/rails_app/app/views/layouts/application.html.erb:5 +msgid "Before case" +msgstr "" + +#: ../spec/support/rails_app/app/views/layouts/application.html.erb:8 +msgid "After case" msgstr "" #: ../spec/support/rails_app/tmp/translation/haml-gettext-00000000.rb:1 diff --git a/translation.gemspec b/translation.gemspec index 67e08bb..242d381 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -18,7 +18,7 @@ Gem::Specification.new do |s| "source_code_uri" => "https://github.com/translation/rails" } - s.add_runtime_dependency 'gettext', '~> 3.2', '>= 3.2.5', '<= 3.4.2' + s.add_runtime_dependency 'gettext', '~> 3.2', '>= 3.2.5', '<= 3.4.3' s.add_development_dependency 'rake', '~> 12.0' s.add_development_dependency 'simplecov', '~> 0.11' From 35efaca714f3a791d7dbe04ab4aa64bbe1229cad Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Fri, 20 May 2022 16:24:25 +0200 Subject: [PATCH 52/92] Fix bad require --- lib/translation.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/translation.rb b/lib/translation.rb index 8d58f57..ef87d24 100644 --- a/lib/translation.rb +++ b/lib/translation.rb @@ -72,7 +72,7 @@ def require_gettext_dependencies require 'gettext/tools' require 'gettext/text_domain_manager' require 'gettext/tools/xgettext' - require "gettext/tools/parser/erubi" + require "gettext/tools/parser/erubi" if Gem::Version.new(GetText::VERSION) >= Gem::Version.new('3.4.3') end def add_parser_for_erb_source_formats(new_erb_formats) From 79749af6e8221427c05e202a56d3ab0289f1fcc1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Fri, 20 May 2022 16:39:29 +0200 Subject: [PATCH 53/92] Bump version to 1.32 + CHANGELOG --- CHANGELOG.md | 6 ++++++ translation.gemspec | 2 +- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 13cc263..dee3d84 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## [v1.32](https://github.com/translation/rails/releases/tag/v1.32) (2022-05-20) + +#### Fixes (bugs & defects): + + * Fix bad `html.erb` parsing when there is a `case` in it, using new gettext 3.4.3 Erubi parser. (cf. [ruby-gettext/gettext PR #91](https://github.com/ruby-gettext/gettext/pull/91)). + ## [v1.31](https://github.com/translation/rails/releases/tag/v1.31) (2022-04-04) #### Fixes (bugs & defects): diff --git a/translation.gemspec b/translation.gemspec index 242d381..6ec842a 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.31' + s.version = '1.32' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] From 269913c7d96811918c3875cb83d609d041447a93 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Fri, 20 May 2022 16:44:22 +0200 Subject: [PATCH 54/92] Remove "limitations" section that is now fixed --- README.md | 28 ---------------------------- 1 file changed, 28 deletions(-) diff --git a/README.md b/README.md index 29c4697..557676d 100644 --- a/README.md +++ b/README.md @@ -52,7 +52,6 @@ Table of contents * [Paths where locales are stored (not recommended)](#paths-where-locales-are-stored-not-recommended) * [GetText Object Class Monkey-Patching](#gettext-object-class-monkey-patching) * [Pure Ruby (without Rails)](#pure-ruby-without-rails) - * [Limitations](#limitations) * [Testing](#testing) * [Contributing](#contributing) * [List of clients for Translation.io](#list-of-clients-for-translationio) @@ -583,33 +582,6 @@ This gem was created specifically for Rails, but you can also use it in a pure R (Thanks [@kubaw](https://github.com/kubaw) for this snippet!) -## Limitations - -If you localize `.erb` files with the [GetText syntax](#gettext), please avoid -the use of `case` and `when` that are not correctly parsed by ERB. - -This syntax will break and your file will be ignored: - -```erb -<% case @state %> -<% when 'received' %> -``` - -Instead, use `if`/`elsif` or this `case` syntax: - -```erb -<% -case @state -when 'received' -%> -``` - -These are the related discussions: [ruby/erb#4](https://github.com/ruby/erb/issues/4) and [translation/rails#44](https://github.com/translation/rails/issues/44). - -There is currently an open PR ([ruby-gettext/gettext#91](https://github.com/ruby-gettext/gettext/pull/91)), switching ERB for [Erubi](https://github.com/jeremyevans/erubi), -that is waiting to be merged into GetText, but it may have unknown undesirable -side effects. - ## Testing To run the specs: From ceeee391aafdda019af2e09f34ad9bde0560dd4e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Fri, 16 Sep 2022 16:50:51 +0200 Subject: [PATCH 55/92] Better simpler CONTRIBUTING.md --- CONTRIBUTING.md | 4 ---- 1 file changed, 4 deletions(-) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 3f890ed..108230e 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -2,10 +2,6 @@ Feel free to contribute to this repository by creating a Pull Request. -Create an issue or reach us by email (contact@translation.io) before doing -the work if you want to increase the chances for your Pull Request to be -accepted. - ## Pull Request Process 1. Fork the repository. From c3b557d8d9fc2f2f11c5aabd9e1717a5837b7f54 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Thu, 6 Oct 2022 10:24:52 +0200 Subject: [PATCH 56/92] Update README with link to Angular package --- README.md | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/README.md b/README.md index 557676d..f16806e 100644 --- a/README.md +++ b/README.md @@ -58,6 +58,7 @@ Table of contents * [Ruby on Rails (Ruby)](#ruby-on-rails-ruby) * [Laravel (PHP)](#laravel-php) * [React, React Native and JavaScript](#react-react-native-and-javascript) + * [Angular](#angular) * [Others](#others) * [License](#license) @@ -630,6 +631,13 @@ Translation.io is directly integrated in the great * GitHub: https://github.com/translation/lingui * NPM: https://www.npmjs.com/package/@translation/lingui +### Angular + +Officially Supported on [https://translation.io/angular](https://translation.io/angular) + + * GitHub: https://github.com/translation/angular + * NPM: https://www.npmjs.com/package/@translation/angular + ### Others If you want to create a new client for your favorite language or framework, please read our From a9d1390219303e93a64a01adbef957f5fd0fbbf2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Fri, 7 Oct 2022 14:30:34 +0200 Subject: [PATCH 57/92] README: Update code syntax from three ticks to three tilds --- README.md | 112 +++++++++++++++++++++++++++--------------------------- 1 file changed, 56 insertions(+), 56 deletions(-) diff --git a/README.md b/README.md index f16806e..21a0351 100644 --- a/README.md +++ b/README.md @@ -68,7 +68,7 @@ Table of contents The default [Rails Internationalization API](http://guides.rubyonrails.org/i18n.html). -```ruby +~~~ruby # Regular t('inbox.title') @@ -77,11 +77,11 @@ t('inbox.message', count: n) # Interpolation t('inbox.hello', name: @user.name) -``` +~~~ With the source YAML file: -```yaml +~~~yaml en: inbox: title: 'Title to be translated' @@ -90,7 +90,7 @@ en: one: 'one message' other: '%{count} messages' hello: 'Hello %{name}' -``` +~~~ You can keep your source YAML file automatically updated using [i18n-tasks](https://github.com/glebm/i18n-tasks). @@ -102,7 +102,7 @@ that you use GetText to translate your application since it allows an easier and Moreover, you won't need to create and manage any YAML file since your code will be automatically scanned for any string to translate. -```ruby +~~~ruby # Regular _("Text to be translated") @@ -117,7 +117,7 @@ np_("context", "Singular text", "Plural text", number) # Interpolations _('%{city1} is bigger than %{city2}') % { city1: "NYC", city2: "BXL" } -``` +~~~ More information about GetText syntax [here](https://github.com/ruby-gettext/gettext#usage). @@ -125,28 +125,28 @@ More information about GetText syntax [here](https://github.com/ruby-gettext/get 1. Add the gem to your project's Gemfile: -```ruby +~~~ruby gem 'translation' -``` +~~~ 2. Create a new translation project [from the UI](https://translation.io). 3. Copy the initializer into your Rails app (`config/initializers/translation.rb`) The initializer looks like this: -```ruby +~~~ruby TranslationIO.configure do |config| config.api_key = 'abcdefghijklmnopqrstuvwxyz012345' config.source_locale = 'en' config.target_locales = ['fr', 'nl', 'de', 'es'] end -``` +~~~ 4. Initialize your project and push existing translations to Translation.io with: -```bash +~~~bash $ bundle exec rake translation:init -``` +~~~ If you need to add or remove languages in the future, please read our [documentation](https://translation.io/blog/adding-target-languages) about that. @@ -157,17 +157,17 @@ If you need to add or remove languages in the future, please read our To send new translatable keys/strings and get new translations from Translation.io, simply run: -```bash +~~~bash $ bundle exec rake translation:sync -``` +~~~ ### Sync and Show Purgeable If you need to find out what are the unused keys/strings from Translation.io, using the current branch as reference: -```bash +~~~bash $ bundle exec rake translation:sync_and_show_purgeable -``` +~~~ As the name says, this operation will also perform a sync at the same time. @@ -175,9 +175,9 @@ As the name says, this operation will also perform a sync at the same time. If you need to remove unused keys/strings from Translation.io, using the current branch as reference: -```bash +~~~bash $ bundle exec rake translation:sync_and_purge -``` +~~~ As the name says, this operation will also perform a sync at the same time. @@ -216,9 +216,9 @@ or another instance of your application. A custom language is always be derived from an [existing language](https://translation.io/docs/languages). Its structure should be like: -```ruby +~~~ruby "#{existing_language_code}-#{custom_text}" -``` +~~~ where `custom_text` can only contain alphabetic characters and `-`. @@ -250,13 +250,13 @@ You can find more information about this The easiest way to change the current locale is with `set_locale`. -```ruby +~~~ruby class ApplicationController < ActionController::Base before_action :set_locale [...] end -``` +~~~ First time the user will connect, it will automatically set the locale extracted from the user's browser `HTTP_ACCEPT_LANGUAGE` value, and keep it in the session between @@ -265,11 +265,11 @@ requests. Update the current locale by redirecting the user to https://yourdomain.com?locale=fr or even https://yourdomain.com/fr if you scoped your routes like this: -```ruby +~~~ruby scope "/:locale", :constraints => { locale: /[a-z]{2}/ } do resources :pages end -``` +~~~ The `set_locale` code is [here](https://github.com/translation/rails/blob/master/lib/translation_io/controller.rb#L3), feel free to override it with your own locale management. @@ -283,9 +283,9 @@ More examples here: https://translation.io/blog/set-current-locale-in-your-rails This command will change the locale for both [I18n (YAML)](#i18n-yaml) and [GetText](#gettext): -```ruby +~~~ruby I18n.locale = 'fr' -``` +~~~ You can call it several times in the same page if you want to switch between languages. @@ -306,27 +306,27 @@ translations as props when mounting the components. Assuming that you use [reactjs/react-rails](https://github.com/reactjs/react-rails), it would look like this if you want to use [I18n (YAML)](#i18n-yaml) syntax: -```erb +~~~erb <%= react_component('MyComponent", { :user_id => current_user.id, :i18n => YAML.load_file("config/locales/#{I18n.locale}.yml")[I18n.locale.to_s]["my_component"] }) %> -``` +~~~ Your `en.yml` should look like this: -```yaml +~~~yaml en: my_component: your_name: Your name title: Title -``` +~~~ You can also directly use the [GetText](#gettext) syntax: -```erb +~~~erb <%= react_component('MyComponent", { :user_id => current_user.id, @@ -336,7 +336,7 @@ react_component('MyComponent", { } }) %> -``` +~~~ In both case, in your React component, you can simply call `this.props.i18n.yourName` and your text will be localized with the current locale. @@ -368,9 +368,9 @@ Since this task can't be concurrently executed a queue but it returns an error under heavy load), we implemented this threadsafe readonly task: -```bash +~~~bash $ bundle exec rake translation:sync_readonly -``` +~~~ This task will prevent your CI to fail and still provide new translations. But be aware that it won't send new keys from your code to Translation.io so you @@ -387,24 +387,24 @@ Some options are described below but for an exhaustive list, please refer to [co If you want to only use YAML files and totally ignore GetText syntax, use: -```ruby +~~~ruby TranslationIO.configure do |config| ... config.disable_gettext = true ... end -``` +~~~ In contrast, if you only want to synchronize GetText files and leave the YAML files unchanged, use: -```ruby +~~~ruby TranslationIO.configure do |config| ... config.disable_yaml = true ... end -``` +~~~ ### Ignored YAML keys @@ -413,7 +413,7 @@ You can use the `ignored_key_prefixes` for that. For example: -```ruby +~~~ruby TranslationIO.configure do |config| ... config.ignored_key_prefixes = [ @@ -428,7 +428,7 @@ TranslationIO.configure do |config| ] ... end -``` +~~~ ### Custom localization key prefixes @@ -448,13 +448,13 @@ to add some more, use the `localization_key_prefixes` option. For example: -```ruby +~~~ruby TranslationIO.configure do |config| ... config.localization_key_prefixes = ['my_gem.date.formats'] ... end -``` +~~~ ### Source file formats (for GetText) @@ -467,7 +467,7 @@ If you are using GetText and you want to manage other file formats than: Just add them in your configuration file like this: -```ruby +~~~ruby TranslationIO.configure do |config| ... config.source_formats << 'rb2' @@ -476,33 +476,33 @@ TranslationIO.configure do |config| config.slim_source_formats << 'slim2' ... end -``` +~~~ ### Gems with GetText strings Public gems usually don't make use of GetText strings, but if you created and localized your own gems with the GetText syntax, you'll want to be able to synchronize them: -```ruby +~~~ruby TranslationIO.configure do |config| ... config.parsed_gems = ['your_gem_name'] ... end -``` +~~~ ### Paths where locales are stored (not recommended) You can specify where your GetText and YAML files are on disk: -```ruby +~~~ruby TranslationIO.configure do |config| ... config.locales_path = 'some/path' # defaults to config/locales/gettext config.yaml_locales_path = 'some/path' # defaults to config/locales ... end -``` +~~~ ### GetText Object Class Monkey-Patching @@ -512,27 +512,27 @@ This is made by extending the global `Object` class. You can disable the built-in `Object` monkey-patching if you prefer a more granular approach: -```ruby +~~~ruby TranslationIO.configure do |config| ... config.gettext_object_delegate = false ... end -``` +~~~ Don't forget to manually include the GetText methods where needed: -```ruby +~~~ruby class Contact < ApplicationRecord extend TranslationIO::Proxy end -``` +~~~ ## Pure Ruby (without Rails) This gem was created specifically for Rails, but you can also use it in a pure Ruby project by making some arrangements: -```ruby +~~~ruby require 'rubygems' require 'active_support/all' require 'yaml' @@ -579,7 +579,7 @@ This gem was created specifically for Rails, but you can also use it in a pure R config.target_locales = ['nl', 'de'] config.metadata_path = 'i18n/.translation_io' end -``` +~~~ (Thanks [@kubaw](https://github.com/kubaw) for this snippet!) @@ -587,9 +587,9 @@ This gem was created specifically for Rails, but you can also use it in a pure R To run the specs: -```bash +~~~bash $ bundle exec rspec -``` +~~~ ## Contributing From d990a89e2850cb24ea32c13186ead02a5f93af64 Mon Sep 17 00:00:00 2001 From: Didier Toussaint Date: Wed, 12 Oct 2022 09:41:15 +0200 Subject: [PATCH 58/92] Fix typos in README.md --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 21a0351..4eaa01c 100644 --- a/README.md +++ b/README.md @@ -308,7 +308,7 @@ it would look like this if you want to use [I18n (YAML)](#i18n-yaml) syntax: ~~~erb <%= -react_component('MyComponent", { +react_component("MyComponent", { :user_id => current_user.id, :i18n => YAML.load_file("config/locales/#{I18n.locale}.yml")[I18n.locale.to_s]["my_component"] }) @@ -328,7 +328,7 @@ You can also directly use the [GetText](#gettext) syntax: ~~~erb <%= -react_component('MyComponent", { +react_component("MyComponent", { :user_id => current_user.id, :i18n => { :your_name => _('Your name'), From 0fcf32e78acc76df89682b6e5a4e44fcdd2a7a88 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Thu, 20 Oct 2022 15:36:32 +0200 Subject: [PATCH 59/92] Wording --- README.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index 4eaa01c..9db624e 100644 --- a/README.md +++ b/README.md @@ -12,7 +12,7 @@ Use the official Rails syntax (with [YAML](#i18n-yaml) files) or use the [GetTex Write only the source text, and keep it synchronized with your translators on [Translation.io](https://translation.io). - + Translation.io interface @@ -23,7 +23,7 @@ Need help? [contact@translation.io](mailto:contact@translation.io) Table of contents ================= - * [Translation syntaxes](#translation-syntaxes) + * [Localization syntaxes](#localization-syntaxes) * [I18n (YAML)](#i18n-yaml) * [GetText](#gettext) * [Installation](#installation) @@ -62,7 +62,7 @@ Table of contents * [Others](#others) * [License](#license) -## Translation syntaxes +## Localization syntaxes ### I18n (YAML) From d74110717e768b7b9d943c86bd3e98fdc3a205f2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Fri, 21 Oct 2022 17:46:16 +0200 Subject: [PATCH 60/92] Update list of clients (README) --- README.md | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index 9db624e..5fa8ba8 100644 --- a/README.md +++ b/README.md @@ -597,11 +597,12 @@ Please read the [CONTRIBUTING](CONTRIBUTING.md) file. ## List of clients for Translation.io -These implementations were usually started by contributors for their own projects. -Some of them are officially supported by [Translation.io](https://translation.io) -and some are not yet supported. However, they are quite well documented. +The following clients are officially supported by [Translation.io](https://translation.io) +and are well documented. -Thanks a lot to these contributors for their hard work! +Some of these implementations (and other non-officially supported ones) +were started by contributors for their own translation projects. +We are thankful to all contributors for their hard work! ### Ruby on Rails (Ruby) From 00b788ff09751fafb0a8ee54509631bd3bd1a06c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Fri, 21 Oct 2022 18:18:06 +0200 Subject: [PATCH 61/92] README: table of contents in h2 --- README.md | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/README.md b/README.md index 5fa8ba8..44683ef 100644 --- a/README.md +++ b/README.md @@ -20,8 +20,7 @@ Write only the source text, and keep it synchronized with your translators on [T Need help? [contact@translation.io](mailto:contact@translation.io) -Table of contents -================= +== Table of contents * [Localization syntaxes](#localization-syntaxes) * [I18n (YAML)](#i18n-yaml) From 7ddde0dbd07fd6795504e74f2c8f4a7ece75ed26 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Fri, 21 Oct 2022 18:18:22 +0200 Subject: [PATCH 62/92] README: table of contents in h2 --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 44683ef..2d1c675 100644 --- a/README.md +++ b/README.md @@ -20,7 +20,7 @@ Write only the source text, and keep it synchronized with your translators on [T Need help? [contact@translation.io](mailto:contact@translation.io) -== Table of contents +## Table of contents * [Localization syntaxes](#localization-syntaxes) * [I18n (YAML)](#i18n-yaml) From 51ddc4331459801d829826ef6a5f6a4ee803ec6d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 24 Oct 2022 14:55:21 +0200 Subject: [PATCH 63/92] typo README --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 2d1c675..bbaf876 100644 --- a/README.md +++ b/README.md @@ -371,7 +371,7 @@ threadsafe readonly task: $ bundle exec rake translation:sync_readonly ~~~ -This task will prevent your CI to fail and still provide new translations. But +This task will prevent your CI from failing and still provide new translations. But be aware that it won't send new keys from your code to Translation.io so you still need to call `bundle exec rake translation:sync` at some point during development. From f4cca89749420ab3983e3d1cea0f0856868c1a80 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 24 Oct 2022 16:42:45 +0200 Subject: [PATCH 64/92] Better list of clients --- README.md | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/README.md b/README.md index bbaf876..2ee7971 100644 --- a/README.md +++ b/README.md @@ -605,7 +605,7 @@ We are thankful to all contributors for their hard work! ### Ruby on Rails (Ruby) -Officially Supported on [https://translation.io/rails](https://translation.io/rails) +Officially supported on [https://translation.io/rails](https://translation.io/rails) * GitHub: https://github.com/translation/rails * RubyGems: https://rubygems.org/gems/translation/ @@ -614,7 +614,7 @@ Credits: [@aurels](https://github.com/aurels), [@michaelhoste](https://github.co ### Laravel (PHP) -Officially Supported on [https://translation.io/laravel](https://translation.io/laravel) +Officially supported on [https://translation.io/laravel](https://translation.io/laravel) * GitHub: https://github.com/translation/laravel * Packagist: https://packagist.org/packages/tio/laravel @@ -623,7 +623,7 @@ Credits: [@armandsar](https://github.com/armandsar), [@michaelhoste](https://git ### React, React Native and JavaScript -Officially Supported on [https://translation.io/lingui](https://translation.io/lingui) +Officially supported on [https://translation.io/lingui](https://translation.io/lingui) Translation.io is directly integrated in the great [Lingui](https://lingui.js.org/) internationalization project. @@ -633,10 +633,12 @@ Translation.io is directly integrated in the great ### Angular -Officially Supported on [https://translation.io/angular](https://translation.io/angular) +Officially supported on [https://translation.io/angular](https://translation.io/angular) * GitHub: https://github.com/translation/angular * NPM: https://www.npmjs.com/package/@translation/angular + +Credits: [@SimonCorellia](https://github.com/SimonCorellia), [@didier-84](hthttps://github.com/didier-84), [@michaelhoste](https://github.com/michaelhoste) ### Others @@ -648,8 +650,8 @@ guide and use the special You can also use the more [traditional API](https://translation.io/docs/api). -Feel free to contact us on [contact@translation.io](mailto:contact@translation.io) if -you need some help or if you want to share your library. +Feel free to contact us on [contact@translation.io](mailto:contact@translation.io) +if you need some help or if you want to share your library. ## License From f5953a78be970e2d577e23747b778a8c56ab6fb4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 24 Oct 2022 21:47:46 +0200 Subject: [PATCH 65/92] Typo in link --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 2ee7971..18a79b8 100644 --- a/README.md +++ b/README.md @@ -638,7 +638,7 @@ Officially supported on [https://translation.io/angular](https://translation.io/ * GitHub: https://github.com/translation/angular * NPM: https://www.npmjs.com/package/@translation/angular -Credits: [@SimonCorellia](https://github.com/SimonCorellia), [@didier-84](hthttps://github.com/didier-84), [@michaelhoste](https://github.com/michaelhoste) +Credits: [@SimonCorellia](https://github.com/SimonCorellia), [@didier-84](https://github.com/didier-84), [@michaelhoste](https://github.com/michaelhoste) ### Others From 3f775c1456433aeb0556770aee1c2af3b70eef74 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 7 Nov 2022 16:18:57 +0100 Subject: [PATCH 66/92] Match I18n fallbacks in GetText (fixes #48) (#50) * Refactor railties (use `prepend` instead of replacing method) * GetText follows the fallbacks of i18n/YAML (`Locale.set_current(*fallback_locales)` instead of `Locale.set_current(locale)`) * Create GetText directory with source PO/MO files to avoid relying only on POT file when other existing fallbacks failed. --- .../base_operation/save_new_po_files_step.rb | 33 +++++- lib/translation_io/client/init_operation.rb | 2 +- lib/translation_io/client/sync_operation.rb | 2 +- lib/translation_io/railtie.rb | 31 ++++-- .../save_new_po_files_step_spec.rb | 104 +++++++++++++++++- 5 files changed, 154 insertions(+), 18 deletions(-) diff --git a/lib/translation_io/client/base_operation/save_new_po_files_step.rb b/lib/translation_io/client/base_operation/save_new_po_files_step.rb index 7f17675..ff96098 100644 --- a/lib/translation_io/client/base_operation/save_new_po_files_step.rb +++ b/lib/translation_io/client/base_operation/save_new_po_files_step.rb @@ -2,7 +2,8 @@ module TranslationIO class Client class BaseOperation class SaveNewPoFilesStep - def initialize(target_locales, locales_path, parsed_response) + def initialize(source_locale, target_locales, locales_path, parsed_response) + @source_locale = source_locale @target_locales = target_locales @locales_path = locales_path @parsed_response = parsed_response @@ -25,8 +26,38 @@ def run end end + create_source_po(text_domain) + return self end + + # Create source locale PO file, with identical source and target + # => Useful for correct fallbacks (cf. discussion https://github.com/translation/rails/issues/48) + def create_source_po(text_domain) + source_locale = Locale::Tag.parse(@source_locale).to_s + + pot_path = File.join(@locales_path, "#{text_domain}.pot") + po_path = File.join(@locales_path, source_locale, "#{text_domain}.po") + + FileUtils.mkdir_p(File.dirname(po_path)) + FileUtils.rm(po_path) if File.exist?(po_path) + + # Generate source PO from POT and parse it + GetText::Tools::MsgInit.run('-i', pot_path, '-o', po_path, '-l', source_locale, '--no-translator') + po_entries = GetText::PO.new + GetText::POParser.new.parse(File.read(po_path), po_entries) + + # Fill with same target as source and save it + po_entries.each do |po_entry| + if po_entry.msgid != '' # header + po_entry.msgstr = [po_entry.msgid, po_entry.msgid_plural].compact.join("\000") + end + end + + File.open(po_path, 'wb') do |file| + file.write(po_entries.to_s) + end + end end end end diff --git a/lib/translation_io/client/init_operation.rb b/lib/translation_io/client/init_operation.rb index f7f9ec6..5eb4645 100644 --- a/lib/translation_io/client/init_operation.rb +++ b/lib/translation_io/client/init_operation.rb @@ -46,7 +46,7 @@ def run if !parsed_response.nil? if !config.disable_gettext - BaseOperation::SaveNewPoFilesStep.new(target_locales, locales_path, parsed_response).run + BaseOperation::SaveNewPoFilesStep.new(source_locale, target_locales, locales_path, parsed_response).run BaseOperation::CreateNewMoFilesStep.new(locales_path).run end diff --git a/lib/translation_io/client/sync_operation.rb b/lib/translation_io/client/sync_operation.rb index 42d51d2..a670f2c 100644 --- a/lib/translation_io/client/sync_operation.rb +++ b/lib/translation_io/client/sync_operation.rb @@ -54,7 +54,7 @@ def run(options = {}) if !parsed_response.nil? if !config.disable_gettext - BaseOperation::SaveNewPoFilesStep.new(target_locales, locales_path, parsed_response).run + BaseOperation::SaveNewPoFilesStep.new(source_locale, target_locales, locales_path, parsed_response).run BaseOperation::CreateNewMoFilesStep.new(locales_path).run end diff --git a/lib/translation_io/railtie.rb b/lib/translation_io/railtie.rb index 341b508..63c2458 100644 --- a/lib/translation_io/railtie.rb +++ b/lib/translation_io/railtie.rb @@ -1,5 +1,6 @@ require 'i18n' require 'i18n/config' +require "i18n/backend/fallbacks" module TranslationIO class Railtie < Rails::Railtie @@ -20,20 +21,32 @@ class Railtie < Rails::Railtie end end -module I18n - class Config - def locale=(locale) - I18n.enforce_available_locales!(locale) if I18n.respond_to?(:enforce_available_locales!) - @locale = locale.to_sym rescue nil +### +# Set GetText/Locale current locale based on I18n.locale +### +module I18nConfigExtension + def locale=(*args) + super - if defined?(GetText) - GetText.set_current_locale(locale.to_s.gsub('-', '_').to_sym) - end + if defined? Locale + # GetText/Locale already uses default fallbacks ("en-us-custom" => "en-us" => "en-custom" => "en") + # But we want to add them custom fallbacks from I18n (ex: "fr" => "nl" => "en") + # cf. https://github.com/translation/rails/issues/48 + fallback_locales = I18n.fallbacks[I18n.locale].collect { |l| l.to_s.gsub('-', '_').to_sym } + + Locale.set_current(*fallback_locales) end end end -if defined?(GetText) +I18n::Config.prepend I18nConfigExtension + +### +# Monkey-Patch GetText to : +# * Ignore GetText warnings +# * Don't stop code parsing if a file is badly formatted + message +### +if defined? GetText module GetText class POParser < Racc::Parser def initialize diff --git a/spec/translation/client/base_operation/save_new_po_files_step_spec.rb b/spec/translation/client/base_operation/save_new_po_files_step_spec.rb index bd91d7a..ddb6605 100644 --- a/spec/translation/client/base_operation/save_new_po_files_step_spec.rb +++ b/spec/translation/client/base_operation/save_new_po_files_step_spec.rb @@ -3,19 +3,111 @@ describe TranslationIO::Client::BaseOperation::SaveNewPoFilesStep do it do + source_locale = 'en' target_locales = ['fr', 'nl'] locales_path = 'tmp' + pot_path = File.join(locales_path, "app.pot") + FileUtils.rm(pot_path) if File.exist?(pot_path) + FileUtils.mkdir_p(File.dirname(pot_path)) + + # Starting with 3.3.9, `red-datasets` must be included as dependency to get plural forms. + # We don't include it with this gem since plural forms are generated by Translation.io with + # its own plural database updates from CLDR, and then correct PO files are sent back to client. + if Gem::Version.new(GetText::VERSION) >= Gem::Version.new('3.3.9') + en_plural_forms = 'nplurals=; plural=;' + else + en_plural_forms = 'nplurals=2; plural=n != 1;' + end + + pot_data = <<-EOS +msgid "" +msgstr "" +"Project-Id-Version: PACKAGE VERSION\\n" +"Report-Msgid-Bugs-To: \\n" +"POT-Creation-Date: 2014-06-05 17:07+0200\\n" +"Last-Translator: FULL NAME \\n" +"Language-Team: LANGUAGE \\n" +"Language: \\n" +"MIME-Version: 1.0\\n" +"Content-Type: text/plain; charset=UTF-8\\n" +"Content-Transfer-Encoding: 8bit\\n" +"Plural-Forms: nplurals=INTEGER; plural=EXPRESSION;\\n" + +msgid "Hello world" +msgstr "" + +msgid "Hello young man" +msgid_plural "Hello young men" +msgstr[0] "" +msgstr[1] "" +EOS + + File.open(pot_path, 'wb') do |file| + file.write(pot_data) + end + + po_data_fr = <<-EOS +msgid "" +msgstr "" + +msgid "Hello world" +msgstr "Bonjour le monde" + +msgid "Hello young man" +msgid_plural "Hello young men" +msgstr[0] "Bonjour jeune homme" +msgstr[1] "Bonjour jeunes hommes" +EOS + + po_data_nl = <<-EOS +msgid "" +msgstr "" + +msgid "Hello world" +msgstr "Hallo wereld" + +msgid "Hello young man" +msgid_plural "Hello young men" +msgstr[0] "Hallo jongeman" +msgstr[1] "Hallo jonge mannen" +EOS + parsed_response = { - 'po_data_fr' => '', - 'po_data_nl' => '' + 'po_data_fr' => po_data_fr, + 'po_data_nl' => po_data_nl } - operation_step = TranslationIO::Client::BaseOperation::SaveNewPoFilesStep.new(target_locales, locales_path, parsed_response) + operation_step = TranslationIO::Client::BaseOperation::SaveNewPoFilesStep.new(source_locale, target_locales, locales_path, parsed_response) operation_step.run - File.read('tmp/fr/app.po').should == '' - File.read('tmp/nl/app.po').should == '' - end + # Check that target PO files are correctly saved + File.read('tmp/fr/app.po').should == po_data_fr + File.read('tmp/nl/app.po').should == po_data_nl + + # Check that source PO is correctly completed (target = source) and saved + File.read('tmp/en/app.po').should == <<-EOS +msgid "" +msgstr "" +"Project-Id-Version: PACKAGE VERSION\\n" +"Report-Msgid-Bugs-To: \\n" +"POT-Creation-Date: 2014-06-05 17:07+0200\\n" +"Last-Translator: FULL NAME \\n" +"Language-Team: English\\n" +"Language: en\\n" +"MIME-Version: 1.0\\n" +"Content-Type: text/plain; charset=UTF-8\\n" +"Content-Transfer-Encoding: 8bit\\n" +"Plural-Forms: #{en_plural_forms}\\n" +"\\n" +msgid "Hello world" +msgstr "Hello world" + +msgid "Hello young man" +msgid_plural "Hello young men" +msgstr[0] "Hello young man" +msgstr[1] "Hello young men" +EOS + end end From 0ebca715aa80064487e78dbe5d1d41292f4e5183 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 7 Nov 2022 16:39:38 +0100 Subject: [PATCH 67/92] Bump version + changelog --- CHANGELOG.md | 9 +++++++++ translation.gemspec | 2 +- 2 files changed, 10 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index dee3d84..5f44a59 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,14 @@ # Changelog +## [v1.33](https://github.com/translation/rails/releases/tag/v1.33) (2022-11-07) + +#### New features: + + * Match I18n fallbacks in GetText (cf. [#48](https://github.com/translation/issues/48) and [#50](https://github.com/translation/pull/50)). Thanks @ryanb! + +**Important information:** a new directory with PO/MO files for the source language will be created in your `locales/gettext` directory. +Don't worry, it's expected: the purpose is to unify fallback management. + ## [v1.32](https://github.com/translation/rails/releases/tag/v1.32) (2022-05-20) #### Fixes (bugs & defects): diff --git a/translation.gemspec b/translation.gemspec index 6ec842a..872f31a 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.32' + s.version = '1.33' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] From 57808a0b370c6400b459d797a462574876cb1bf6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 16 Nov 2022 14:35:13 +0100 Subject: [PATCH 68/92] Fix plural rule in source PO file by manually adding it (for GetText >= 3.3.9) (#53) * Manually manage plural rules for source PO file Manually manage plural rules for source PO file when GetText >= 3.3.9 and the introduction of optional `red-datasets` dependency for plural rules --- .../base_operation/save_new_po_files_step.rb | 14 +++++++++++--- .../base_operation/save_new_po_files_step_spec.rb | 11 +++-------- 2 files changed, 14 insertions(+), 11 deletions(-) diff --git a/lib/translation_io/client/base_operation/save_new_po_files_step.rb b/lib/translation_io/client/base_operation/save_new_po_files_step.rb index ff96098..d68204d 100644 --- a/lib/translation_io/client/base_operation/save_new_po_files_step.rb +++ b/lib/translation_io/client/base_operation/save_new_po_files_step.rb @@ -34,19 +34,27 @@ def run # Create source locale PO file, with identical source and target # => Useful for correct fallbacks (cf. discussion https://github.com/translation/rails/issues/48) def create_source_po(text_domain) - source_locale = Locale::Tag.parse(@source_locale).to_s + source_locale = Locale::Tag.parse(@source_locale) pot_path = File.join(@locales_path, "#{text_domain}.pot") - po_path = File.join(@locales_path, source_locale, "#{text_domain}.po") + po_path = File.join(@locales_path, source_locale.to_s, "#{text_domain}.po") FileUtils.mkdir_p(File.dirname(po_path)) FileUtils.rm(po_path) if File.exist?(po_path) # Generate source PO from POT and parse it - GetText::Tools::MsgInit.run('-i', pot_path, '-o', po_path, '-l', source_locale, '--no-translator') + GetText::Tools::MsgInit.run('-i', pot_path, '-o', po_path, '-l', source_locale.to_s, '--no-translator') po_entries = GetText::PO.new GetText::POParser.new.parse(File.read(po_path), po_entries) + # With GetText after 3.3.9 and the introduction of optional `red-datasets` dependency, we need to complete the plural forms manually + # Source languages must have only 2 plural forms, and only 2 different pluralization rules exist for these languages + if %w(ak am as bn fa fr gu hi hy kn ln mg nso pa si ti zu).include?(source_locale.language) + po_entries[''].msgstr.gsub!('Plural-Forms: nplurals=; plural=;', 'Plural-Forms: nplurals=2; plural=n > 1;') # 0 and 1 are singular + else + po_entries[''].msgstr.gsub!('Plural-Forms: nplurals=; plural=;', 'Plural-Forms: nplurals=2; plural=n != 1;') # only 1 is singular + end + # Fill with same target as source and save it po_entries.each do |po_entry| if po_entry.msgid != '' # header diff --git a/spec/translation/client/base_operation/save_new_po_files_step_spec.rb b/spec/translation/client/base_operation/save_new_po_files_step_spec.rb index ddb6605..1fbef5e 100644 --- a/spec/translation/client/base_operation/save_new_po_files_step_spec.rb +++ b/spec/translation/client/base_operation/save_new_po_files_step_spec.rb @@ -11,14 +11,9 @@ FileUtils.rm(pot_path) if File.exist?(pot_path) FileUtils.mkdir_p(File.dirname(pot_path)) - # Starting with 3.3.9, `red-datasets` must be included as dependency to get plural forms. - # We don't include it with this gem since plural forms are generated by Translation.io with - # its own plural database updates from CLDR, and then correct PO files are sent back to client. - if Gem::Version.new(GetText::VERSION) >= Gem::Version.new('3.3.9') - en_plural_forms = 'nplurals=; plural=;' - else - en_plural_forms = 'nplurals=2; plural=n != 1;' - end + # Completed with either GetText (before 3.3.9 and the introduction of optional `red-datasets` dependency) + # or this Gem (after 3.3.9 because the default plural rule without optional gem was then 'nplurals=; plural=;'). + en_plural_forms = 'nplurals=2; plural=n != 1;' pot_data = <<-EOS msgid "" From 78e59d32b880a06a1f8d3c0da2265ecfa7d1f3ec Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 16 Nov 2022 14:37:27 +0100 Subject: [PATCH 69/92] Bump version 1.33 + changelog --- CHANGELOG.md | 6 ++++++ translation.gemspec | 2 +- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 5f44a59..a2b38a9 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## [v1.34](https://github.com/translation/rails/releases/tag/v1.34) (2022-11-16) + +#### Fixes (bugs & defects): + + * Fix plural rule in source PO file by manually adding it (for GetText >= 3.3.9) + ## [v1.33](https://github.com/translation/rails/releases/tag/v1.33) (2022-11-07) #### New features: diff --git a/translation.gemspec b/translation.gemspec index 872f31a..5c0fb72 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.33' + s.version = '1.34' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] From 1de0f524ae334de0fdbccd5550d57ae890b8908d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Thu, 12 Jan 2023 13:55:10 +0100 Subject: [PATCH 70/92] Fix links in changelog --- CHANGELOG.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index a2b38a9..ce455ad 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -10,7 +10,7 @@ #### New features: - * Match I18n fallbacks in GetText (cf. [#48](https://github.com/translation/issues/48) and [#50](https://github.com/translation/pull/50)). Thanks @ryanb! + * Match I18n fallbacks in GetText (cf. [#48](https://github.com/translation/rails/issues/48) and [#50](https://github.com/translation/rails/pull/50)). Thanks @ryanb! **Important information:** a new directory with PO/MO files for the source language will be created in your `locales/gettext` directory. Don't worry, it's expected: the purpose is to unify fallback management. From d9272e463527ba7c3e740676b0b6627ed7990dae Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Thu, 12 Jan 2023 14:09:55 +0100 Subject: [PATCH 71/92] Add Ruby 3.2 to testing matrix + Update test.yml to really test "3.0" and not 3 that is transformed to "3.2" --- .github/workflows/test.yml | 25 +++++++++++++------------ 1 file changed, 13 insertions(+), 12 deletions(-) diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index f8f7572..fecf1cd 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -9,25 +9,26 @@ jobs: fail-fast: false matrix: ruby: - - 2.2 - - 2.3 - - 2.4 - - 2.5 - - 2.6 - - 2.7 - - 3.0 - - 3.1 - - jruby-9.1.17.0 + - '2.2' + - '2.3' + - '2.4' + - '2.5' + - '2.6' + - '2.7' + - '3.0' + - '3.1' + - '3.2' + - 'jruby-9.1.17.0' gemfile: - lowest - latest exclude: # Ruby > 2.6 removed BigDecimal.new which was used on Rails 4.1 (removed with Rails 4.2 though) - - ruby: 2.7 + - ruby: '2.7' gemfile: lowest - - ruby: 3.0 + - ruby: '3.0' gemfile: lowest - - ruby: 3.1 + - ruby: '3.1' gemfile: lowest env: BUNDLE_GEMFILE: ${{ github.workspace }}/gemfiles/${{ matrix.gemfile }}.gemfile From ff737a0b8ad129ff64a5268cc37f68df2a3b055f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Thu, 12 Jan 2023 14:13:03 +0100 Subject: [PATCH 72/92] Fix `File.exists?` to `File.exist` (compatibility with Ruby 3.2) --- .github/workflows/test.yml | 2 ++ .../client/sync_operation/apply_yaml_source_edits_step.rb | 2 +- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index fecf1cd..4d31b13 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -30,6 +30,8 @@ jobs: gemfile: lowest - ruby: '3.1' gemfile: lowest + - ruby: '3.2' + gemfile: lowest env: BUNDLE_GEMFILE: ${{ github.workspace }}/gemfiles/${{ matrix.gemfile }}.gemfile CC_TEST_REPORTER_ID: 945dfb58a832d233a3caeb84e3e6d3be212e8c7abcb48117fce63b9adcb43647 diff --git a/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb b/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb index d6ed93c..d55c024 100644 --- a/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb +++ b/lib/translation_io/client/sync_operation/apply_yaml_source_edits_step.rb @@ -103,7 +103,7 @@ def apply_gem_source_edit(source_edit) # Source yaml file like config/locales/en.yml yaml_file_path = File.expand_path(File.join(TranslationIO.config.yaml_locales_path, "#{@source_locale}.yml")) - if File.exists?(yaml_file_path) + if File.exist?(yaml_file_path) # Complete existing hash if YAML file already exists existing_yaml_source = @yaml_sources.detect { |y_s| normalize_path(y_s[:yaml_file_path]) == normalize_path(yaml_file_path) } yaml_flat_hash = existing_yaml_source[:yaml_flat_hash] From ca482f71701644c6c7ffa17de5cfd3a9d79e53b6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Thu, 12 Jan 2023 14:21:49 +0100 Subject: [PATCH 73/92] Changelog + Bump version to 1.35 --- CHANGELOG.md | 6 ++++++ translation.gemspec | 20 ++++++++++---------- 2 files changed, 16 insertions(+), 10 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index ce455ad..cbdc6b8 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## [v1.35](https://github.com/translation/rails/releases/tag/v1.35) (2023-01-12) + +#### Fixes (bugs & defects): + + * Compatibility with Ruby 3.2 (Fix `File.exists?` to `File.exist?`) + ## [v1.34](https://github.com/translation/rails/releases/tag/v1.34) (2022-11-16) #### Fixes (bugs & defects): diff --git a/translation.gemspec b/translation.gemspec index 5c0fb72..bdedb10 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -1,14 +1,14 @@ Gem::Specification.new do |s| - s.name = 'translation' - s.summary = 'Localize your app with YAML or GetText. Synchronize with your translators on Translation.io.' - s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' - s.homepage = 'https://translation.io' - s.email = 'contact@translation.io' - s.version = '1.34' - s.authors = ['Michael Hoste', 'Aurelien Malisart'] - s.license = "MIT" - s.require_paths = ["lib"] - s.files = Dir["lib/**/*"] + ['README.md'] + s.name = 'translation' + s.summary = 'Localize your app with YAML or GetText. Synchronize with your translators on Translation.io.' + s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' + s.homepage = 'https://translation.io' + s.email = 'contact@translation.io' + s.version = '1.35' + s.authors = ['Michael Hoste', 'Aurelien Malisart'] + s.license = "MIT" + s.require_paths = ["lib"] + s.files = Dir["lib/**/*"] + ['README.md'] s.metadata = { "bug_tracker_uri" => "https://github.com/translation/rails/issues", From 79a96b384ab2548cffbdc68a24cb94caba7e3e42 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Tue, 7 Feb 2023 11:00:41 +0100 Subject: [PATCH 74/92] Update README with direct "translation.io/rails" link --- README.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index 18a79b8..1f7fbaa 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,4 @@ -# [Translation.io](https://translation.io) client for Ruby on Rails +# [Translation.io](https://translation.io/rails) client for Ruby on Rails [![Software License](https://img.shields.io/badge/license-MIT-brightgreen.svg?style=flat-square)](LICENSE) [![Build Status](https://github.com/translation/rails/actions/workflows/test.yml/badge.svg?branch=master)](https://github.com/translation/rails/actions/workflows/test.yml) @@ -10,7 +10,7 @@ Add this gem to localize your **Ruby on Rails** application. Use the official Rails syntax (with [YAML](#i18n-yaml) files) or use the [GetText](#gettext) syntax. -Write only the source text, and keep it synchronized with your translators on [Translation.io](https://translation.io). +Write only the source text, and keep it synchronized with your translators on [Translation.io](https://translation.io/rails). Translation.io interface @@ -128,7 +128,7 @@ More information about GetText syntax [here](https://github.com/ruby-gettext/get gem 'translation' ~~~ - 2. Create a new translation project [from the UI](https://translation.io). + 2. Create a new translation project [from the UI](https://translation.io/rails). 3. Copy the initializer into your Rails app (`config/initializers/translation.rb`) The initializer looks like this: From 96c8974d6ec0739e9c74f90469418c3780d07fa5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 15 Feb 2023 16:22:37 +0100 Subject: [PATCH 75/92] Update Lingui URL --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 1f7fbaa..8201801 100644 --- a/README.md +++ b/README.md @@ -348,7 +348,7 @@ In both case, in your React component, you can simply call ### Using our official React & JavaScript package As Translation.io is directly integrated in the great -[Lingui](https://lingui.js.org/) internationalization framework, +[Lingui](https://lingui.dev/) internationalization framework, you can also consider frontend localization as a completely different localization project. @@ -626,7 +626,7 @@ Credits: [@armandsar](https://github.com/armandsar), [@michaelhoste](https://git Officially supported on [https://translation.io/lingui](https://translation.io/lingui) Translation.io is directly integrated in the great -[Lingui](https://lingui.js.org/) internationalization project. +[Lingui](https://lingui.dev/) internationalization project. * GitHub: https://github.com/translation/lingui * NPM: https://www.npmjs.com/package/@translation/lingui From 5b5d4774055081eb439b15aab846fe6080778199 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Sun, 26 Mar 2023 17:23:39 +0200 Subject: [PATCH 76/92] Fix `translation.io/usage` to `translation.io/rails/usage` and many remaining `http://` to `https://` --- README.md | 10 +++++----- lib/translation_io/extractor.rb | 2 +- lib/translation_io/tasks.rb | 2 +- spec/translation/client_spec.rb | 4 ++-- translation.gemspec | 2 +- 5 files changed, 10 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index 8201801..855efc3 100644 --- a/README.md +++ b/README.md @@ -65,7 +65,7 @@ Need help? [contact@translation.io](mailto:contact@translation.io) ### I18n (YAML) -The default [Rails Internationalization API](http://guides.rubyonrails.org/i18n.html). +The default [Rails Internationalization API](https://guides.rubyonrails.org/i18n.html). ~~~ruby # Regular @@ -274,7 +274,7 @@ The `set_locale` code is [here](https://github.com/translation/rails/blob/master feel free to override it with your own locale management. Don't forget to define your available locales with -[I18n.available_locales](http://guides.rubyonrails.org/i18n.html#setup-the-rails-application-for-internationalization). +[I18n.available_locales](https://guides.rubyonrails.org/i18n.html#setup-the-rails-application-for-internationalization). More examples here: https://translation.io/blog/set-current-locale-in-your-rails-app @@ -461,8 +461,8 @@ If you are using GetText and you want to manage other file formats than: * `rb`, `ruby` and `rabl` for Ruby. * `erb` and `inky` for Ruby templating. - * `haml` and `mjmlhaml` for [HAML](http://haml.info/). - * `slim` and `mjmlslim` for [SLIM](http://slim-lang.com/). + * `haml` and `mjmlhaml` for [HAML](https://haml.info/). + * `slim` and `mjmlslim` for [SLIM](https://github.com/slim-template/slim). Just add them in your configuration file like this: @@ -656,6 +656,6 @@ if you need some help or if you want to share your library. ## License The [translation gem](https://rubygems.org/gems/translation) in released under MIT license by -[Aurélien Malisart](http://aurelien.malisart.be) and [Michaël Hoste](https://80limit.com) (see [LICENSE](LICENSE) file). +[Aurélien Malisart](https://aurelien.malisart.be) and [Michaël Hoste](https://80limit.com) (see [LICENSE](LICENSE) file). (c) [https://translation.io](https://translation.io) / [contact@translation.io](mailto:contact@translation.io) diff --git a/lib/translation_io/extractor.rb b/lib/translation_io/extractor.rb index c45a7a7..81eaa2f 100644 --- a/lib/translation_io/extractor.rb +++ b/lib/translation_io/extractor.rb @@ -1,7 +1,7 @@ module TranslationIO module Extractor # visual: https://www.debuggex.com/r/fYSQ-jwQfTjhhE6T - # .*? is non-greedy (lazy) match : http://stackoverflow.com/a/1919995/1243212 + # .*? is non-greedy (lazy) match : https://stackoverflow.com/a/1919995/1243212 REGEXP_INSIDE_1 = '\s*(?:\[?(?:(?:(?:".*?")|(?:\'.*?\'))\s*?,?\s*?){1}\]?)\s*?' REGEXP_INSIDE_2 = '\s*(?:\[?(?:(?:(?:".*?")|(?:\'.*?\'))\s*?,?\s*?){2}\]?),?\s*?.*?\s*' REGEXP_INSIDE_2B = '\s*(?:\[?(?:(?:(?:".*?")|(?:\'.*?\'))\s*?,?\s*?){2}\]?)\s*?' diff --git a/lib/translation_io/tasks.rb b/lib/translation_io/tasks.rb index 53551c0..e809a0b 100644 --- a/lib/translation_io/tasks.rb +++ b/lib/translation_io/tasks.rb @@ -50,7 +50,7 @@ def client_ready? true else TranslationIO.info("[Error] Can't configure client. Did you set up the initializer?\n"\ - "Read usage instructions here : http://translation.io/usage") + "Read usage instructions here : https://translation.io/rails/usage") false end end diff --git a/spec/translation/client_spec.rb b/spec/translation/client_spec.rb index 48a126e..9033d0b 100644 --- a/spec/translation/client_spec.rb +++ b/spec/translation/client_spec.rb @@ -2,12 +2,12 @@ describe TranslationIO::Client do before :each do - @client = TranslationIO::Client.new('4242', 'http://bidule.com/api') + @client = TranslationIO::Client.new('4242', 'https://bidule.com/api') end it do @client.api_key.should == '4242' - @client.endpoint.should == 'http://bidule.com/api' + @client.endpoint.should == 'https://bidule.com/api' end it do diff --git a/translation.gemspec b/translation.gemspec index bdedb10..ef9828b 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -13,7 +13,7 @@ Gem::Specification.new do |s| s.metadata = { "bug_tracker_uri" => "https://github.com/translation/rails/issues", "changelog_uri" => "https://github.com/translation/rails/blob/master/CHANGELOG.md", - "documentation_uri" => "https://translation.io/usage", + "documentation_uri" => "https://translation.io/rails/usage", "homepage_uri" => "https://translation.io", "source_code_uri" => "https://github.com/translation/rails" } From c8e576fd5d5bad05f659d9100b1e43c4d88d8679 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 26 Apr 2023 17:53:46 +0200 Subject: [PATCH 77/92] Init cleanup: keep YAML files and keys from locales that are not in the configuration file. (#54) * Don't delete unmanaged locales YAML files when init new project * Add spec to check that cleanup don't remove ignored target languages --- .../init_operation/cleanup_yaml_files_step.rb | 39 +++++++++---------- lib/translation_io/yaml_entry.rb | 4 +- .../cleanup_yaml_files_step_spec.rb | 18 ++++++++- 3 files changed, 36 insertions(+), 25 deletions(-) diff --git a/lib/translation_io/client/init_operation/cleanup_yaml_files_step.rb b/lib/translation_io/client/init_operation/cleanup_yaml_files_step.rb index 13ec831..ef315a4 100644 --- a/lib/translation_io/client/init_operation/cleanup_yaml_files_step.rb +++ b/lib/translation_io/client/init_operation/cleanup_yaml_files_step.rb @@ -12,30 +12,28 @@ def initialize(source_locale, target_locales, yaml_file_paths, yaml_locales_path def run @yaml_file_paths.each do |locale_file_path| if locale_file_removable?(locale_file_path) - if File.exist?(locale_file_path) - content_hash = TranslationIO.yaml_load(File.read(locale_file_path)) || {} - source_content_hash = content_hash.select { |k| k.to_s == @source_locale.to_s } + content_hash = TranslationIO.yaml_load(File.read(locale_file_path)) || {} + source_content_hash = content_hash.reject { |k| k.to_s.in?(@target_locales.collect(&:to_s)) } - if source_content_hash.empty? - TranslationIO.info "Removing #{locale_file_path}", 2, 2 - FileUtils.rm(locale_file_path) - elsif content_hash != source_content_hash # in case of mixed languages in source YAML file - TranslationIO.info "Rewriting #{locale_file_path}", 2, 2 + if source_content_hash.empty? + TranslationIO.info "Removing #{locale_file_path}", 2, 2 + FileUtils.rm(locale_file_path) + elsif content_hash != source_content_hash # in case of mixed languages in source YAML file + TranslationIO.info "Rewriting #{locale_file_path}", 2, 2 - if TranslationIO.config.yaml_line_width - file_content = source_content_hash.to_yaml(:line_width => TranslationIO.config.yaml_line_width) - else - file_content = source_content_hash.to_yaml - end + if TranslationIO.config.yaml_line_width + file_content = source_content_hash.to_yaml(:line_width => TranslationIO.config.yaml_line_width) + else + file_content = source_content_hash.to_yaml + end - file_content = file_content.gsub(/ $/, '') # remove trailing spaces + file_content = file_content.gsub(/ $/, '') # remove trailing spaces - File.open(locale_file_path, 'wb') do |file| - file.write(file_content) - end - else - # don't touch source + File.open(locale_file_path, 'wb') do |file| + file.write(file_content) end + else + # don't touch source end end end @@ -44,6 +42,7 @@ def run private def locale_file_removable?(locale_file_path) + exists = File.exist?(locale_file_path) in_project = locale_file_path_in_project?(locale_file_path) protected_file = @target_locales.any? do |target_locale| @@ -55,7 +54,7 @@ def locale_file_removable?(locale_file_path) paths.include?(TranslationIO.normalize_path(locale_file_path)) end - in_project && !protected_file + exists && in_project && !protected_file end def locale_file_path_in_project?(locale_file_path) diff --git a/lib/translation_io/yaml_entry.rb b/lib/translation_io/yaml_entry.rb index 5c99b34..873b239 100644 --- a/lib/translation_io/yaml_entry.rb +++ b/lib/translation_io/yaml_entry.rb @@ -39,9 +39,7 @@ def localization?(key, value) end def localization_prefix?(key) - localization_key_prefixes.any? do |prefix| - key_without_locale(key).match(/^#{Regexp.escape(prefix)}\b/) != nil - end + localization_key_prefixes.any? { |prefix| key_without_locale(key).match(/^#{Regexp.escape(prefix)}\b/) != nil } end private diff --git a/spec/translation/client/init_operation/cleanup_yaml_files_step_spec.rb b/spec/translation/client/init_operation/cleanup_yaml_files_step_spec.rb index 2017c4e..b76c53e 100644 --- a/spec/translation/client/init_operation/cleanup_yaml_files_step_spec.rb +++ b/spec/translation/client/init_operation/cleanup_yaml_files_step_spec.rb @@ -2,7 +2,7 @@ describe TranslationIO::Client::InitOperation::CleanupYamlFilesStep do - it 'removes bad target files' do + it 'removes files and keys from initialized target locale codes (and ignore not-initialized target locales)' do yaml_locales_path = 'tmp/config/locales' FileUtils.mkdir_p(yaml_locales_path) @@ -24,6 +24,15 @@ EOS end + File.open("#{yaml_locales_path}/nl.yml", 'wb') do |file| + file.write <<-EOS +--- +nl: + main: + hello: Hallo wereld +EOS + end + File.open("#{yaml_locales_path}/mixed.yml", 'wb') do |file| file.write <<-EOS --- @@ -31,7 +40,9 @@ misc: yo: Yo folks fr: - home: "Accueil" + home: Accueil +nl: + home: Receptie EOS end @@ -44,6 +55,7 @@ File.exist?("#{yaml_locales_path}/en.yml" ).should be true File.exist?("#{yaml_locales_path}/fr.yml" ).should be false + File.exist?("#{yaml_locales_path}/nl.yml" ).should be true # not removed because no in target locales File.exist?("#{yaml_locales_path}/mixed.yml").should be true File.read("#{yaml_locales_path}/mixed.yml").should == <<-EOS @@ -51,6 +63,8 @@ en: misc: yo: Yo folks +nl: + home: Receptie EOS end From aa03abdc19dc3952114e2c57bdec07a2290e546a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 3 May 2023 16:50:50 +0200 Subject: [PATCH 78/92] Bump to version 1.36 --- CHANGELOG.md | 6 ++++++ translation.gemspec | 2 +- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index cbdc6b8..52d5e4a 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## [v1.36](https://github.com/translation/rails/releases/tag/v1.36) (2023-05-03) + +#### Fixes (bugs & defects): + + * Keep YAML files and keys from locales that are not in the configuration file (#54) + ## [v1.35](https://github.com/translation/rails/releases/tag/v1.35) (2023-01-12) #### Fixes (bugs & defects): diff --git a/translation.gemspec b/translation.gemspec index ef9828b..75d7ccb 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.35' + s.version = '1.36' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] From 45d57a5c348e9670db2bbd281c56869ee1f45e42 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 3 May 2023 16:57:58 +0200 Subject: [PATCH 79/92] Remove old Ruby 2.2 from CI (CI triggers an error unrelated to our code) --- .github/workflows/test.yml | 1 - 1 file changed, 1 deletion(-) diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 4d31b13..5e4ef47 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -9,7 +9,6 @@ jobs: fail-fast: false matrix: ruby: - - '2.2' - '2.3' - '2.4' - '2.5' From 608d3b4e519a0c2f67659f5cdeb12b6ec1e840ae Mon Sep 17 00:00:00 2001 From: Didier Toussaint Date: Thu, 4 May 2023 10:12:09 +0200 Subject: [PATCH 80/92] Update README.md Replace relative link by absolute link --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 855efc3..cbe7f40 100644 --- a/README.md +++ b/README.md @@ -442,7 +442,7 @@ with percent signs or spaces) that he might break. We think localization is part of the configuration of the app and it should not reach the translator UI at all. That's why these localization keys are detected and separated on a dedicated YAML file with Translation.io. -We automatically treat [known localization keys](lib/translation_io/yaml_entry.rb), but if you would like +We automatically treat [known localization keys](https://github.com/translation/rails/blob/master/lib/translation_io/yaml_entry.rb), but if you would like to add some more, use the `localization_key_prefixes` option. For example: From 91351e75b780d1b32a9e6d1f5fb284af159cda87 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 22 May 2023 11:19:04 +0200 Subject: [PATCH 81/92] Improve README (remove `$` in bash commands to allow copy-paste) --- README.md | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/README.md b/README.md index cbe7f40..fe6bd10 100644 --- a/README.md +++ b/README.md @@ -144,7 +144,7 @@ end 4. Initialize your project and push existing translations to Translation.io with: ~~~bash -$ bundle exec rake translation:init +bundle exec rake translation:init ~~~ If you need to add or remove languages in the future, please read our @@ -157,7 +157,7 @@ If you need to add or remove languages in the future, please read our To send new translatable keys/strings and get new translations from Translation.io, simply run: ~~~bash -$ bundle exec rake translation:sync +bundle exec rake translation:sync ~~~ ### Sync and Show Purgeable @@ -165,7 +165,7 @@ $ bundle exec rake translation:sync If you need to find out what are the unused keys/strings from Translation.io, using the current branch as reference: ~~~bash -$ bundle exec rake translation:sync_and_show_purgeable +bundle exec rake translation:sync_and_show_purgeable ~~~ As the name says, this operation will also perform a sync at the same time. @@ -175,7 +175,7 @@ As the name says, this operation will also perform a sync at the same time. If you need to remove unused keys/strings from Translation.io, using the current branch as reference: ~~~bash -$ bundle exec rake translation:sync_and_purge +bundle exec rake translation:sync_and_purge ~~~ As the name says, this operation will also perform a sync at the same time. @@ -368,7 +368,7 @@ a queue but it returns an error under heavy load), we implemented this threadsafe readonly task: ~~~bash -$ bundle exec rake translation:sync_readonly +bundle exec rake translation:sync_readonly ~~~ This task will prevent your CI from failing and still provide new translations. But @@ -587,7 +587,7 @@ This gem was created specifically for Rails, but you can also use it in a pure R To run the specs: ~~~bash -$ bundle exec rspec +bundle exec rspec ~~~ ## Contributing From 9b76837b0e15263db75575ec8a646f90f8a7ce9f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 26 Jun 2023 17:28:04 +0200 Subject: [PATCH 82/92] Bump GetText dependency ("3.4.4 added racc to runtime dependencies because Ruby 3.3 doesn't include racc/parser") --- translation.gemspec | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/translation.gemspec b/translation.gemspec index 75d7ccb..a1925c0 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -18,7 +18,7 @@ Gem::Specification.new do |s| "source_code_uri" => "https://github.com/translation/rails" } - s.add_runtime_dependency 'gettext', '~> 3.2', '>= 3.2.5', '<= 3.4.3' + s.add_runtime_dependency 'gettext', '~> 3.2', '>= 3.2.5', '<= 3.4.4' s.add_development_dependency 'rake', '~> 12.0' s.add_development_dependency 'simplecov', '~> 0.11' From 67f7909cc8e2a76e53f5c63a4a2a52852d2227c0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 26 Jun 2023 17:31:37 +0200 Subject: [PATCH 83/92] Add Ruby `3.3.0-preview1` in Github Actions --- .github/workflows/test.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 5e4ef47..fc4512f 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -17,6 +17,7 @@ jobs: - '3.0' - '3.1' - '3.2' + - '3.3.0-preview1' - 'jruby-9.1.17.0' gemfile: - lowest From f932a9e55ca5a0fd76f8947605f38928001ae4b7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 26 Jun 2023 17:36:03 +0200 Subject: [PATCH 84/92] Remove 3.3.0-preview1 from test pipeline with lowest dependencies --- .github/workflows/test.yml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index fc4512f..d9765b1 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -32,6 +32,8 @@ jobs: gemfile: lowest - ruby: '3.2' gemfile: lowest + - ruby: '3.3.0-preview1' + gemfile: lowest env: BUNDLE_GEMFILE: ${{ github.workspace }}/gemfiles/${{ matrix.gemfile }}.gemfile CC_TEST_REPORTER_ID: 945dfb58a832d233a3caeb84e3e6d3be212e8c7abcb48117fce63b9adcb43647 From 3136a1a93d642cd1875c10b52bd3f844e43ae05d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Tue, 27 Jun 2023 12:01:15 +0200 Subject: [PATCH 85/92] Changelog + bump version to 1.37 --- CHANGELOG.md | 6 ++++++ translation.gemspec | 2 +- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 52d5e4a..7f2545f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## [v1.37](https://github.com/translation/rails/releases/tag/v1.37) (2023-06-27) + +#### Fixes (bugs & defects): + + * Prepare compatibility with Ruby 3.3 by bumping GetText dependency + ## [v1.36](https://github.com/translation/rails/releases/tag/v1.36) (2023-05-03) #### Fixes (bugs & defects): diff --git a/translation.gemspec b/translation.gemspec index a1925c0..26718a6 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.36' + s.version = '1.37' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] From 7f02656b5639ae531932c114fd52571a4aad965a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Wed, 12 Jul 2023 11:58:53 +0200 Subject: [PATCH 86/92] Update gemspec links --- translation.gemspec | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/translation.gemspec b/translation.gemspec index 26718a6..42cea96 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -11,11 +11,11 @@ Gem::Specification.new do |s| s.files = Dir["lib/**/*"] + ['README.md'] s.metadata = { + "homepage_uri" => "https://translation.io/rails", + "source_code_uri" => "https://github.com/translation/rails", "bug_tracker_uri" => "https://github.com/translation/rails/issues", "changelog_uri" => "https://github.com/translation/rails/blob/master/CHANGELOG.md", - "documentation_uri" => "https://translation.io/rails/usage", - "homepage_uri" => "https://translation.io", - "source_code_uri" => "https://github.com/translation/rails" + "documentation_uri" => "https://translation.io/docs/guide-to-translate-your-rails-applications" } s.add_runtime_dependency 'gettext', '~> 3.2', '>= 3.2.5', '<= 3.4.4' From 3b3e08818d792158a2f4dabd3998ca615c9dbf03 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 23 Oct 2023 14:51:53 +0200 Subject: [PATCH 87/92] Bump GetText dependencies to max 3.4.9 --- translation.gemspec | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/translation.gemspec b/translation.gemspec index 42cea96..bf67378 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -18,7 +18,7 @@ Gem::Specification.new do |s| "documentation_uri" => "https://translation.io/docs/guide-to-translate-your-rails-applications" } - s.add_runtime_dependency 'gettext', '~> 3.2', '>= 3.2.5', '<= 3.4.4' + s.add_runtime_dependency 'gettext', '~> 3.2', '>= 3.2.5', '<= 3.4.9' s.add_development_dependency 'rake', '~> 12.0' s.add_development_dependency 'simplecov', '~> 0.11' From c12d760a48106338846ac1d2e67dc5218abd973c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Mon, 23 Oct 2023 16:00:53 +0200 Subject: [PATCH 88/92] Bump version to 1.38 and CHANGELOG --- CHANGELOG.md | 6 ++++++ translation.gemspec | 2 +- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 7f2545f..a28f06b 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## [v1.38](https://github.com/translation/rails/releases/tag/v1.38) (2023-10-23) + +#### Fixes (bugs & defects): + + * Bump GetText dependency to 3.4.9 (fix `\r` escape and other improvements) + ## [v1.37](https://github.com/translation/rails/releases/tag/v1.37) (2023-06-27) #### Fixes (bugs & defects): diff --git a/translation.gemspec b/translation.gemspec index bf67378..9628e90 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.37' + s.version = '1.38' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] From 31faa1398cb3af146655592ffd9f47848e12b9d2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Fri, 9 Feb 2024 14:50:57 +0100 Subject: [PATCH 89/92] Fix bug when YAML is commented and only the language key is present --- lib/translation_io/yaml_conversion.rb | 4 ++-- spec/support/data/commented.en.yml | 4 ++++ spec/support/data/empty.yml | 0 spec/translation/yaml_conversion_spec.rb | 7 +++++++ 4 files changed, 13 insertions(+), 2 deletions(-) create mode 100644 spec/support/data/commented.en.yml delete mode 100644 spec/support/data/empty.yml diff --git a/lib/translation_io/yaml_conversion.rb b/lib/translation_io/yaml_conversion.rb index 34c9c4f..9c2d775 100644 --- a/lib/translation_io/yaml_conversion.rb +++ b/lib/translation_io/yaml_conversion.rb @@ -28,9 +28,9 @@ def get_flat_translations_for_yaml_file(file_path) def get_flat_translations_for_yaml_data(yaml_data) translations = TranslationIO.yaml_load(yaml_data) - if translations + if translations && translations.values.all? { |value| value.present? } return FlatHash.to_flat_hash(translations) - else # loading an empty file returns false + else # loading an empty file, or file with only the language, returns false return {} end end diff --git a/spec/support/data/commented.en.yml b/spec/support/data/commented.en.yml new file mode 100644 index 0000000..b020394 --- /dev/null +++ b/spec/support/data/commented.en.yml @@ -0,0 +1,4 @@ +en: +# devise: +# confirmations: +# confirmed: "Your email address has been successfully confirmed." diff --git a/spec/support/data/empty.yml b/spec/support/data/empty.yml deleted file mode 100644 index e69de29..0000000 diff --git a/spec/translation/yaml_conversion_spec.rb b/spec/translation/yaml_conversion_spec.rb index ab24e5d..fe2976a 100644 --- a/spec/translation/yaml_conversion_spec.rb +++ b/spec/translation/yaml_conversion_spec.rb @@ -117,6 +117,13 @@ result.should == {} end + + it 'returns an empty Hash if the YAML file is commented (bug fix)' do + yaml_path = 'spec/support/data/commented.en.yml' + result = subject.get_flat_translations_for_yaml_file(yaml_path) + + result.should == {} + end end describe '#get_yaml_data_from_flat_translations' do From 5b33dcdf6a601b9b8cbecfbc2b5e1988bb384999 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Fri, 9 Feb 2024 14:53:52 +0100 Subject: [PATCH 90/92] Bump to 1.39 --- CHANGELOG.md | 6 ++++++ translation.gemspec | 2 +- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index a28f06b..2b8d853 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## [v1.39](https://github.com/translation/rails/releases/tag/v1.39) (2024-02-09) + +#### Fixes (bugs & defects): + + * Fix bug when YAML file is commented and the language key is still present. + ## [v1.38](https://github.com/translation/rails/releases/tag/v1.38) (2023-10-23) #### Fixes (bugs & defects): diff --git a/translation.gemspec b/translation.gemspec index 9628e90..9f582b7 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.38' + s.version = '1.39' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"] From 832762e92d9a1408b83bf8c6248512b7bfe94958 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Fri, 9 Feb 2024 15:55:08 +0100 Subject: [PATCH 91/92] Better bugfix for empty YAML files (only the language prefix) --- .../client/init_operation/create_yaml_po_files_step.rb | 2 +- .../client/sync_operation/create_yaml_pot_file_step.rb | 2 +- lib/translation_io/yaml_conversion.rb | 2 +- .../init_operation/create_yaml_po_files_step_spec.rb | 9 ++++++++- .../sync_operation/create_yaml_pot_file_step_spec.rb | 7 +++++++ 5 files changed, 18 insertions(+), 4 deletions(-) diff --git a/lib/translation_io/client/init_operation/create_yaml_po_files_step.rb b/lib/translation_io/client/init_operation/create_yaml_po_files_step.rb index e2ac079..7a4abe3 100644 --- a/lib/translation_io/client/init_operation/create_yaml_po_files_step.rb +++ b/lib/translation_io/client/init_operation/create_yaml_po_files_step.rb @@ -20,7 +20,7 @@ def run(params) TranslationIO.info file_path, 2, 2 file_translations = TranslationIO.yaml_load(File.read(file_path)) - unless file_translations.blank? + if file_translations.present? && file_translations.values.all? { |value| value.present? } all_translations = all_translations.deep_merge(file_translations) end end diff --git a/lib/translation_io/client/sync_operation/create_yaml_pot_file_step.rb b/lib/translation_io/client/sync_operation/create_yaml_pot_file_step.rb index 4463858..7d28304 100644 --- a/lib/translation_io/client/sync_operation/create_yaml_pot_file_step.rb +++ b/lib/translation_io/client/sync_operation/create_yaml_pot_file_step.rb @@ -16,7 +16,7 @@ def run(params) TranslationIO.info file_path, 2, 2 file_translations = TranslationIO.yaml_load(File.read(file_path)) - unless file_translations.blank? + if file_translations.present? && file_translations.values.all? { |value| value.present? } all_translations = all_translations.deep_merge(file_translations) end end diff --git a/lib/translation_io/yaml_conversion.rb b/lib/translation_io/yaml_conversion.rb index 9c2d775..378f19b 100644 --- a/lib/translation_io/yaml_conversion.rb +++ b/lib/translation_io/yaml_conversion.rb @@ -28,7 +28,7 @@ def get_flat_translations_for_yaml_file(file_path) def get_flat_translations_for_yaml_data(yaml_data) translations = TranslationIO.yaml_load(yaml_data) - if translations && translations.values.all? { |value| value.present? } + if translations.present? && translations.values.all? { |value| value.present? } return FlatHash.to_flat_hash(translations) else # loading an empty file, or file with only the language, returns false return {} diff --git a/spec/translation/client/init_operation/create_yaml_po_files_step_spec.rb b/spec/translation/client/init_operation/create_yaml_po_files_step_spec.rb index cfc0132..9e36e9b 100644 --- a/spec/translation/client/init_operation/create_yaml_po_files_step_spec.rb +++ b/spec/translation/client/init_operation/create_yaml_po_files_step_spec.rb @@ -29,7 +29,14 @@ EOS end - File.open('tmp/config/locales/fr.yml', 'wb') do |file| + File.open("tmp/config/locales/empty.en.yml", 'wb') do |file| + file.write <<-EOS +--- +en: +EOS + end + + File.open('tmp/config/locales/fr.yml', 'wb') do |file| file.write <<-EOS --- fr: diff --git a/spec/translation/client/sync_operation/create_yaml_pot_file_step_spec.rb b/spec/translation/client/sync_operation/create_yaml_pot_file_step_spec.rb index 606a5e8..ef32c4c 100644 --- a/spec/translation/client/sync_operation/create_yaml_pot_file_step_spec.rb +++ b/spec/translation/client/sync_operation/create_yaml_pot_file_step_spec.rb @@ -24,6 +24,13 @@ EOS end + File.open("#{yaml_locales_path}/empty.en.yml", 'wb') do |file| + file.write <<-EOS +--- +en: +EOS + end + source_locale = 'en' yaml_file_paths = Dir["#{yaml_locales_path}/*.yml"] From 35c0c4ae71b0ad83bedec48a9dd2381724503f6a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Hoste?= Date: Fri, 9 Feb 2024 15:57:18 +0100 Subject: [PATCH 92/92] Bump to version 1.40 --- CHANGELOG.md | 6 ++++++ translation.gemspec | 2 +- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 2b8d853..712846f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## [v1.40](https://github.com/translation/rails/releases/tag/v1.40) (2024-02-09) + +#### Fixes (bugs & defects): + + * Fix *more* bugs when YAML file is commented and the language key is still present. + ## [v1.39](https://github.com/translation/rails/releases/tag/v1.39) (2024-02-09) #### Fixes (bugs & defects): diff --git a/translation.gemspec b/translation.gemspec index 9f582b7..934045e 100644 --- a/translation.gemspec +++ b/translation.gemspec @@ -4,7 +4,7 @@ Gem::Specification.new do |s| s.description = 'Localize your app using either t(".keys") or _("source text") and type "rake translation:sync" to synchronize with your translators on Translation.io.' s.homepage = 'https://translation.io' s.email = 'contact@translation.io' - s.version = '1.39' + s.version = '1.40' s.authors = ['Michael Hoste', 'Aurelien Malisart'] s.license = "MIT" s.require_paths = ["lib"]