代码之家  ›  专栏  ›  技术社区  ›  Debilski

带关联的Ruby Datamapper表继承

  •  5
  • Debilski  · 技术社区  · 15 年前

    我开始学习 Datamapper 我喜欢的是,我可以用真正的继承来编写我的模型。

    现在我想知道,是否有可能在这方面更先进一些:

    class Event
      include DataMapper::Resource
      property :id, Serial
      property :begin, DateTime
      property :type, Discriminator
    end
    
    class Talk<Event
      property :title, String
      belongs_to :meeting
    end
    
    class Meeting<Event
      has n, :talks
    end
    

    该代码无法创建 :title 用于 Talk 显然,鉴别器列在这里没有什么价值,因为从数据库视图来看,这两个列应该有单独的表 谈话 Meeting .

    所以,最后,我想 谈话 会议 共享中定义的相同属性 Event 但是,对于可能的附加属性和0..1:n关系(一个会议可以有几个会谈,但也有一些会谈没有举行会议。)有没有一种方法可以在不重复列定义和/或放弃继承的情况下实现这一点?

    编辑

    再举一个例子:我喜欢继承的部分是,一般的 事件 可以单独查询。所以,当我想知道,在某个特定的时刻 :begin 日期,我不需要查看两个或更多的表,但可以只查询 事件 桌子。在某种程度上,以下结构可以满足我的需要。

    class Event
      include DataMapper::Resource
      property :id, Serial
      property :begin, DateTime
    end
    
    class Talk
      include DataMapper::Resource
      property :id, Serial
      property :title, String
      belongs_to :event
      belongs_to :meeting
    end
    
    class Meeting
      include DataMapper::Resource
      property :id, Serial
      belongs_to :event
      has n, :talks
    end
    

    但是,为了使用它,我需要手动创建一个 事件 每次,我都想创建或编辑 谈话 . 也就是说,我做不到 talk.begin Talk.create(:begin => Time.now) . 有没有办法避免修补所有函数和合并属性?我不想在使用模型时被提醒底层结构。

    1 回复  |  直到 15 年前
        1
  •  7
  •   JamesAlmond    15 年前

    如果您想将事件的属性复制到Talk和Meeting中,那么可以将其移动到一个模块中:

    module EventFields
      def self.included(base)
        base.class_eval do
          include DataMapper::Resource
          property :id, DataMapper::Types::Serial
          property :begin, DateTime 
          # other fields here
        end
      end
    end
    
    class Talk
      include EventFields
      property :title, String
      belongs_to :meeting
    end
    
    class Meeting
      include EventFields
      has n, :talks
    end
    

    这将为您提供不同的表,但意味着减少了重复。

    推荐文章