Agile Web Development with Rails, Edition 4

15.4 Task J4: Add a locale switcher. 15.2 Task J2: translating the store front

15.3 Task J3: Translating Checkout

Expected at least 1 element matching "input[type='submit'][value$='Comprar']", found 0.

Traceback:
  /home/rubys/git/awdwr/edition4/checkdepot.rb:380:in `block in <class:DepotTest>'

Edit the new order page

edit app/views/orders/new.html.erb
<div class="depot_form">
  <fieldset>
    <legend><%= t('.legend') %></legend>
    <%= render 'form' %>
  </fieldset>
</div>

Edit the form used by the new order page

edit app/views/orders/_form.html.erb
<%= form_for(@order) do |f| %>
  <% if @order.errors.any? %>
    <div id="error_explanation">
      <h2><%= pluralize(@order.errors.count, "error") %>
      prohibited this order from being saved:</h2>
 
      <ul>
      <% @order.errors.full_messages.each do |msg| %>
        <li><%= msg %></li>
      <% end %>
      </ul>
    </div>
  <% end %>
 
  <div class="field">
    <%= f.label :name, t('.name') %><br />
    <%= f.text_field :name, size: 40 %>
  </div>
  <div class="field">
    <%= f.label :address, t('.address_html') %><br />
    <%= f.text_area :address, rows: 3, cols: 40 %>
  </div>
  <div class="field">
    <%= f.label :email, t('.email') %><br />
    <%= f.email_field :email, size: 40 %>
  </div>
  <div class="field">
    <%= f.label :pay_type, t('.pay_type') %><br />
    <%= f.select :pay_type, Order::PAYMENT_TYPES,
                  prompt: t('.pay_prompt_html') %>
  </div>
  <div class="actions">
    <%= f.submit t('.submit') %>
  </div>
<% end %>

Define some translations for the new order.

edit config/locales/en.yml
en:
 
  orders:
    new:
      legend:       "Please Enter Your Details"
    form:
      name:         "Name"
      address_html: "Address"
      email:        "E-mail"
      pay_type:     "Pay with"
      pay_prompt_html: "Select a payment method"
      submit:       "Place Order"
edit config/locales/es.yml
es:
 
  orders:
    new:
      legend:       "Por favor, introduzca sus datos"
    form:
      name:         "Nombre"
      address_html: "Direcci&oacute;n"
      email:        "E-mail"
      pay_type:     "Forma de pago"
      pay_prompt_html: "Seleccione un m&eacute;todo de pago"
      submit:       "Realizar Pedido"

Add to cart

get /es

NameError in Store#index

Showing /home/rubys/git/awdwr/edition4/work-192-30/depot/app/views/store/index.html.erb where line #6 raised:

uninitialized constant I18n::RESERVED_KEYS

Extracted source (around line #6):

3: <% end %>
4: 
5: <!-- START_HIGHLIGHT -->
6: <h1><%= t('.title_html') %></h1>
7: <!-- END_HIGHLIGHT -->
8: 
9: <% @products.each do |product| %>

Rails.root: /home/rubys/git/awdwr/edition4/work-192-30/depot

Application Trace | Framework Trace | Full Trace
app/views/store/index.html.erb:6:in `_app_views_store_index_html_erb___2376477419595695665_70128298172420_558081496217810729'

Request

Parameters:

{"locale"=>"es"}

Show session dump

Show env dump

Response

Headers:

None

Show mixed validation errors

get /es/orders/new
You are being redirected.

Translate the errors to human names.

edit config/locales/es.yml
es:
 
  activerecord:
    errors:
      messages:
        inclusion: "no est&aacute; incluido en la lista"
        blank:     "no puede quedar en blanco"
  errors:
    template:
      body:        "Hay problemas con los siguientes campos:"
      header:
        one:       "1 error ha impedido que este %{model} se guarde"
        other:     "%{count} errores han impedido que este %{model} se guarde"

Display messages in raw form, and translate error messages

edit app/views/orders/_form.html.erb
<%= form_for(@order) do |f| %>
  <% if @order.errors.any? %>
    <div id="error_explanation">
      <h2><%=raw t('errors.template.header', count: @order.errors.count,
        model: t('activerecord.models.order')) %>.</h2>
      <p><%= t('errors.template.body') %></p>
 
      <ul>
      <% @order.errors.full_messages.each do |msg| %>
        <li><%=raw msg %></li>
      <% end %>
      </ul>
    </div>
  <% end %>
<!-- ... -->
 
  <div class="field">
    <%= f.label :name, t('.name') %><br />
    <%= f.text_field :name, size: 40 %>
  </div>
  <div class="field">
    <%= f.label :address, t('.address_html') %><br />
    <%= f.text_area :address, rows: 3, cols: 40 %>
  </div>
  <div class="field">
    <%= f.label :email, t('.email') %><br />
    <%= f.email_field :email, size: 40 %>
  </div>
  <div class="field">
    <%= f.label :pay_type, t('.pay_type') %><br />
    <%= f.select :pay_type, Order::PAYMENT_TYPES,
                  prompt: t('.pay_prompt_html') %>
  </div>
  <div class="actions">
    <%= f.submit t('.submit') %>
  </div>
<% end %>

Translate the model names to human names.

edit config/locales/es.yml
es:
 
  activerecord:
    models:
      order:       "pedido"
    attributes:
      order:
        address:   "Direcci&oacute;n"
        name:      "Nombre"
        email:     "E-mail"
        pay_type:  "Forma de pago"

Show validation errors

get /es/orders/new
You are being redirected.

Replace translatable text with calls out to translation functions.

edit app/controllers/orders_controller.rb
  def create
    @order = Order.new(params[:order])
    @order.add_line_items_from_cart(@cart)
 
    respond_to do |format|
      if @order.save
        Cart.destroy(session[:cart_id])
        session[:cart_id] = nil
        OrderNotifier.received(@order).deliver
        format.html { redirect_to(store_url, notice: 
          I18n.t('.thanks')) }
        format.xml  { render xml: @order, status: :created,
          location: @order }
      else
        format.html { render action: "new" }
        format.xml  { render xml: @order.errors,
          status: :unprocessable_entity }
      end
    end
  end

Define some translations for the flash.

edit config/locales/en.yml
en:
 
  thanks:          "Thank you for your order"
edit config/locales/es.yml
es:
 
  thanks:          "Gracias por su pedido"

Place the order

get /es/orders/new
You are being redirected.

15.4 Task J4: Add a locale switcher. 15.2 Task J2: translating the store front