有两种车型:Car(例如Audi,Mercedes)和Option(ABS,Laser Headlights,Night Vision ......)。汽车habtm选项。
假设奥迪和梅赛德斯"夜视"选项可用。 但要在梅赛德斯拥有它,你需要为这个选项支付一些额外的钱。因此,我猜我需要以某种方式扩展我的选项模型,以存储某些汽车的选项额外价格。我认为车型也应该进行修改。但无法想象如何。
我的目标是实现这样的行为:
Audi.options.night_vision.extra_price =>零
Mercedes.options.night_vision.extra_price => 300
当然,我不想复制"夜视"每辆车的选项集中的选项。
感谢。
答案 0 :(得分:0)
这既不是最简单的,也不是最优雅的,只是基于对如何实施选项的假设而有效的想法。如果您需要更多帮助,请回复我。
要实现audi.options.night_vision.extra_price我假设您有以下模型:
class car
include Mongoid::Document
field :name, type: String
has_and_belongs_to_many :options do
def night_vision
@target.find_by(name:'night_vision')
end
end
end
class option
include Mongoid::Document
field :name, type: String
field :extra_price, type: Float
has_and_belongs_to_many :cars
end
这将使您能够:
audi = Car.find_by(name:'audi')
audi.options.night_vision.extra_price
如果上述假设是正确的,你应该可以像这样修改你的类:
class option
include Mongoid::Document
attr_accessor :extra_price
field :name, type: String
has_and_belongs_to_many :cars
embeds_many :extras
end
class extra
include Mongoid::Document
field :car_id, type: String
field :price, type: String
embedded_in :option
end
class car
include Mongoid::Document
field :name, type: String
has_and_belongs_to_many :options do
def night_vision
extra = @target.find_by(name:'night_vision')
extra_price = extra.prices.find_by(car_id: @target._id.to_s) if extra
extra.extra_price = extra_price.price if extra && extra_price
return extra
end
def find_or_create_option(args)
extra = @target.find_or_create_by(name:args)
price = extra.extras.find_or_create_by(car_id:@target._id.to_s)
price.set(price: args.price
end
end
end
然后,您应该可以填写以下选项:
audi.options.find_or_create_option({name:'night_vision', price:2310.30})
bmw.options.find_or_create_option({name:'night_vision', price:1840.99})
audi.options.night_vision.extra_price
=> 2310.30
bmw.options.night_vision.extra_price
=> 1840.99
如果你试图在没有night_vision的汽车上找到night_vision,你会得到:
skoda.options.night_vision
=> nil
skoda.options.night_vision.extra_price
=> NoMethodError (undefined method 'extra_price' for nil:NilClass)