0

Я пытаюсь объединить start_date, start hour и start_minute виртуальных атрибутов из моей Event формы для того, чтобы создать атрибут start_datetime (который хранится в базе данных) ,Объединения виртуальных атрибутов одного класса атрибуты в родительском классе (STI)

У меня (через STI) несколько подклассов Event; назовем их TrainingSession и WorkSession и PersonalTime.

Классы структурированы как таковой:

class Event < ActiveRecord::Base 
    ... 
end 

class TrainingSession < Event 
    ... 
end 

class WorkSession < Event 
    ... 
end 

class PersonalTime < Event 
    ... 
end 

Соответствующие части event.rb:

class Event < ActiveRecord::Base 
    attr_accessor :start_date, :start_hour, :start_minute 

    validates :start_datetime, :presence => true 

    before_validation :merge_attributes_for_datetime_string 

    def merge_attributes_for_datetime_string 
    start_datetime_string = "#{ start_date } #{ start_hour }:#{ start_minute }:00" 
    end 

    def start_datetime=(start_datetime_string) 
    self.start_datetime = start_datetime_string 
    end 

    def start_date 
    start_datetime.strftime("%d") if start_datetime? 
    end 

    def start_hour 
    start_datetime.strftime("%H") if start_datetime? 
    end 

    def start_minute 
    start_datetime.strftime("%M") if start_datetime? 
    end 
end 

... и events_controller.rb:

def create 
    @event = Event.new(event_params) 
    if @event.save 
     redirect_to :root, :flash => { :success => "Event added." } 
    else 
     redirect_to :back, :flash => { :notice => "There was an error creating the event." } 
    end 
    end 

    private 

    def event_params 
    params.require(:event).permit(
     :type, 
     :start_datetime, 
     :start_date, 
     :start_hour, 
     :start_minute, 
     ... 
    ) 
    end 

    def training_session_params 
    params.require(:training_session).permit(
     ... 
    ) 
    end 

    def work_session_params 
    params.require(:work_session).permit(
     ... 
    ) 
    end 

    def personal_time_params 
    params.require(:personal_time).permit(
     ... 
    ) 
    end 

Я проверял в моей серверных журналов, что правильные параметры отправляются из формы:

Parameters: {"utf8"=>"✓", "authenticity_token"=>"<TOKEN HERE>=", "event"=>{"start_date" => "2013-08-23", "start_hour"=>"15", "start_minute"=>"00", "type"=>"PersonalTime"}, "commit"=>"Add Personal Time"} 

Тем не менее каждый раз, когда я пытаюсь создать событие (любого типа), я получаю уведомление There was an error creating the event. (согласно моему создать метод). Если я прокомментирую validates :start_datetime, событие будет создано, но с start_datetime из nil.

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

Что мне здесь не хватает? Есть ли лучший способ установить start_datetime?

ответ

0

Основываясь на том, что вы опубликовали, я не вижу, где вы вызываете метод start_datetime.

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

before_validation :merge_attributes_for_datetime_string 

def merge_attributes_for_datetime_string 
    self.start_datetime = "#{ start_date } #{ start_hour }:#{ start_minute }:00" 
end 
+0

Не следует ли существующий метод 'start_datetime = (value_from_other_method)' действует как сеттер? (По крайней мере, * рабочий *, если не самый чистый способ его обработки) – jasonmklug

+0

... Кроме того, если я просто использую 'start_datetime' в качестве имени моего метода, это мешает в любое время, когда я хочу получить атрибут start_datetime из базы данных , – jasonmklug

+0

@ jasonmklug, Да, вы правы, в этом случае это вызовет проблемы. Таким образом, вы являетесь именем метода 'merge_attributes_for_datetime_string', будет правильным в этом случае. – vee

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