Spec-Zone.ru › Ruby on Rails 5.1

модуль ActionView::Helpers::FormHelper

Включенные модули:
ActionView::Helpers::FormTagHelper, ActionView::Helpers::UrlHelper, ActionView::RecordIdentifier

Помощники для форм разработаны для того, чтобы работа с ресурсами была намного проще, чем использование обычного HTML.

Обычно форма, предназначенная для создания или обновления ресурса, отражает идентичность ресурса несколькими способами: (i) URL, к которому отправляется форма (атрибут элемента формы action) должен привести к тому, что запрос будет перенаправлен на соответствующее действие контроллера (с соответствующим параметром :id в случае существующего ресурса), (ii) поля ввода должны быть именованы таким образом, чтобы в контроллере их значения появлялись в соответствующих местах в хеше params, и (iii) для существующего запися, при первоначальном отображении формы, поля ввода, соответствующие атрибутам ресурса, должны показывать текущие значения этих атрибутов.

В Rails это обычно достигается путем создания формы с помощью form_for и ряда связанных методов помощников. form_for генерирует соответствующий тег form и возвращает объект билдера форм, который знает модель, к которой относится форма. Поля ввода создаются путем вызова методов, определенных в билдере форм, что означает, что они могут генерировать соответствующие имена и значения по умолчанию, соответствующие атрибутам модели, а также удобные идентификаторы и т. д. Конвенции в сгенерированных именах полей позволяют контроллерам получать данные из формы в виде красиво структурированного хеша params без дополнительных усилий с вашей стороны.

Например, для создания нового человека обычно необходимо создать новый экземпляр Person в действии PeopleController#new, @person, и в шаблоне представления передать этот объект в form_for:

<%= form_for @person do |f| %>
  <%= f.label :first_name %>:
  <%= f.text_field :first_name %><br />

  <%= f.label :last_name %>:
  <%= f.text_field :last_name %><br />

  <%= f.submit %>
<% end %>

Сгенерированный HTML для этого будет выглядеть следующим образом (с модулем форматирования):

<form action="/people" class="new_person" id="new_person" method="post">
  <input name="authenticity_token" type="hidden" value="NrOp5bsjoLRuK8IW5+dQEYjKGUJDe7TQoZVvq95Wteg=" />
  <label for="person_first_name">First name</label>:
  <input id="person_first_name" name="person[first_name]" type="text" /><br />

  <label for="person_last_name">Last name</label>:
  <input id="person_last_name" name="person[last_name]" type="text" /><br />

  <input name="commit" type="submit" value="Create Person" />
</form>

Как вы видите, HTML отражает информацию о ресурсе в нескольких местах, например, путь, по которому должна отправляться форма, или имена полей ввода.

В частности, благодаря конвенциям, используемым в сгенерированных именах полей, контроллер получает вложенный хеш params[:person] с атрибутами человека, заданными в форме. Этот хеш готов к передаче в Person.new:

@person = Person.new(params[:person])
if @person.save
  # success
else
  # error handling
end

Интересно, что тот же код представления в предыдущем примере может использоваться для редактирования человека. Если @person - это существующая запись с именем «John Smith» и идентификатором 256, то приведенный выше код в таком виде вернет:

<form action="/people/256" class="edit_person" id="edit_person_256" method="post">
  <input name="_method" type="hidden" value="patch" />
  <input name="authenticity_token" type="hidden" value="NrOp5bsjoLRuK8IW5+dQEYjKGUJDe7TQoZVvq95Wteg=" />
  <label for="person_first_name">First name</label>:
  <input id="person_first_name" name="person[first_name]" type="text" value="John" /><br />

  <label for="person_last_name">Last name</label>:
  <input id="person_last_name" name="person[last_name]" type="text" value="Smith" /><br />

  <input name="commit" type="submit" value="Update Person" />
</form>

Обратите внимание, что конечная точка, значения по умолчанию и метка кнопки отправки настроены для @person. Это происходит потому, что связанные помощники знают, является ли ресурс новой записью или нет, и генерируют HTML соответственно.

Контроллер снова получит данные формы в params[:person], готовые к передаче в Person#update:

if @person.update(params[:person])
  # success
else
  # error handling
end

Вот как обычно работают с ресурсами.

Публичные методы экземпляров

check_box(object_name, method, options = {}, checked_value = "1", unchecked_value = "0") Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1311
def check_box(object_name, method, options = {}, checked_value = "1", unchecked_value = "0")
  Tags::CheckBox.new(object_name, method, self, checked_value, unchecked_value, options).render
end

Возвращает тег флажка, настроенный для доступа к указанному атрибуту (определяемому по method) объекта, присвоенного шаблону (определяемому по object). Этот объект должен быть объектом экземпляра (@object), а не локальным объектом. Ожидается, что method вернет целое число, и если это целое число больше нуля, то флажок установлен. Дополнительные параметры тега ввода могут быть переданы в виде хеша с options. Значение checked_value по умолчанию равно 1, а значение unchecked_value по умолчанию равно 0, что удобно для булевых значений.

Особенности

Спецификация HTML гласит, что неактивные флажки не успешны, и поэтому веб-браузеры их не отправляют. К сожалению, это создает проблему: если у модели Invoice есть флаг paid, и в форме для редактирования оплаченного счета пользователь снимит флажок, параметр paid не отправляется. Следовательно, любые выражения для массовой присваивания, такие как

@invoice.update(params[:invoice])

не обновили бы флаг.

Чтобы предотвратить это, помощник генерирует вспомогательное скрытое поле перед самим флажком. У скрытого поля то же имя, а его атрибуты имитируют снятие флажка.

Таким образом, клиент либо отправляет только скрытое поле (что означает, что флажок снят), либо оба поля. Поскольку спецификация HTML гласит, что пары ключ/значение должны отправляться в том же порядке, в котором они появляются в форме, а извлечение параметров получает последнее вхождение любого повторяющегося ключа в строке запроса, это работает для обычных форм.

К сожалению, это решение не работает, когда флажок находится в массивоподобном параметре, как в

<%= fields_for "project[invoice_attributes][]", invoice, index: nil do |form| %>
  <%= form.check_box :paid %>
  ...
<% end %>

поскольку повторение имен параметров именно то, что Rails пытается отличить элементы массива. Для каждого элемента с установленными флажками вы получаете дополнительный фиктивный элемент только с этим атрибутом, присвоенным «0».

В этом случае предпочтительнее использовать check_box_tag или использовать хеши вместо массивов.

# Let's say that @post.validated? is 1:
check_box("post", "validated")
# => <input name="post[validated]" type="hidden" value="0" />
#    <input checked="checked" type="checkbox" id="post_validated" name="post[validated]" value="1" />

# Let's say that @puppy.gooddog is "no":
check_box("puppy", "gooddog", {}, "yes", "no")
# => <input name="puppy[gooddog]" type="hidden" value="no" />
#    <input type="checkbox" id="puppy_gooddog" name="puppy[gooddog]" value="yes" />

check_box("eula", "accepted", { class: 'eula_check' }, "yes", "no")
# => <input name="eula[accepted]" type="hidden" value="no" />
#    <input type="checkbox" class="eula_check" id="eula_accepted" name="eula[accepted]" value="yes" />
color_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1341
def color_field(object_name, method, options = {})
  Tags::ColorField.new(object_name, method, self, options).render
end

Возвращает #text_field типа «цвет».

color_field("car", "color")
# => <input id="car_color" name="car[color]" type="color" value="#000000" />
date_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1405
def date_field(object_name, method, options = {})
  Tags::DateField.new(object_name, method, self, options).render
end

Возвращает #text_field типа «дата».

date_field("user", "born_on")
# => <input id="user_born_on" name="user[born_on]" type="date" />

Значение по умолчанию генерируется путем попытки вызова strftime с «%Y-%m-%d» для значения объекта, что обеспечивает ожидаемое поведение для экземпляров DateTime и ActiveSupport::TimeWithZone. Вы всё равно можете переопределить это, явно передав параметр «value», например:

@user.born_on = Date.new(1984, 1, 27)
date_field("user", "born_on", value: "1984-05-12")
# => <input id="user_born_on" name="user[born_on]" type="date" value="1984-05-12" />

Вы можете создавать значения для атрибутов «min» и «max», передавая экземпляры Date или Time в хеш параметров.

date_field("user", "born_on", min: Date.today)
# => <input id="user_born_on" name="user[born_on]" type="date" min="2014-05-20" />

В качестве альтернативы, вы можете передать строку String, отформатированную как дата ISO8601, в качестве значений для «min» и «max».

date_field("user", "born_on", min: "2014-05-20")
# => <input id="user_born_on" name="user[born_on]" type="date" min="2014-05-20" />
datetime_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1463
def datetime_field(object_name, method, options = {})
  Tags::DatetimeLocalField.new(object_name, method, self, options).render
end

Возвращает #text_field типа «datetime-local».

datetime_field("user", "born_on")
# => <input id="user_born_on" name="user[born_on]" type="datetime-local" />

Значение по умолчанию генерируется путем попытки вызова strftime с «%Y-%m-%dT%T» для значения объекта, что обеспечивает ожидаемое поведение для экземпляров DateTime и ActiveSupport::TimeWithZone.

@user.born_on = Date.new(1984, 1, 12)
datetime_field("user", "born_on")
# => <input id="user_born_on" name="user[born_on]" type="datetime-local" value="1984-01-12T00:00:00" />

Вы можете создавать значения для атрибутов «min» и «max», передавая экземпляры Date или Time в хеш параметров.

datetime_field("user", "born_on", min: Date.today)
# => <input id="user_born_on" name="user[born_on]" type="datetime-local" min="2014-05-20T00:00:00.000" />

В качестве альтернативы, вы можете передать строку String, отформатированную как дата/время ISO8601, в качестве значений для «min» и «max».

datetime_field("user", "born_on", min: "2014-05-20T00:00:00")
# => <input id="user_born_on" name="user[born_on]" type="datetime-local" min="2014-05-20T00:00:00.000" />
Также алиас: datetime_local_field
datetime_local_field(object_name, method, options = {})
Псевдоним для: datetime_field
email_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1517
def email_field(object_name, method, options = {})
  Tags::EmailField.new(object_name, method, self, options).render
end

Возвращает #text_field типа «email».

email_field("user", "address")
# => <input id="user_address" name="user[address]" type="email" />
fields(scope = nil, model: nil, **options, &block) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1071
def fields(scope = nil, model: nil, **options, &block)
  options[:allow_method_names_outside_object] = true
  options[:skip_default_ids] = true

  if model
    scope ||= model_name_from_record_or_class(model).param_key
  end

  builder = instantiate_builder(scope, model, options)
  capture(builder, &block)
end

Ограничивает поля ввода с помощью явного ограничения или модели. Как form_with с :scope или :model, за исключением того, что теги форм не выводятся.

# Using a scope prefixes the input field names:
<%= fields :comment do |fields| %>
  <%= fields.text_field :body %>
<% end %>
# => <input type="text" name="comment[body]>

# Using a model infers the scope and assigns field values:
<%= fields model: Comment.new(body: "full bodied") do |fields| %<
  <%= fields.text_field :body %>
<% end %>
# =>
<input type="text" name="comment[body] value="full bodied">

# Using +fields+ with +form_with+:
<%= form_with model: @post do |form| %>
  <%= form.text_field :title %>

  <%= form.fields :comment do |fields| %>
    <%= fields.text_field :body %>
  <% end %>
<% end %>

Как и form_with, передаётся экземпляр FormBuilder, связанный с областью или моделью, поэтому все сгенерированные имена полей предваряются либо указанной областью, либо областью, полученной из :model.

При использовании меток fields необходимо задать идентификатор для поля, к которому относится метка:

<%= fields :comment do |fields| %>
  <%= fields.label :body %>
  <%= fields.text_field :body, id: :comment_body %>
<% end %>

См. label для получения дополнительной информации о том, как выводится атрибут for.

Использование с другими помощниками форм

Хотя form_with использует объект FormBuilder, можно смешивать методы самостоятельного помощника FormHelper и методы FormTagHelper:

<%= fields model: @comment do |fields| %>
  <%= fields.text_field :body %>

  <%= text_area :commenter, :biography %>
  <%= check_box_tag "comment[all_caps]", "1", @comment.commenter.hulk_mode? %>
<% end %>

То же самое относится к методам в FormOptionHelper и DateHelper, предназначенных для работы с объектом в качестве основы, таких как FormOptionHelper#collection_select и ActionView::Helpers::DateHelper#datetime_select.

fields_for(record_name, record_object = nil, options = {}, &block) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1010
def fields_for(record_name, record_object = nil, options = {}, &block)
  builder = instantiate_builder(record_name, record_object, options)
  capture(builder, &block)
end

Создаёт область действия вокруг конкретного объекта модели, подобно #form_for, но не создаёт сами теги формы. Это делает #fields_for подходящим для указания дополнительных объектов модели в той же форме.

Несмотря на схожее использование и назначение с fields_for, его сигнатура метода немного отличается. Подобно form_for, он передаёт объект FormBuilder, связанный с определённым объектом модели, в блок, и внутри блока можно вызывать методы для генерации полей, связанных с объектом модели. Поля могут отражать объект модели двумя способами — как они названы (и, следовательно, как представятся отправленные значения в хэше params в контроллере) и какие значения по умолчанию будут показаны при первом отображении формы, в которой появляются поля. Для независимого указания обоих этих функций можно передавать как имя объекта (символ или строка), так и сам объект в метод отдельно —

<%= form_for @person do |person_form| %>
  First name: <%= person_form.text_field :first_name %>
  Last name : <%= person_form.text_field :last_name %>

  <%= fields_for :permission, @person.permission do |permission_fields| %>
    Admin?  : <%= permission_fields.check_box :admin %>
  <% end %>

  <%= person_form.submit %>
<% end %>

В этом случае, поле типа checkbox будет представлено тегом HTML input с атрибутом name permission[admin], а отправленное значение будет отображаться в контроллере как params[:permission][:admin]. Если @person.permission — это существующий объект с атрибутом admin, начальное состояние checkbox при первом отображении будет отражать значение @person.permission.admin.

Часто это можно упростить, передав только имя объекта модели в fields_for —

<%= fields_for :permission do |permission_fields| %>
  Admin?: <%= permission_fields.check_box :admin %>
<% end %>

…в этом случае, если :permission также является именем переменной экземпляра @permission, начальное состояние поля ввода будет отражать значение атрибута этой переменной @permission.admin.

В качестве альтернативы, можно передать только сам объект модели (если первый аргумент не является строкой или символом fields_for поймёт, что имя опущено) —

<%= fields_for @person.permission do |permission_fields| %>
  Admin?: <%= permission_fields.check_box :admin %>
<% end %>

и fields_for выведет необходимое имя поля из класса объекта модели, например, если @person.permission, является объектом класса Permission, поле всё равно будет названо permission[admin].

Примечание: Это также работает для методов в FormOptionHelper и DateHelper, которые предназначены для работы с объектом в качестве основы, как FormOptionHelper#collection_select и ActionView::Helpers::DateHelper#datetime_select.

Примеры вложенных атрибутов

Когда объект, принадлежащий текущей области действия, имеет запись вложенного атрибута для определённого атрибута, #fields_for создаст новую область действия для этого атрибута. Это позволяет создавать формы, которые устанавливают или изменяют атрибуты родительского объекта и его ассоциаций одновременно.

Записи вложенных атрибутов — это обычные методы установщика, названные в честь ассоциации. Наиболее распространённый способ определения этих установщиков — либо с помощью accepts_nested_attributes_for в определении модели, либо путём определения метода с соответствующим именем. Например: метод установщика атрибута для ассоциации :address называется address_attributes=.

Тип формы-билдера (один к одному или один ко многим) зависит от того, возвращает ли обычный метод чтения один объект или массив объектов.

Один к одному

Рассмотрим класс Person, который возвращает один объект Address из метода чтения address и отвечает на метод записи address_attributes=:

class Person
  def address
    @address
  end

  def address_attributes=(attributes)
    # Process the attributes hash
  end
end

Теперь эту модель можно использовать с вложенным #fields_for, например так:

<%= form_for @person do |person_form| %>
  ...
  <%= person_form.fields_for :address do |address_fields| %>
    Street  : <%= address_fields.text_field :street %>
    Zip code: <%= address_fields.text_field :zip_code %>
  <% end %>
  ...
<% end %>

Если адрес уже является ассоциацией в Person, вы можете использовать accepts_nested_attributes_for для определения метода установщика за вас:

class Person < ActiveRecord::Base
  has_one :address
  accepts_nested_attributes_for :address
end

Если вы хотите удалить ассоциированную модель через форму, вы должны сначала включить это с помощью опции :allow_destroy для accepts_nested_attributes_for:

class Person < ActiveRecord::Base
  has_one :address
  accepts_nested_attributes_for :address, allow_destroy: true
end

Теперь, когда вы используете элемент формы с параметром _destroy, со значением, которое оценивается как true, вы удалите ассоциированную модель (например, 1, '1', true или 'true'):

<%= form_for @person do |person_form| %>
  ...
  <%= person_form.fields_for :address do |address_fields| %>
    ...
    Delete: <%= address_fields.check_box :_destroy %>
  <% end %>
  ...
<% end %>

Один ко многим

Рассмотрим класс Person, который возвращает массив экземпляров Project из метода чтения projects и отвечает на метод записи projects_attributes=:

class Person
  def projects
    [@project1, @project2]
  end

  def projects_attributes=(attributes)
    # Process the attributes hash
  end
end

Обратите внимание, что метод записи projects_attributes= фактически необходим для #fields_for для правильной идентификации :projects как коллекции и корректного установки индексов в разметке формы.

Если проекты уже являются ассоциацией в Person, вы можете использовать accepts_nested_attributes_for для определения метода установщика за вас:

class Person < ActiveRecord::Base
  has_many :projects
  accepts_nested_attributes_for :projects
end

Теперь эту модель можно использовать с вложенными полями fields_for. Блок, переданный в вызов вложенного #fields_for, будет повторяться для каждого экземпляра в коллекции:

<%= form_for @person do |person_form| %>
  ...
  <%= person_form.fields_for :projects do |project_fields| %>
    <% if project_fields.object.active? %>
      Name: <%= project_fields.text_field :name %>
    <% end %>
  <% end %>
  ...
<% end %>

Также можно указать экземпляр для использования:

<%= form_for @person do |person_form| %>
  ...
  <% @person.projects.each do |project| %>
    <% if project.active? %>
      <%= person_form.fields_for :projects, project do |project_fields| %>
        Name: <%= project_fields.text_field :name %>
      <% end %>
    <% end %>
  <% end %>
  ...
<% end %>

Или коллекцию для использования:

<%= form_for @person do |person_form| %>
  ...
  <%= person_form.fields_for :projects, @active_projects do |project_fields| %>
    Name: <%= project_fields.text_field :name %>
  <% end %>
  ...
<% end %>

Если вы хотите удалить любые из ассоциированных моделей через форму, вы должны сначала включить это с помощью опции :allow_destroy для accepts_nested_attributes_for:

class Person < ActiveRecord::Base
  has_many :projects
  accepts_nested_attributes_for :projects, allow_destroy: true
end

Это позволит указать модели для удаления в хеше атрибутов, добавив элемент формы для параметра _destroy со значением, которое оценивается как true (например, 1, '1', true или 'true'):

<%= form_for @person do |person_form| %>
  ...
  <%= person_form.fields_for :projects do |project_fields| %>
    Delete: <%= project_fields.check_box :_destroy %>
  <% end %>
  ...
<% end %>

Когда используется коллекция, вам может потребоваться знать индекс каждого объекта в массиве. Для этой цели доступен метод index в объекте FormBuilder.

<%= form_for @person do |person_form| %>
  ...
  <%= person_form.fields_for :projects do |project_fields| %>
    Project #<%= project_fields.index %>
    ...
  <% end %>
  ...
<% end %>

Обратите внимание, что #fields_for автоматически сгенерирует скрытое поле для хранения идентификатора записи. Есть случаи, когда это скрытое поле не нужно, и вы можете передать include_id: false чтобы предотвратить автоматическое отображение #fields_for.

file_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1223
def file_field(object_name, method, options = {})
  Tags::FileField.new(object_name, method, self, options).render
end

Возвращает тег ввода для загрузки файлов, настроенный для доступа к указанному атрибуту (идентифицируемому по method) объекта, назначенного шаблону (идентифицируемого по object). Дополнительные параметры для тега ввода можно передать в виде хэша с options. Эти параметры будут добавлены к HTML в качестве атрибутов HTML, как показано в примере.

Использование этого метода внутри блока form_for установит кодировку окружающей формы на multipart/form-data.

Параметры

  • Создаёт стандартные атрибуты HTML для тега.

  • :disabled — Если установлено в true, пользователь не сможет использовать этот элемент ввода.

  • :multiple — Если установлено в true, *в большинстве современных браузеров* пользователь сможет выбрать несколько файлов.

  • :accept — Если установлено в один или несколько MIME-типов, пользователю будет предложен фильтр при выборе файла. Вам всё ещё нужно настроить валидации модели.

Примеры

file_field(:user, :avatar)
# => <input type="file" id="user_avatar" name="user[avatar]" />

file_field(:post, :image, multiple: true)
# => <input type="file" id="post_image" name="post[image][]" multiple="multiple" />

file_field(:post, :attached, accept: 'text/html')
# => <input accept="text/html" type="file" id="post_attached" name="post[attached]" />

file_field(:post, :image, accept: 'image/png,image/gif,image/jpeg')
# => <input type="file" id="post_image" name="post[image]" accept="image/png,image/gif,image/jpeg" />

file_field(:attachment, :file, class: 'file_input')
# => <input type="file" id="attachment_file" name="attachment[file]" class="file_input" />
form_for(record, options = {}, &block) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 428
def form_for(record, options = {}, &block)
  raise ArgumentError, "Missing block" unless block_given?
  html_options = options[:html] ||= {}

  case record
  when String, Symbol
    object_name = record
    object      = nil
  else
    object      = record.is_a?(Array) ? record.last : record
    raise ArgumentError, "First argument in form cannot contain nil or be empty" unless object
    object_name = options[:as] || model_name_from_record_or_class(object).param_key
    apply_form_for_options!(record, object, options)
  end

  html_options[:data]   = options.delete(:data)   if options.has_key?(:data)
  html_options[:remote] = options.delete(:remote) if options.has_key?(:remote)
  html_options[:method] = options.delete(:method) if options.has_key?(:method)
  html_options[:enforce_utf8] = options.delete(:enforce_utf8) if options.has_key?(:enforce_utf8)
  html_options[:authenticity_token] = options.delete(:authenticity_token)

  builder = instantiate_builder(object_name, object, options)
  output  = capture(builder, &block)
  html_options[:multipart] ||= builder.multipart?

  html_options = html_options_for_form(options[:url] || {}, html_options)
  form_tag_with_body(html_options, output)
end

Создаёт форму, позволяющую пользователю создавать или обновлять атрибуты конкретного объекта модели.

Метод может использоваться несколькими слегка различающимися способами, в зависимости от того, насколько вы хотите полагаться на Rails для автоматического вывода из модели, как должна быть построена форма. Для общих объектов модели форму можно создать, передав form_for строку или символ, представляющий объект, который нас интересует:

<%= form_for :person do |f| %>
  First name: <%= f.text_field :first_name %><br />
  Last name : <%= f.text_field :last_name %><br />
  Biography : <%= f.text_area :biography %><br />
  Admin?    : <%= f.check_box :admin %><br />
  <%= f.submit %>
<% end %>

Переменная f передаётся в блок в виде объекта FormBuilder, который включает в себя знания об объекте модели, представленном :person передаваемом в form_for. Методы, определённые в FormBuilder, используются для генерации полей, связанных с этой моделью. Таким образом, например,

<%= f.text_field :first_name %>

будет расширено до

<%= text_field :person, :first_name %>

что приводит к HTML-тегу <input>, у которого атрибут name имеет значение person[first_name]. Это означает, что при отправке формы значение, введённое пользователем, будет доступно в контроллере как params[:person][:first_name].

Для полей, сгенерированных таким образом с помощью FormBuilder, если :person также является именем экземпляра переменной @person, значение по умолчанию для поля, отображаемого при первоначальном отображении формы (например, в ситуации редактирования существующего записей), будет значением соответствующего атрибута @person.

Правый аргумент form_for — это необязательный хэш опций:

  • :url — URL, на который будет отправляться форма. Это может быть представлено таким же образом, как значения, передаваемые в url_for или link_to. Так, например, можно напрямую использовать именованный маршрут. Если опция :url не указана, по умолчанию форма будет отправлена ​​на текущий URL (мы опишем ниже альтернативное использование form_for с ресурсно-ориентированной направленностью, в котором URL не нужно указывать явно).

  • :namespace — имя пространства имён для вашей формы, чтобы обеспечить уникальность атрибутов id элементов формы. Атрибут пространства имён будет предваряться нижним подчеркиванием в сгенерированном HTML идентификаторе.

  • :method — метод, который будет использоваться при отправке формы, обычно «get» или «post». Если используется «patch», «put», «delete» или другой глагол, добавляется скрытый ввод с именем _method, чтобы смоделировать глагол над post.

  • :authenticity_token — маркер подлинности для использования в форме. Используйте только в том случае, если вам нужно передать строку пользовательского маркера подлинности или не добавлять поле authenticity_token вообще (передав false). Дистанционные формы могут опустить встроенный маркер подлинности, задав config.action_view.embed_authenticity_token_in_remote_forms = false. Это полезно при кэшировании фрагментов формы. Дистанционные формы получают маркер подлинности из тега meta, поэтому вставка не требуется, если вы поддерживаете браузеры без JavaScript.

  • :remote — если установлено в true, позволит драйверам Unobtrusive JavaScript управлять поведением отправки. По умолчанию это поведение — отправка по AJAX.

  • :enforce_utf8 — если установлено в false, скрытый ввод с именем utf8 не выводится.

  • :html — необязательные HTML-атрибуты для тега формы.

Также обратите внимание, что form_for не создаёт исключительной области. Всё ещё возможно использовать как автономные методы FormHelper, так и методы из FormTagHelper. Например:

<%= form_for :person do |f| %>
  First name: <%= f.text_field :first_name %>
  Last name : <%= f.text_field :last_name %>
  Biography : <%= text_area :person, :biography %>
  Admin?    : <%= check_box_tag "person[admin]", "1", @person.company.admin? %>
  <%= f.submit %>
<% end %>

Это также работает для методов в FormOptionHelper и DateHelper, которые предназначены для работы с объектом в качестве основы, например FormOptionHelper#collection_select и ActionView::Helpers::DateHelper#datetime_select.

form_for с объектом модели

В примерах выше объект для создания или редактирования представлялся символом, переданным в form_for, и мы отметили, что строку также можно использовать эквивалентно. Однако также возможно передать сам объект модели в form_for. Например, если @post — это существующая запись, которую вы хотите отредактировать, вы можете создать форму, используя

<%= form_for @post do |f| %>
  ...
<% end %>

Это ведёт себя почти так же, как описано ранее, с несколькими небольшими исключениями. Во-первых, префикс, используемый для именования элементов ввода в форме (следовательно, ключ, обозначающий их в хэше params ), фактически получен из класса объекта, например params[:post] , если класс объекта — Post. Однако это можно переопределить, используя опцию :as, например —

<%= form_for(@person, as: :client) do |f| %>
  ...
<% end %>

что приведёт к params[:client].

Во-вторых, значения полей, отображаемые при первоначальном отображении формы, берутся из атрибутов объекта, переданного в form_for, независимо от того, является ли объект экземпляром переменной. Итак, например, если у нас есть локальная переменная post , представляющая существующую запись,

<%= form_for post do |f| %>
  ...
<% end %>

будет генерировать форму с полями, начальное состояние которых отражает текущие значения атрибутов post.

Ресурсно-ориентированный стиль

В только что показанных примерах, хотя и не указано явно, нам всё ещё нужно использовать опцию :url для указания того, куда будет отправляться форма. Однако возможна дальнейшая упрощение, если запись, переданная в form_for — это ресурс, т.е. она соответствует набору маршрутов REST, например, определённых с помощью метода resources в config/routes.rb. В этом случае Rails просто выведет соответствующий URL из самой записи. Например,

<%= form_for @post do |f| %>
  ...
<% end %>

тогда эквивалентно чему-то вроде:

<%= form_for @post, as: :post, url: post_path(@post), method: :patch, html: { class: "edit_post", id: "edit_post_45" } do |f| %>
  ...
<% end %>

А для новой записи

<%= form_for(Post.new) do |f| %>
  ...
<% end %>

эквивалентно чему-то вроде:

<%= form_for @post, as: :post, url: posts_path, html: { class: "new_post", id: "new_post" } do |f| %>
  ...
<% end %>

Однако вы всё ещё можете переопределить отдельные соглашения, такие как:

<%= form_for(@post, url: super_posts_path) do |f| %>
  ...
<% end %>

Вы также можете задать формат ответа, например так:

<%= form_for(@post, format: :json) do |f| %>
  ...
<% end %>

Для маршрутов с именами пространств имён, например admin_post_url:

<%= form_for([:admin, @post]) do |f| %>
 ...
<% end %>

Если у вашего ресурса есть определённые ассоциации, например, вы хотите добавить комментарии к документу при условии, что маршруты установлены правильно:

<%= form_for([@document, @comment]) do |f| %>
 ...
<% end %>

Где @document = Document.find(params[:id]) и @comment = Comment.new.

Установка метода

Вы можете принудительно заставить форму использовать весь массив HTTP-глаголов, установив

method: (:get|:post|:patch|:put|:delete)

в хэше опций. Если глагол не GET или POST, которые непосредственно поддерживаются HTML-формами, форма будет установлена ​​на POST, а скрытый элемент ввода с именем _method будет содержать предназначенный глагол для интерпретации сервером.

Неинвазивный JavaScript

Указание:

remote: true

в хэше опций создаёт форму, которая позволит драйверам неинвазивного JavaScript изменять её поведение. Ожидаемое поведение по умолчанию — это отправка XMLHttpRequest в фоновом режиме вместо стандартной POST-отправки, но в конечном счёте поведение зависит от разработчика реализующего драйвера JavaScript. Несмотря на то, что для сериализации элементов формы используется JavaScript, отправка формы будет работать так же, как и стандартная отправка, с точки зрения стороны приёма (все элементы доступны в params).

Пример:

<%= form_for(@post, remote: true) do |f| %>
  ...
<% end %>

Сгенерированный HTML для этого будет:

<form action='http://www.example.com' method='post' data-remote='true'>
  <input name='_method' type='hidden' value='patch' />
  ...
</form>

Настройка HTML-опций

Вы можете установить атрибуты данных непосредственно, передав хэш данных, но все остальные HTML-опции должны быть заключены в ключ HTML. Пример:

<%= form_for(@post, data: { behavior: "autosave" }, html: { name: "go" }) do |f| %>
  ...
<% end %>

Сгенерированный HTML для этого будет:

<form action='http://www.example.com' method='post' data-behavior='autosave' name='go'>
  <input name='_method' type='hidden' value='patch' />
  ...
</form>

Удаление скрытых идентификаторов модели

Метод #form_for автоматически включает идентификатор модели в виде скрытого поля в форме. Это используется для поддержания корреляции между данными формы и её связанной моделью. Некоторые системы ORM не используют идентификаторы для вложенных моделей, поэтому в этом случае вы хотите иметь возможность отключить скрытый идентификатор.

В следующем примере модель Post имеет много комментариев, хранящихся в ней в базе данных NoSQL, поэтому для комментариев нет первичного ключа.

Пример:

<%= form_for(@post) do |f| %>
  <%= f.fields_for(:comments, include_id: false) do |cf| %>
    ...
  <% end %>
<% end %>

Настраиваемые генераторы форм

Вы также можете создавать формы, используя настраиваемый класс FormBuilder. Наследуйте FormBuilder и переопределите или определите некоторые дополнительные помощники, затем используйте свой собственный генератор. Например, предположим, что вы создали помощник для автоматического добавления меток к элементам ввода формы.

<%= form_for @person, url: { action: "create" }, builder: LabellingFormBuilder do |f| %>
  <%= f.text_field :first_name %>
  <%= f.text_field :last_name %>
  <%= f.text_area :biography %>
  <%= f.check_box :admin %>
  <%= f.submit %>
<% end %>

В этом случае, если вы используете это:

<%= render f %>

Рендер шаблона — people/_labelling_form, а локальная переменная, ссылающаяся на генератор формы, называется labelling_form.

Настраиваемый класс FormBuilder автоматически объединяется с опциями вложенного вызова #fields_for, если явно не задан.

Во многих случаях вам нужно будет обернуть это в другой помощник, поэтому вы могли бы сделать что-то вроде следующего:

def labelled_form_for(record_or_name_or_array, *args, &block)
  options = args.extract_options!
  form_for(record_or_name_or_array, *(args << options.merge(builder: LabellingFormBuilder)), &block)
end

Если вам не нужно прикреплять форму к экземпляру модели, ознакомьтесь с ActionView::Helpers::FormTagHelper#form_tag.

Форма для внешних ресурсов

Когда вы создаёте формы для внешних ресурсов, иногда вам нужно установить маркер подлинности или просто рендерить форму без него, например, когда вы отправляете данные на платежный шлюз, а количество и типы полей могут быть ограничены.

Чтобы установить маркер подлинности, вам нужно передать параметр :authenticity_token

<%= form_for @invoice, url: external_url, authenticity_token: 'external_token' do |f|
  ...
<% end %>

Если вы не хотите, чтобы поле маркера подлинности вообще рендерилось, просто передайте false:

<%= form_for @invoice, url: external_url, authenticity_token: false do |f|
  ...
<% end %>
form_with(model: nil, scope: nil, url: nil, format: nil, **options) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 745
def form_with(model: nil, scope: nil, url: nil, format: nil, **options)
  options[:allow_method_names_outside_object] = true
  options[:skip_default_ids] = true

  if model
    url ||= polymorphic_path(model, format: format)

    model   = model.last if model.is_a?(Array)
    scope ||= model_name_from_record_or_class(model).param_key
  end

  if block_given?
    builder = instantiate_builder(scope, model, options)
    output  = capture(builder, &Proc.new)
    options[:multipart] ||= builder.multipart?

    html_options = html_options_for_form_with(url, model, options)
    form_tag_with_body(html_options, output)
  else
    html_options = html_options_for_form_with(url, model, options)
    form_tag_html(html_options)
  end
end

Создаёт тег формы на основе смешивания URL, областей или моделей.

# Using just a URL:
<%= form_with url: posts_path do |form| %>
  <%= form.text_field :title %>
<% end %>
# =>
<form action="/posts" method="post" data-remote="true">
  <input type="text" name="title">
</form>

# Adding a scope prefixes the input field names:
<%= form_with scope: :post, url: posts_path do |form| %>
  <%= form.text_field :title %>
<% end %>
# =>
<form action="/posts" method="post" data-remote="true">
  <input type="text" name="post[title]">
</form>

# Using a model infers both the URL and scope:
<%= form_with model: Post.new do |form| %>
  <%= form.text_field :title %>
<% end %>
# =>
<form action="/posts" method="post" data-remote="true">
  <input type="text" name="post[title]">
</form>

# An existing model makes an update form and fills out field values:
<%= form_with model: Post.first do |form| %>
  <%= form.text_field :title %>
<% end %>
# =>
<form action="/posts/1" method="post" data-remote="true">
  <input type="hidden" name="_method" value="patch">
  <input type="text" name="post[title]" value="<the title of the post>">
</form>

# Though the fields don't have to correspond to model attributes:
<%= form_with model: Cat.new do |form| %>
  <%= form.text_field :cats_dont_have_gills %>
  <%= form.text_field :but_in_forms_they_can %>
<% end %>
# =>
<form action="/cats" method="post" data-remote="true">
  <input type="text" name="cat[cats_dont_have_gills]">
  <input type="text" name="cat[but_in_forms_they_can]">
</form>

Параметры в формах доступны в контроллерах в соответствии с их именованным вложенным строением. Так, поля с именами title и post[title] доступны как params[:title] и params[:post][:title] соответственно.

По умолчанию form_with добавляет атрибут data-remote, отправляя форму асинхронно через XMLHTTPRequest, если используется драйвер Unobtrusive JavaScript, такой как rails-ujs. Подробнее см. опцию :local.

Для удобства сравнения в примерах выше отсутствуют кнопки отправки, а также автоматически сгенерированные скрытые поля, которые обеспечивают поддержку UTF-8 и добавляют маркер подлинности, необходимый для защиты от межсайтовых поддельных запросов.

Ориентированный на ресурсы стиль

Во многих приведённых примерах параметр :model, переданный в form_with , является ресурсом. Он соответствует набору маршрутов REST, скорее всего, определённых через resources в config/routes.rb.

Таким образом, при передаче такой записи модели Rails определяет URL и метод.

<%= form_with model: @post do |form| %>
  ...
<% end %>

тогда эквивалентно чему-то вроде:

<%= form_with scope: :post, url: post_path(@post), method: :patch do |form| %>
  ...
<% end %>

И для новой записи

<%= form_with model: Post.new do |form| %>
  ...
<% end %>

эквивалентно чему-то вроде:

<%= form_with scope: :post, url: posts_path do |form| %>
  ...
<% end %>

Опции

  • :url - URL, на который отправляется форма. Аналогично значениям, передаваемым в url_for или link_to . Например, вы можете использовать именованный маршрут напрямую. Если :scope передаётся без :url , форма отправляется на текущий URL.

  • :method - Метод, используемый при отправке формы, обычно «get» или «post». Если «patch», «put», «delete» или другой глагол, добавляется скрытое поле с именем _method для имитации глагола через post.

  • :format - Формат маршрута, на который отправляется форма. Полезно при отправке на другой тип ресурса, такой как :json . Пропускается, если передан :url.

  • :scope - Область для префикса имен полей ввода и, таким образом, группировки переданных параметров в контроллерах.

  • :model - Объект модели для вывода :url и :scope плюс заполнения значений полей ввода. Так, если атрибут title имеет значение «Ahoy!», то значение поля ввода title будет «Ahoy!». Если модель представляет собой новую запись, генерируется форма создания, если существующую запись, то форма обновления. Передайте :scope или :url для переопределения значений по умолчанию. Например, преобразуйте params[:post] в params[:article].

  • :authenticity_token - Маркер подлинности, используемый в форме. Переопределите его с помощью пользовательского маркера подлинности или передайте false для пропуска поля маркера подлинности. Полезно при отправке на внешний ресурс, такой как шлюз платежей, который может ограничивать допустимые поля. Отдалённые формы могут опустить встроенный маркер подлинности, установив config.action_view.embed_authenticity_token_in_remote_forms = false . Это полезно при кэшировании фрагментов формы. Отдалённые формы получают маркер подлинности из тега meta , поэтому встраивание не требуется, если вы поддерживаете браузеры без JavaScript.

  • :local - По умолчанию отправка формы — это удалённые и неутражаемые XHR-запросы. Отключить удалённые отправки с помощью local: true.

  • :skip_enforcing_utf8 - По умолчанию выводится скрытое поле с именем utf8 для принудительной отправки UTF-8. Установите в значение true, чтобы пропустить поле.

  • :builder - Переопределить объект, используемый для построения формы.

  • :id - Необязательный атрибут id HTML.

  • :class - Необязательный атрибут class HTML.

  • :data - Необязательные атрибуты данных HTML.

  • :html - Другие необязательные атрибуты тега формы HTML.

Примеры

При отсутствии блока, form_with генерирует только открывающий тег формы.

<%= form_with(model: @post, url: super_posts_path) %>
<%= form_with(model: @post, scope: :article) %>
<%= form_with(model: @post, format: :json) %>
<%= form_with(model: @post, authenticity_token: false) %> # Disables the token.

Для пространств имён маршрутов, например, admin_post_url:

<%= form_with(model: [ :admin, @post ]) do |form| %>
  ...
<% end %>

Если у вашего ресурса есть определённые ассоциации, например, вы хотите добавить комментарии к документу, при условии правильного определения маршрутов:

<%= form_with(model: [ @document, Comment.new ]) do |form| %>
  ...
<% end %>

Где @document = Document.find(params[:id]).

При использовании меток form_with требует установки id для поля, которое меткой метится:

<%= form_with(model: @post) do |form| %>
  <%= form.label :title %>
  <%= form.text_field :title, id: :post_title %>
<% end %>

См. label для получения дополнительной информации о том, как выводится атрибут for.

Смешивание с другими помощниками форм

Хотя form_with использует объект FormBuilder, можно смешивать автономные методы FormHelper и методы из FormTagHelper:

<%= form_with scope: :person do |form| %>
  <%= form.text_field :first_name %>
  <%= form.text_field :last_name %>

  <%= text_area :person, :biography %>
  <%= check_box_tag "person[admin]", "1", @person.company.admin? %>

  <%= form.submit %>
<% end %>

То же самое относится к методам в FormOptionHelper и DateHelper, предназначенным для работы с объектом в качестве основы, например, FormOptionHelper#collection_select и ActionView::Helpers::DateHelper#datetime_select.

Указание метода

Вы можете принудительно использовать полный набор HTTP-глаголов, установив

method: (:get|:post|:patch|:put|:delete)

в хэше опций. Если глагол не GET или POST, которые изначально поддерживаются HTML-формами, форма будет установлена в POST, а скрытое поле с именем _method будет содержать предназначенный глагол для интерпретации сервером.

Установка HTML-опций

Вы можете установить атрибуты данных непосредственно в хэше данных, но HTML-опции кроме id и class должны быть заключены в ключ HTML:

<%= form_with(model: @post, data: { behavior: "autosave" }, html: { name: "go" }) do |form| %>
  ...
<% end %>

генерирует

<form action="/posts/123" method="post" data-behavior="autosave" name="go">
  <input name="_method" type="hidden" value="patch" />
  ...
</form>

Удаление скрытых id моделей

Метод form_with автоматически включает идентификатор модели в виде скрытого поля в форме. Это используется для поддержания связи между данными формы и связанной моделью. Некоторые системы ORM не используют идентификаторы вложенных моделей, поэтому в этом случае вы хотите иметь возможность отключить скрытый идентификатор.

В следующем примере модель Post имеет много комментариев, хранящихся внутри неё в базе данных NoSQL, поэтому для комментариев нет первичного ключа.

<%= form_with(model: @post) do |form| %>
  <%= form.fields(:comments, skip_id: true) do |fields| %>
    ...
  <% end %>
<% end %>

Настраиваемые строители форм

Вы также можете создавать формы с использованием настраиваемого класса FormBuilder. Наследуйте от FormBuilder и переопределите или определите ещё несколько помощников, затем используйте ваш настраиваемый строитель. Например, давайте представим, что вы создали помощник для автоматического добавления меток к полям ввода формы.

<%= form_with model: @person, url: { action: "create" }, builder: LabellingFormBuilder do |form| %>
  <%= form.text_field :first_name %>
  <%= form.text_field :last_name %>
  <%= form.text_area :biography %>
  <%= form.check_box :admin %>
  <%= form.submit %>
<% end %>

В этом случае, если вы используете:

<%= render form %>

Отображаемый шаблон people/_labelling_form , а локальная переменная, ссылающаяся на строитель формы, называется labelling_form.

Настраиваемый класс FormBuilder автоматически объединяется с параметрами вложенного вызова fields , если явно не задано другое.

Во многих случаях вы захотите заключить всё вышеизложенное в другой помощник, поэтому вы можете сделать что-то вроде этого:

def labelled_form_with(**options, &block)
  form_with(**options.merge(builder: LabellingFormBuilder), &block)
end
hidden_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1191
def hidden_field(object_name, method, options = {})
  Tags::HiddenField.new(object_name, method, self, options).render
end

Возвращает скрытый тег ввода, настроенный для доступа к указанному атрибуту (идентифицированному по method ) объекта, назначенного шаблону (идентифицированному по object). Дополнительные опции тега ввода могут быть переданы в виде хэша с options . Эти опции будут добавлены к HTML в качестве атрибута HTML-элемента, как показано в примере.

Примеры

hidden_field(:signup, :pass_confirm)
# => <input type="hidden" id="signup_pass_confirm" name="signup[pass_confirm]" value="#{@signup.pass_confirm}" />

hidden_field(:post, :tag_list)
# => <input type="hidden" id="post_tag_list" name="post[tag_list]" value="#{@post.tag_list}" />

hidden_field(:user, :token)
# => <input type="hidden" id="user_token" name="user[token]" value="#{@user.token}" />
label(object_name, method, content_or_options = nil, options = nil, &block) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1131
def label(object_name, method, content_or_options = nil, options = nil, &block)
  Tags::Label.new(object_name, method, self, content_or_options, options).render(&block)
end

Возвращает тег метки, настроенный для маркировки поля ввода для указанного атрибута (идентифицированного по method ) объекта, назначенного шаблону (идентифицированного по object). Текст метки по умолчанию соответствует имени атрибута, если не найдено перевода в текущем локале I18n (через helpers.label.<modelname>.<attribute>) или вы его явно не задаёте. Дополнительные опции тега метки могут быть переданы в виде хэша с options . Эти опции будут добавлены к HTML в качестве атрибута HTML-элемента, как в показанном примере, за исключением опции :value , которая предназначена для назначения меток для тегов #radio_button (где значение используется в ID тега ввода).

Примеры

label(:post, :title)
# => <label for="post_title">Title</label>

Вы можете локализовать свои метки на основе имён модели и атрибутов. Например, вы можете определить следующее в своём локале (например, en.yml)

helpers:
  label:
    post:
      body: "Write your entire text here"

Что затем приведёт к

label(:post, :body)
# => <label for="post_body">Write your entire text here</label>

Локализация также может быть основана только на переводе имени атрибута (если вы используете ActiveRecord):

activerecord:
  attributes:
    post:
      cost: "Total cost"

label(:post, :cost)
# => <label for="post_cost">Total cost</label>

label(:post, :title, "A short title")
# => <label for="post_title">A short title</label>

label(:post, :title, "A short title", class: "title_label")
# => <label for="post_title" class="title_label">A short title</label>

label(:post, :privacy, "Public Post", value: "public")
# => <label for="post_privacy_public">Public Post</label>

label(:post, :terms) do
  raw('Accept <a href="/terms">Terms</a>.')
end
# => <label for="post_terms">Accept <a href="/terms">Terms</a>.</label>
month_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1482
def month_field(object_name, method, options = {})
  Tags::MonthField.new(object_name, method, self, options).render
end

Возвращает элемент #text_field типа “month”.

month_field("user", "born_on")
# => <input id="user_born_on" name="user[born_on]" type="month" />

Значение по умолчанию генерируется путем вызова strftime с “%Y-%m” на значении объекта, что обеспечивает ожидаемое поведение для экземпляров DateTime и ActiveSupport::TimeWithZone.

@user.born_on = Date.new(1984, 1, 27)
month_field("user", "born_on")
# => <input id="user_born_on" name="user[born_on]" type="date" value="1984-01" />
number_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1525
def number_field(object_name, method, options = {})
  Tags::NumberField.new(object_name, method, self, options).render
end

Возвращает тег input типа “number”.

Параметры

  • Принимает те же параметры, что и number_field_tag

password_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1173
def password_field(object_name, method, options = {})
  Tags::PasswordField.new(object_name, method, self, options).render
end

Возвращает тег input типа “password”, предназначенный для доступа к указанному атрибуту (определяемому method) объекта, присвоенного шаблону (определяемому object). Дополнительные параметры тега input могут быть переданы в виде хеша с options. Эти параметры будут добавлены в HTML как атрибут HTML-элемента, как показано в примере. По соображениям безопасности это поле по умолчанию пустое; передайте значение через options, если этого не требуется.

Примеры

password_field(:login, :pass, size: 20)
# => <input type="password" id="login_pass" name="login[pass]" size="20" />

password_field(:account, :secret, class: "form_input", value: @account.secret)
# => <input type="password" id="account_secret" name="account[secret]" value="#{@account.secret}" class="form_input" />

password_field(:user, :password, onchange: "if ($('#user_password').val().length > 30) { alert('Your password needs to be shorter!'); }")
# => <input type="password" id="user_password" name="user[password]" onchange="if ($('#user_password').val().length > 30) { alert('Your password needs to be shorter!'); }"/>

password_field(:account, :pin, size: 20, class: 'form_input')
# => <input type="password" id="account_pin" name="account[pin]" size="20" class="form_input" />
phone_field(object_name, method, options = {})

является псевдонимом для #telephone_field

Псевдоним для: telephone_field
radio_button(object_name, method, tag_value, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1333
def radio_button(object_name, method, tag_value, options = {})
  Tags::RadioButton.new(object_name, method, self, tag_value, options).render
end

Возвращает тег радиокнопки для доступа к указанному атрибуту (определяемому method) объекта, присвоенного шаблону (определяемому object). Если текущее значение method равно tag_value, радиокнопка будет отмечена.

Чтобы принудительно установить флажок радиокнопки, передайте checked: true в хеш options. Вы также можете передать HTML-параметры.

# Let's say that @post.category returns "rails":
radio_button("post", "category", "rails")
radio_button("post", "category", "java")
# => <input type="radio" id="post_category_rails" name="post[category]" value="rails" checked="checked" />
#    <input type="radio" id="post_category_java" name="post[category]" value="java" />

# Let's say that @user.receive_newsletter returns "no":
radio_button("user", "receive_newsletter", "yes")
radio_button("user", "receive_newsletter", "no")
# => <input type="radio" id="user_receive_newsletter_yes" name="user[receive_newsletter]" value="yes" />
#    <input type="radio" id="user_receive_newsletter_no" name="user[receive_newsletter]" value="no" checked="checked" />
range_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1533
def range_field(object_name, method, options = {})
  Tags::RangeField.new(object_name, method, self, options).render
end

Возвращает тег input типа “range”.

Параметры

  • Принимает те же параметры, что и range_field_tag

search_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1364
def search_field(object_name, method, options = {})
  Tags::SearchField.new(object_name, method, self, options).render
end

Возвращает элемент input типа “search” для доступа к указанному атрибуту (определяемому method) объекта, присвоенного шаблону (определяемому object_name). Элементы input типа “search” могут отображаться браузерами по-разному.

search_field(:user, :name)
# => <input id="user_name" name="user[name]" type="search" />
search_field(:user, :name, autosave: false)
# => <input autosave="false" id="user_name" name="user[name]" type="search" />
search_field(:user, :name, results: 3)
# => <input id="user_name" name="user[name]" results="3" type="search" />
#  Assume request.host returns "www.example.com"
search_field(:user, :name, autosave: true)
# => <input autosave="com.example.www" id="user_name" name="user[name]" results="10" type="search" />
search_field(:user, :name, onsearch: true)
# => <input id="user_name" incremental="true" name="user[name]" onsearch="true" type="search" />
search_field(:user, :name, autosave: false, onsearch: true)
# => <input autosave="false" id="user_name" incremental="true" name="user[name]" onsearch="true" type="search" />
search_field(:user, :name, autosave: true, onsearch: true)
# => <input autosave="com.example.www" id="user_name" incremental="true" name="user[name]" onsearch="true" results="10" type="search" />
telephone_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1373
def telephone_field(object_name, method, options = {})
  Tags::TelField.new(object_name, method, self, options).render
end

Возвращает #text_field типа “tel”.

telephone_field("user", "phone")
# => <input id="user_phone" name="user[phone]" type="tel" />
Также алиас для: phone_field
text_area(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1251
def text_area(object_name, method, options = {})
  Tags::TextArea.new(object_name, method, self, options).render
end

Возвращает набор открывающих и закрывающих тегов textarea, предназначенный для доступа к указанному атрибуту (определяемому method объекта, присвоенного шаблону (определяемому object). Дополнительные параметры тега input могут быть переданы в виде хеша с options.

Примеры

text_area(:post, :body, cols: 20, rows: 40)
# => <textarea cols="20" rows="40" id="post_body" name="post[body]">
#      #{@post.body}
#    </textarea>

text_area(:comment, :text, size: "20x30")
# => <textarea cols="20" rows="30" id="comment_text" name="comment[text]">
#      #{@comment.text}
#    </textarea>

text_area(:application, :notes, cols: 40, rows: 15, class: 'app_input')
# => <textarea cols="40" rows="15" id="application_notes" name="application[notes]" class="app_input">
#      #{@application.notes}
#    </textarea>

text_area(:entry, :body, size: "20x20", disabled: 'disabled')
# => <textarea cols="20" rows="20" id="entry_body" name="entry[body]" disabled="disabled">
#      #{@entry.body}
#    </textarea>
text_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1152
def text_field(object_name, method, options = {})
  Tags::TextField.new(object_name, method, self, options).render
end

Возвращает тег input типа “text”, предназначенный для доступа к указанному атрибуту (определяемому method) объекта, присвоенного шаблону (определяемому object). Дополнительные параметры тега input могут быть переданы в виде хеша с options. Эти параметры будут добавлены в HTML как атрибут HTML-элемента, как показано в примере.

Примеры

text_field(:post, :title, size: 20)
# => <input type="text" id="post_title" name="post[title]" size="20" value="#{@post.title}" />

text_field(:post, :title, class: "create_input")
# => <input type="text" id="post_title" name="post[title]" value="#{@post.title}" class="create_input" />

text_field(:session, :user, onchange: "if ($('#session_user').val() === 'admin') { alert('Your login cannot be admin!'); }")
# => <input type="text" id="session_user" name="session[user]" value="#{@session.user}" onchange="if ($('#session_user').val() === 'admin') { alert('Your login cannot be admin!'); }"/>

text_field(:snippet, :code, size: 20, class: 'code_input')
# => <input type="text" id="snippet_code" name="snippet[code]" size="20" value="#{@snippet.code}" class="code_input" />
time_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1434
def time_field(object_name, method, options = {})
  Tags::TimeField.new(object_name, method, self, options).render
end

Возвращает #text_field типа “time”.

Значение по умолчанию генерируется путем вызова strftime с “%T.%L” на значении объекта. Вы по-прежнему можете переопределить его, передав параметр «value».

Параметры

  • Принимает те же параметры, что и time_field_tag

Пример

time_field("task", "started_at")
# => <input id="task_started_at" name="task[started_at]" type="time" />

Вы можете задать значения для атрибутов «min» и «max», передав экземпляры Date или Time в хеш параметров.

time_field("task", "started_at", min: Time.now)
# => <input id="task_started_at" name="task[started_at]" type="time" min="01:00:00.000" />

В качестве альтернативы вы можете передать строку, отформатированную как время ISO8601, в качестве значений для «min» и «max».

time_field("task", "started_at", min: "01:00:00")
# => <input id="task_started_at" name="task[started_at]" type="time" min="01:00:00.000" />
url_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1508
def url_field(object_name, method, options = {})
  Tags::UrlField.new(object_name, method, self, options).render
end

Возвращает #text_field типа “url”.

url_field("user", "homepage")
# => <input id="user_homepage" name="user[homepage]" type="url" />
week_field(object_name, method, options = {}) Показать исходный код
# File actionview/lib/action_view/helpers/form_helper.rb, line 1499
def week_field(object_name, method, options = {})
  Tags::WeekField.new(object_name, method, self, options).render
end

Возвращает #text_field типа “week”.

week_field("user", "born_on")
# => <input id="user_born_on" name="user[born_on]" type="week" />

Значение по умолчанию генерируется путем вызова strftime с “%Y-W%W” на значении объекта, что обеспечивает ожидаемое поведение для экземпляров DateTime и ActiveSupport::TimeWithZone.

@user.born_on = Date.new(1984, 5, 12)
week_field("user", "born_on")
# => <input id="user_born_on" name="user[born_on]" type="date" value="1984-W19" />

© 2004–2018 David Heinemeier Hansson
Licensed under the MIT License.

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API