Module: DB::Model::Record::Base

Defined in:
lib/db/model/record.rb

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Instance Attribute Details

#key_columnsObject (readonly)

Returns the value of attribute key_columns.



41
42
43
# File 'lib/db/model/record.rb', line 41

def key_columns
  @key_columns
end

#propertiesObject (readonly)

Returns the value of attribute properties.



39
40
41
# File 'lib/db/model/record.rb', line 39

def properties
  @properties
end

#relationshipsObject (readonly)

Returns the value of attribute relationships.



40
41
42
# File 'lib/db/model/record.rb', line 40

def relationships
  @relationships
end

#typeObject (readonly)

Returns the value of attribute type.



38
39
40
# File 'lib/db/model/record.rb', line 38

def type
  @type
end

Class Method Details

.extended(klass) ⇒ Object



28
29
30
31
32
33
34
35
36
# File 'lib/db/model/record.rb', line 28

def self.extended(klass)
	klass.instance_variable_set(:@properties, {})
	klass.instance_variable_set(:@relationships, {})
	
	klass.instance_variable_set(:@key_columns, [:id].freeze)
	
	default_type = klass.name.split("::").last.gsub(/(.)([A-Z])/,'\1_\2').downcase!.to_sym
	klass.instance_variable_set(:@type, default_type)
end

Instance Method Details

#create(context, **attributes) ⇒ Object

Directly create one record.



50
51
52
53
54
55
# File 'lib/db/model/record.rb', line 50

def create(context, **attributes)
	Statement::Insert.new(self,
		Statement::Fields.new(attributes.keys),
		Statement::Tuple.new(attributes.values)
	).to_a(context).first
end

#find(context, *key) ⇒ Object

Find records which match the given primary key.



72
73
74
75
76
77
# File 'lib/db/model/record.rb', line 72

def find(context, *key)
	Statement::Select.new(self,
		where: find_predicate(*key),
		limit: Statement::Limit::ONE
	).to_a(context).first
end

#find_predicate(*key) ⇒ Object



79
80
81
# File 'lib/db/model/record.rb', line 79

def find_predicate(*key)
	Statement::Equal.new(self, self.primary_key, key)
end

#insert(context, keys, rows, **attributes) ⇒ Object

Directly insert one or more records.



58
59
60
61
62
63
64
65
66
67
68
69
# File 'lib/db/model/record.rb', line 58

def insert(context, keys, rows, **attributes)
	if attributes.any?
		fields = Statement::Fields.new(attributes.keys + keys)
		values = attributes.values
		tuples = rows.map{|row| Statement::Tuple.new(values + row)}
	else
		fields = Statement::Fields.new(keys)
		tuples = rows.map{|row| Statement::Tuple.new(row)}
	end
	
	return Statement::Insert.new(self, fields, Statement::Multiple.new(tuples)).to_a(context)
end

#primary_keyObject



43
44
45
46
47
# File 'lib/db/model/record.rb', line 43

def primary_key
	@key_columns.map do |name|
		DB::Identifier[@type, name]
	end
end

#property(name, klass = nil) ⇒ Object



87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
# File 'lib/db/model/record.rb', line 87

def property(name, klass = nil)
	if @properties.key?(name)
		raise ArgumentError.new("Property #{name.inspect} already defined!")
	end
	
	@properties[name] = klass
	
	if klass
		self.define_method(name) do
			if @changed&.key?(name)
				return @changed[name]
			elsif @attributes.key?(name)
				value = @attributes[name]
				klass.load(value)
			else
				nil
			end
		end
	else
		self.define_method(name) do
			if @changed&.key?(name)
				return @changed[name]
			else
				@attributes[name]
			end
		end
	end
	
	self.define_method(:"#{name}=") do |value|
		@changed ||= Hash.new
		@changed[name] = value
	end
	
	self.define_method(:"#{name}?") do
		value = self.send(name)
		
		if !value
			false
		elsif value.respond_to?(:empty?)
			!value.empty?
		else
			true
		end
	end
end

#where(context, *arguments, **options, &block) ⇒ Object



83
84
85
# File 'lib/db/model/record.rb', line 83

def where(context, *arguments, **options, &block)
	Where.new(context, self, *arguments, **options, &block)
end