Как добавить виртуальный атрибут к модели в Ruby on Rails?
Я работаю над приложением RubyonRails / ActiveAdmin. Моя версия RoR-4.2.5, а версия AA-1.0.0. У меня есть модель Message
следующим образом.
class Message < ActiveRecord::Base
belongs_to :user
validates :user, :content, presence: true
def palindrome
# return true/false
end
end
как вы видите, я хочу иметь атрибут только для чтения palindrome
который зависит только от content
сообщения. Я хочу, чтобы этот атрибут рассматривался точно так же, как обычный атрибут. Под нормальным, я имею в виду, когда я получаю сообщения через rails console
или запрос json
формат сообщений, я хочу видеть palindrome
атрибут в списке. Я также хотелось бы иметь фильтр для сообщения по этому атрибуту.
Я не уверен, как я могу добиться этого.
2 ответов
в вашей модели вы можете написать методы доступа к атрибутам (reader/writer) для вашего виртуального атрибута palindrome
атрибут так:
# attr_reader
def palindrome
self[:palindrome]
end
# attr_writer
def palindrome=(val)
self[:palindrome] = val
end
# virtual attribute
def palindrome
#return true/false
end
и, как вы используете Rails 4, Вы должны белый список palindrome
атрибут, как и любой другой атрибут модели в вашем сильном определении param внутри вашего контроллера, чтобы иметь возможность массово назначить значение palindrome
. Что-то вроде этого:--10-->
# your_controller.rb
private
def your_model_params
params.require(:message).permit(:palindrome)
end
взгляните на это RailsCast по виртуальным атрибутам. Хотя, это немного старовато, но было бы полезно для концепций.
Примечание:
виртуальный атрибут не будет отображаться в списке параметров автоматически. Но вы должны иметь доступ к нему через консоль Rails следующим образом:Message.new.palindrome
. Кроме того, вы можете предоставить этот виртуальный атрибут в JSON API, например, если вы используете Активная Модель Сериализатор вы можете: attribute palindrome
в своем MessageSerializer
а то palindrome
будет подвергаться воздействию JSON ПРИКЛАДНОЙ ПРОГРАММНЫЙ ИНТЕРФЕЙС.
Rails на самом деле давайте создадим виртуальные атрибуты таким образом, что вам не придется вручную создавать методы getter и setter:
attr_reader :palindrome #getter
attr_writer :palindrome #setter
attr_accessor :palindrome #both
вы также можете передать несколько аргументов:
attr_accessor :palindrome, :foo, :bar