Blog

Rails, JavaScript and I18n

Icône flèche bleue vers la gauche
Back to blog
Rails, JavaScript and I18n

Rails, JavaScript and I18n

May 1, 2012

First and foremost, internationalizing an existing application is a tedious, repetitive task. So even though your customer may not need it as part of the first development, paying attention to this aspect is not only recommended, but often turns out to be quite necessary. This will avoid a lot of trouble for you in the long run!

Here are some techniques, tools and tips that will help you get started. But first, let’s review how i18n (I’m not typing that word a second time) works in Rails.

First of all, you don’t need any extra gem to internationalize your application. Everything is already built into the framework.

The default language is English (:en), and all your translations (in YAML files) are stored into config/locales/.

The format of these files is relatively free, except for the names of ActiveRecord models and attributes, and validation error messages. As usual with Rails, conventions exist and the process will be a lot easier if you follow them.

order.en.yml

en:
order: "Order"
activerecord:
models:
order: "Order"
attributes:
order:
quote_id: "Quote"
internal_reference: "Internal reference"
user_id: "User"
patent_id: "Patent"
currency: "Currency"
billing_country_id: "Billing country"
billing_title: "Title"
billing_lastname: "Lastname"
billing_firstname: "Firstname"
billing_function: "Function"
billing_company: "Company"
billing_vat_number: "VAT# of the company/firm"
billing_address_1: "Address line 1"
billing_address_2: "Address line 2"
billing_city: "City"
billing_postcode: "Post/Zip Code"
reference: "Reference"
ordering_paralegal_id: "Ordering paralegal"
provided_translation_ids: "Provided translations"
person_in_charge: "Person in charge"
first_annuities_offices_ids: "First annuities offices"
annuities_offices_ids: "Annuities offices"
ordered_at: "Order date"
orders:
certificates_have_been_ordered: "Your certificates have been correctly ordered"
thank_you: "Thank you for your order!"
place_an_order: "Place an order in 4 simple steps."
place_order_now: "Place order now"
nothing_to_down: "Nothing to download"
process_steps:
quote_summary: "Quote Summary"
special_requests: "Special Requests"
billing_mailing_info: "Billing/Mailing Info"
confirmation: "Confirmation"
fast_track_process_steps:
ft_service_selection: "Service Selection"
ft_special_requests: "Special Requests"
ft_billing_mailing_info: "Billing/Mailing Info"
ft_confirmation: "Confirmation"
footer:
print_page: "Print this page"
start_valid: "Start a new validation quote for this patent"
back_to: "Back to cases"
export_pdf: "Export to PDF"
export_exel: "Export to Excel"
header:
placed: "placed on"
you_can: "You can review your order here."
validation_certificates: "Validation certificates ordering"

You can put all your texts in a single file (such as en.yml), but we recommend splitting them into different theme files, which must be namesome_theme.language_code.yml (e.g. users.en.yml).

The first thing you need to do is set the locale of the application. Here is how you would do it if your User model has a stored locale:

application_controller.rb

class ApplicationController < ActionController::Base
before_filter :set_locale

def set_locale
I18n.locale = (@current_user.locale.to_sym || I18n.default_locale)
end
end

Now that we know which local to use, we need to replace all the text in our views, controllers, etc by a method code, which will select the correct translation. This is the translate(key) method (aliased to t for short). This method is automatically available in views. In controllers, you will need to call I18n.t(key).

As said before, the translation files have conventions as to their structure. Here is where they will prove useful: let’s say you want to display the text “Print this page” (line 48), you could callt('orders.footer.print_page'), but that is a little long, especially if you consider you will have to do this for every single link, button, header and paragraph of your view (I warned you it was tedious). But if you’re in app/views/orders/_footer.html.erb, you can simply call t('.print_page'). Rails will know to complete the missing hierarchy of your key with the path to the current view or partial. Of course, you can still use the complete path whenever you need to access translations outside your current scope.

Lastly, a little tip for the text in your JavaScript: have a look at the i18n-js gem, which lets you use similar tools as what is provided by Rails from JavaScript.

Read more: I18n on RailsGuides

Ready to build your software product? Contact us!