2012-05-26 5 views
10

Я использую simple_form и хочу переопределить считыватели для атрибутов модели.Превосходные читатели атрибутов модели не влияют на поля ввода simple_form

Таким образом, следующее не работает

class C < ActiveRecord::Base 

    # it has attribute named pack 

    def pack 
    "Some value" 
    end 

end 

В связи есть следующий код

<%= simple_form_for @c do |f| %> 
    <%= f.input :pack %> 
<% end %> 

, таким образом, он должен показать форму с поля ввода, имеющего значение «какое-то значение», но она пуста. Почему не отменяет работу с simple_form?

+0

у меня такая же проблема, я думаю, 'simple_form', или скорее рельсы образуют хелперы, используйте' read_attribute' вместо ' отправить' т o получить входные значения из объектов ActiveRecord. – Kris

ответ

12

Я понял это, мой комментарий был в основном правильным, simple_form опирается на помощников формы Rails, которые используют read_attribute, чтобы получить значение от объекта ActiveRecord, таким образом, считывая значение в базе данных и не используя ваш метод. Симптом стойкости/домена/презентации. Обойти это:

<%= f.input :pack, :input_html => { :value => @c.pack } %> 
# or 
<%= f.input :pack, :input_html => { :value => f.object.pack } %> 

Или, если вы хотите, чтобы это поведение по умолчанию вы можете создать свой собственный вид строитель на вершине simple_for, таких как:

# lib/my_form_builder.rb ** 

class MyFormBuilder < SimpleForm::FormBuilder                        
    def input(attribute_name, options={}, &block)         
    options[:input_html] ||= {}             
    options[:input_html][:value] = object.send(attribute_name)     
    super(attribute_name, options, &block)               
    end 
end 

И в вашей форме:

<%= simple_form_for @c, :builder => MyFormBuilder do |f| %> 
    <%= f.input :pack %> 
<% end %> 

** в Rails 3, я не думаю, что lib добавляется к пути загрузки по умолчанию, так что вам может понадобиться, чтобы добавить его и перезапустить вас приложение или положите его в app/models (отказ от ответственности не рекомендуется, lib лучше).

5

В Rails 3.2, по крайней мере, он больше не использует read_attribute. Но если вы используете текстовое поле, для извлечения значения используется InstanceTag.value_before_type_cast. При этом используется:

object.respond_to?(method_name + "_before_type_cast") ? 
    object.send(method_name + "_before_type_cast") : 
    object.send(method_name) 

(где method_name это имя атрибута в этом контексте)

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

alias pack_before_type_cast pack 

это работает для меня, просто убедитесь, что вернуть строку там ...

+0

Работал для меня тоже. :) –

+0

Работал для меня. Пришлось использовать 'alias_method', потому что я был в беспокойстве –

Смежные вопросы