Class: ROM::Schema::DSL

Inherits:
BasicObject
Extended by:
Initializer
Defined in:
lib/rom/schema/dsl.rb

Overview

Schema DSL exposed as ‘schema { .. }` in relation classes

Constant Summary collapse

KERNEL_METHODS =
i(extend method).freeze

Instance Attribute Summary collapse

Instance Method Summary collapse

Methods included from Initializer

extended

Constructor Details

#initialize(&block) ⇒ DSL

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.

Returns a new instance of DSL.



60
61
62
63
64
65
66
67
# File 'lib/rom/schema/dsl.rb', line 60

def initialize(*, &block)
  super

  @attributes = {}
  @plugins = {}

  @definition = block
end

Instance Attribute Details

#adapterSymbol (readonly)



38
# File 'lib/rom/schema/dsl.rb', line 38

option :adapter, default: -> { :default }

#associations_dslObject (readonly)



57
58
59
# File 'lib/rom/schema/dsl.rb', line 57

def associations_dsl
  @associations_dsl
end

#attr_classClass (readonly)



34
# File 'lib/rom/schema/dsl.rb', line 34

option :attr_class, default: -> { Attribute }

#attributesObject (readonly)



45
46
47
# File 'lib/rom/schema/dsl.rb', line 45

def attributes
  @attributes
end

#definitionObject (readonly)



53
54
55
# File 'lib/rom/schema/dsl.rb', line 53

def definition
  @definition
end

#inferrerInferrer (readonly)



26
# File 'lib/rom/schema/dsl.rb', line 26

option :inferrer, default: -> { DEFAULT_INFERRER }

#pluginsObject (readonly)



49
50
51
# File 'lib/rom/schema/dsl.rb', line 49

def plugins
  @plugins
end

#relationRelation::Name (readonly)



22
# File 'lib/rom/schema/dsl.rb', line 22

param :relation

#schema_classClass (readonly)



30
# File 'lib/rom/schema/dsl.rb', line 30

option :schema_class, default: -> { Schema }

Instance Method Details

#app_plugin(plugin, options = ::ROM::EMPTY_HASH) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



178
179
180
181
# File 'lib/rom/schema/dsl.rb', line 178

def app_plugin(plugin, options = ::ROM::EMPTY_HASH)
  plugin.extend_dsl(self)
  @plugins[plugin.name] = [plugin, plugin.config.to_hash.merge(options)]
end

#associations(&block) ⇒ AssociationDSL

Define associations for a relation

Examples:

class Users < ROM::Relation[:sql]
  schema(infer: true) do
    associations do
      has_many :tasks
      has_many :posts
      has_many :posts, as: :priority_posts, view: :prioritized
      belongs_to :account
    end
  end
end

class Posts < ROM::Relation[:sql]
  schema(infer: true) do
    associations do
      belongs_to :users, as: :author
    end
  end

  view(:prioritized) do
    where { priority <= 3 }
  end
end


116
117
118
# File 'lib/rom/schema/dsl.rb', line 116

def associations(&block)
  @associations_dsl = AssociationsDSL.new(relation, &block)
end

#attribute(name, type_or_options, options = EMPTY_HASH) ⇒ Object

Defines a relation attribute with its type and options.

When only options are given, type is left as nil. It makes sense when it is used alongside an schema inferrer, which will populate the type.

See Also:



78
79
80
81
82
83
84
85
# File 'lib/rom/schema/dsl.rb', line 78

def attribute(name, type_or_options, options = EMPTY_HASH)
  if attributes.key?(name)
    ::Kernel.raise ::ROM::AttributeAlreadyDefinedError,
                   "Attribute #{ name.inspect } already defined"
  end

  attributes[name] = build_attribute_info(name, type_or_options, options)
end

#build_attribute_info(name, type_or_options, options = EMPTY_HASH) ⇒ Hash

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.

Builds a representation of the information needed to create an attribute. It returns a hash with :type and :options keys.

See Also:

  • ROM::Schema::DSL.[Schema[Schema.build_attribute_info]


128
129
130
131
132
133
134
135
136
137
138
# File 'lib/rom/schema/dsl.rb', line 128

def build_attribute_info(name, type_or_options, options = EMPTY_HASH)
  type, options = if type_or_options.is_a?(::Hash)
                    [nil, type_or_options]
                  else
                    [build_type(type_or_options, options), options]
                  end
  Schema.build_attribute_info(
    type,
    options.merge(name: name)
  )
end

#build_type(type, options = EMPTY_HASH) ⇒ Dry::Types::Type

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.

Builds a type instance from base type and meta options



145
146
147
148
149
150
151
152
153
# File 'lib/rom/schema/dsl.rb', line 145

def build_type(type, options = EMPTY_HASH)
  if options[:read]
    type.meta(source: relation, read: options[:read])
  elsif type.optional? && type.meta[:read]
    type.meta(source: relation, read: type.meta[:read].optional)
  else
    type.meta(source: relation)
  end.meta(Attribute::META_OPTIONS.map { |opt| [opt, options[opt]] if options.key?(opt) }.compact.to_h)
end

#call(&block) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



184
185
186
187
188
189
190
191
192
193
# File 'lib/rom/schema/dsl.rb', line 184

def call(&block)
  instance_exec(&block) if block
  instance_exec(&definition) if definition

  schema_class.define(relation, opts) do |schema|
    plugins.values.each do |plugin, options|
      plugin.apply_to(schema, options)
    end
  end
end

#plugin_options(plugin) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



196
197
198
# File 'lib/rom/schema/dsl.rb', line 196

def plugin_options(plugin)
  @plugins[plugin][1]
end

#primary_key(*names) ⇒ Object

Specify which key(s) should be the primary key



158
159
160
161
162
163
164
# File 'lib/rom/schema/dsl.rb', line 158

def primary_key(*names)
  names.each do |name|
    attributes[name][:type] =
      attributes[name][:type].meta(primary_key: true)
  end
  self
end

#use(plugin_name, options = ::ROM::EMPTY_HASH) ⇒ Object

Enables for the schema



172
173
174
175
# File 'lib/rom/schema/dsl.rb', line 172

def use(plugin_name, options = ::ROM::EMPTY_HASH)
  plugin = ::ROM.plugin_registry[:schema].fetch(plugin_name, adapter)
  app_plugin(plugin, options)
end