lore 0.4.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/LICENSE +19 -0
- data/README +74 -0
- data/aspect.rb +80 -0
- data/behaviours/lockable.rb +41 -0
- data/behaviours/movable.rb +54 -0
- data/behaviours/versioned.rb +24 -0
- data/benchmark.rb +193 -0
- data/bits.rb +52 -0
- data/cache/abstract_entity_cache.rb +82 -0
- data/cache/bits.rb +22 -0
- data/cache/cacheable.rb +202 -0
- data/cache/cached_entities.rb +116 -0
- data/cache/file_index.rb +35 -0
- data/cache/mmap_entity_cache.rb +67 -0
- data/clause.rb +528 -0
- data/connection.rb +155 -0
- data/custom_functions.sql +14 -0
- data/exception/ambiguous_attribute.rb +14 -0
- data/exception/cache_exception.rb +30 -0
- data/exception/invalid_klass_parameters.rb +63 -0
- data/exception/invalid_parameter.rb +42 -0
- data/exception/unknown_typecode.rb +19 -0
- data/file_index.sql +56 -0
- data/gui/erb_template.rb +79 -0
- data/gui/erb_template_helpers.rhtml +19 -0
- data/gui/form.rb +314 -0
- data/gui/form_element.rb +676 -0
- data/gui/form_generator.rb +151 -0
- data/gui/templates/button.rhtml +2 -0
- data/gui/templates/checkbox.rhtml +3 -0
- data/gui/templates/checkbox_row.rhtml +1 -0
- data/gui/templates/file.rhtml +2 -0
- data/gui/templates/file_readonly.rhtml +3 -0
- data/gui/templates/form_element.rhtml +5 -0
- data/gui/templates/form_element_horizontal.rhtml +3 -0
- data/gui/templates/form_element_listed.rhtml +8 -0
- data/gui/templates/form_table.rhtml +3 -0
- data/gui/templates/form_table_blank.rhtml +3 -0
- data/gui/templates/form_table_horizontal.rhtml +8 -0
- data/gui/templates/password.rhtml +2 -0
- data/gui/templates/password_readonly.rhtml +3 -0
- data/gui/templates/radio.rhtml +1 -0
- data/gui/templates/radio_row.rhtml +1 -0
- data/gui/templates/select.rhtml +23 -0
- data/gui/templates/text.rhtml +2 -0
- data/gui/templates/text_readonly.rhtml +3 -0
- data/gui/templates/textarea.rhtml +3 -0
- data/gui/templates/textarea_readonly.rhtml +4 -0
- data/lore.gemspec +40 -0
- data/lore.rb +94 -0
- data/migration.rb +48 -0
- data/model.rb +139 -0
- data/model_factory.rb +202 -0
- data/model_shortcuts.rb +16 -0
- data/query_shortcuts.rb +367 -0
- data/reserved_methods.txt +3 -0
- data/result.rb +100 -0
- data/symbol.rb +58 -0
- data/table_accessor.rb +1926 -0
- data/table_deleter.rb +115 -0
- data/table_inserter.rb +168 -0
- data/table_instance.rb +384 -0
- data/table_selector.rb +314 -0
- data/table_updater.rb +155 -0
- data/test/README +31 -0
- data/test/env.rb +5 -0
- data/test/lore_test.log +8218 -0
- data/test/model.rb +142 -0
- data/test/prepare.rb +37 -0
- data/test/tc_aspect.rb +58 -0
- data/test/tc_cache.rb +80 -0
- data/test/tc_clause.rb +104 -0
- data/test/tc_deep_inheritance.rb +49 -0
- data/test/tc_factory.rb +57 -0
- data/test/tc_filter.rb +37 -0
- data/test/tc_form.rb +32 -0
- data/test/tc_model.rb +86 -0
- data/test/tc_prepare.rb +45 -0
- data/test/tc_refined_query.rb +88 -0
- data/test/tc_table_accessor.rb +265 -0
- data/test/test.log +181 -0
- data/test/test_db.sql +400 -0
- data/test/ts_lore.rb +49 -0
- data/types.rb +55 -0
- data/validation/message.rb +60 -0
- data/validation/parameter_validator.rb +104 -0
- data/validation/reason.rb +54 -0
- data/validation/type_validator.rb +91 -0
- data/validation.rb +65 -0
- metadata +170 -0
@@ -0,0 +1,151 @@
|
|
1
|
+
|
2
|
+
require('lore/types')
|
3
|
+
require('lore/gui/form')
|
4
|
+
|
5
|
+
module Lore
|
6
|
+
module GUI
|
7
|
+
|
8
|
+
# Usage:
|
9
|
+
#
|
10
|
+
# generator = Form_Generator.new(Table_Accessor, Lang, :readonly | :mutable)
|
11
|
+
# form = generator.generate
|
12
|
+
#
|
13
|
+
# See documentation of Cuba::GUI::Form for usage of form instances.
|
14
|
+
#
|
15
|
+
class Form_Generator
|
16
|
+
|
17
|
+
def initialize(klass=nil, labels={}, mode=:mutable, custom_elements={}) # {{{
|
18
|
+
|
19
|
+
@logger = Lore.logger
|
20
|
+
@form = Form.new()
|
21
|
+
@labels = labels
|
22
|
+
@klass = klass
|
23
|
+
@custom_elements = custom_elements
|
24
|
+
|
25
|
+
Textarea.reset_counter
|
26
|
+
|
27
|
+
@logger.debug('CUSTOM ELEMENTS: ' << @custom_elements.inspect)
|
28
|
+
|
29
|
+
if @klass.nil? then return end
|
30
|
+
@logger.debug('GET_ATTRIBUTES: ' << @klass.inspect)
|
31
|
+
@logger.debug('GET_ATTRIBUTES: ' << @klass.get_attributes.inspect)
|
32
|
+
@klass.get_attributes.each_pair { |table, attributes|
|
33
|
+
|
34
|
+
# handle attributes passed via attrib_setup:
|
35
|
+
|
36
|
+
attributes.each { |attrib|
|
37
|
+
|
38
|
+
label_tag = table.gsub('.','--') << '--' << attrib
|
39
|
+
if(@labels[label_tag].to_s != '' && @labels[label_tag] != label_tag) then
|
40
|
+
label = @labels[label_tag]
|
41
|
+
else
|
42
|
+
label = attrib.gsub('_',' ').capitalize
|
43
|
+
end
|
44
|
+
|
45
|
+
# @custom_elements is a hash mapping attribute names to
|
46
|
+
# Custom_Element instances.
|
47
|
+
if ((@custom_elements[table]) and
|
48
|
+
(@custom_elements[table][attrib])) then
|
49
|
+
|
50
|
+
form_element = @custom_elements[table][attrib].new(table, attrib, label)
|
51
|
+
form_element.mode = mode
|
52
|
+
@form.add(form_element)
|
53
|
+
|
54
|
+
elsif (@klass.get_primary_keys[table].nil? or
|
55
|
+
!@klass.get_primary_keys[table].include? attrib) and
|
56
|
+
(@klass.get_implicit_attributes[table].nil? or
|
57
|
+
!@klass.get_implicit_attributes[table].include? attrib) and
|
58
|
+
(@klass.get_has_a_klasses.nil? or
|
59
|
+
@klass.get_has_a_klasses[table+'.'+attrib].nil?) and
|
60
|
+
(@klass.get_hidden_attributes[table].nil? or
|
61
|
+
!@klass.get_hidden_attributes[table].include? attrib)
|
62
|
+
then
|
63
|
+
|
64
|
+
case @klass.get_attribute_types[table][attrib]
|
65
|
+
|
66
|
+
when Lore::PG_BOOL
|
67
|
+
form_element = Radio.new(table, attrib, label, ['t','f'])
|
68
|
+
|
69
|
+
when Lore::PG_SMALLINT || Lore::PG_INT
|
70
|
+
form_element = Text.new(table, attrib, label, nil)
|
71
|
+
|
72
|
+
when Lore::PG_VARCHAR
|
73
|
+
form_element = Text.new(table, attrib, label, nil, nil)
|
74
|
+
if (!@klass.get_maxlength.nil? &&
|
75
|
+
!@klass.get_maxlength[table].nil? &&
|
76
|
+
!@klass.get_maxlength[table][attrib.intern].nil?) then
|
77
|
+
form_element.set_length(@klass.get_maxlength[table][attrib.intern])
|
78
|
+
end
|
79
|
+
|
80
|
+
when Lore::PG_TEXT
|
81
|
+
form_element = Textarea.new(table, attrib, label, nil, nil)
|
82
|
+
if (!@klass.get_maxlength.nil? &&
|
83
|
+
!@klass.get_maxlength[table].nil? &&
|
84
|
+
!@klass.get_maxlength[table][attrib.intern].nil?) then
|
85
|
+
form_element.set_length(@klass.get_maxlength[table][attrib.intern])
|
86
|
+
end
|
87
|
+
|
88
|
+
when Lore::PG_TIMESTAMP_TIMEZONE
|
89
|
+
form_element = Date.new(table, attrib, label, nil)
|
90
|
+
|
91
|
+
when Lore::PG_DATE
|
92
|
+
form_element = Date.new(table, attrib, label, nil)
|
93
|
+
|
94
|
+
else
|
95
|
+
form_element = Text.new(table, attrib, label, nil)
|
96
|
+
end
|
97
|
+
|
98
|
+
form_element.set_mode(mode)
|
99
|
+
@form.add(form_element)
|
100
|
+
|
101
|
+
elsif (!@klass.get_has_a_klasses.nil? and
|
102
|
+
!@klass.get_has_a_klasses[table+'.'+attrib].nil?)
|
103
|
+
then
|
104
|
+
foreign_klass = @klass.get_has_a_klasses[table+'.'+attrib]
|
105
|
+
foreign_table = foreign_klass.table_name
|
106
|
+
|
107
|
+
form_element = Klass_Select.new(foreign_klass, table, attrib, label)
|
108
|
+
form_element.set_mode(mode)
|
109
|
+
@form.add(form_element)
|
110
|
+
|
111
|
+
elsif (!@klass.get_aggregate_klasses.nil? and
|
112
|
+
!@klass.get_aggregate_klasses[table+'.'+attrib].nil?)
|
113
|
+
then
|
114
|
+
foreign_klass = @klass.get_aggregate_klasses[table+'.'+attrib]
|
115
|
+
foreign_table = foreign_klass.table_name
|
116
|
+
|
117
|
+
form_element = Klass_Select.new(foreign_klass, table, attrib, label)
|
118
|
+
form_element.set_mode(mode)
|
119
|
+
@form.add(form_element)
|
120
|
+
|
121
|
+
# Attribute is explixit (expected/required) but not
|
122
|
+
# catched before -> Add attribute as hidden field:
|
123
|
+
elsif (!@klass.get_explicit_attributes[table].nil? and
|
124
|
+
@klass.get_explicit_attributes[table].include? attrib)
|
125
|
+
then
|
126
|
+
form_element = Hidden.new(table, attrib)
|
127
|
+
@form.add(form_element)
|
128
|
+
|
129
|
+
elsif (!@klass.get_implicit_attributes[table].nil? and
|
130
|
+
@klass.get_implicit_attributes[table].include? attrib)
|
131
|
+
then
|
132
|
+
@logger.debug(attrib+' is implicit')
|
133
|
+
|
134
|
+
end
|
135
|
+
|
136
|
+
}
|
137
|
+
}
|
138
|
+
end # }}}
|
139
|
+
|
140
|
+
# Returns instance of Cuba::GUI::Form configured
|
141
|
+
# for klass passed in constructor:
|
142
|
+
def generate() # {{{
|
143
|
+
return @form
|
144
|
+
end # }}}
|
145
|
+
|
146
|
+
end # class
|
147
|
+
|
148
|
+
|
149
|
+
end # module
|
150
|
+
end # module
|
151
|
+
|
@@ -0,0 +1 @@
|
|
1
|
+
<div class="lore_checkbox_row"><%= checkboxes %></div>
|
@@ -0,0 +1 @@
|
|
1
|
+
<nobr><font style="width: 120px; "><input type="radio" <%= tag_attributes(attributes) %> /> <%= attributes[:label] %> </font></nobr>
|
@@ -0,0 +1 @@
|
|
1
|
+
<div class="lore_radio_row"><%= radios %></div>
|
@@ -0,0 +1,23 @@
|
|
1
|
+
<div class="lore_select_wrap">
|
2
|
+
<select <%= tag_attributes(attributes) %> >
|
3
|
+
<%=
|
4
|
+
option_index = 0
|
5
|
+
options = "\n"
|
6
|
+
|
7
|
+
range.each { |attrib|
|
8
|
+
attrib = attrib.to_s
|
9
|
+
|
10
|
+
if value.to_s == attrib.to_s then
|
11
|
+
selected = 'selected'
|
12
|
+
else selected = '' end
|
13
|
+
|
14
|
+
options += '<option value="'+attrib.to_s+'" '+selected+' >'
|
15
|
+
options += labels[option_index].to_s
|
16
|
+
options += '</options>'
|
17
|
+
|
18
|
+
option_index += 1
|
19
|
+
}
|
20
|
+
options
|
21
|
+
%>
|
22
|
+
</select>
|
23
|
+
</div>
|
data/lore.gemspec
ADDED
@@ -0,0 +1,40 @@
|
|
1
|
+
|
2
|
+
require 'rake'
|
3
|
+
|
4
|
+
spec = Gem::Specification.new { |s|
|
5
|
+
|
6
|
+
s.name = 'lore'
|
7
|
+
s.rubyforge_project = 'lore'
|
8
|
+
s.summary = 'A flexible ORM based on PostgreSQL'
|
9
|
+
s.description = <<-EOF
|
10
|
+
Lore is an object-relational mapping (ORM) implementation
|
11
|
+
providing many features like prepared statements,
|
12
|
+
(multiple) inheritance, a comfortable query syntax,
|
13
|
+
highly customizable automated form generation,
|
14
|
+
and result caching using memory mapping (MMap).
|
15
|
+
Lore is currently using PostgreSQL as database backend.
|
16
|
+
EOF
|
17
|
+
s.version = '0.4.2'
|
18
|
+
s.author = 'Tobias Fuchs'
|
19
|
+
s.email = 'fuchs@atomnode.net'
|
20
|
+
s.date = Time.now
|
21
|
+
s.files = '*.rb'
|
22
|
+
s.add_dependency('mmap', '>= 0.1')
|
23
|
+
s.add_dependency('postgres', '>= 0.1')
|
24
|
+
s.files = FileList['*',
|
25
|
+
'behaviours/*',
|
26
|
+
'test/*',
|
27
|
+
'cache/*',
|
28
|
+
'validation/*',
|
29
|
+
'gui/*',
|
30
|
+
'gui/templates/*',
|
31
|
+
'exception/*'].to_a
|
32
|
+
|
33
|
+
s.has_rdoc = true
|
34
|
+
s.rdoc_options << '--title' << 'Lore ORM' <<
|
35
|
+
'--main' << 'README' <<
|
36
|
+
'--line-numbers'
|
37
|
+
|
38
|
+
s.homepage = 'http://lore.rubyforge.org'
|
39
|
+
|
40
|
+
}
|
data/lore.rb
ADDED
@@ -0,0 +1,94 @@
|
|
1
|
+
|
2
|
+
require('logger')
|
3
|
+
|
4
|
+
module Lore
|
5
|
+
|
6
|
+
@logfile = '/var/log/lore/query.log'
|
7
|
+
def self.logfile
|
8
|
+
@logfile
|
9
|
+
end
|
10
|
+
def self.logfile=(file)
|
11
|
+
@logger = Logger.new(file)
|
12
|
+
end
|
13
|
+
def self.logger
|
14
|
+
@logger
|
15
|
+
end
|
16
|
+
@logger = Logger.new(Lore.logfile)
|
17
|
+
|
18
|
+
def self.log(&log_block)
|
19
|
+
return if Lore.logging_disabled?
|
20
|
+
Lore.logger.debug(&log_block)
|
21
|
+
end
|
22
|
+
|
23
|
+
def self.log_queries?
|
24
|
+
true
|
25
|
+
end
|
26
|
+
def self.logging_disabled?
|
27
|
+
false
|
28
|
+
end
|
29
|
+
|
30
|
+
@cache_entities = false
|
31
|
+
|
32
|
+
@logins = {
|
33
|
+
}
|
34
|
+
|
35
|
+
def self.set_login_data(login_hash)
|
36
|
+
@logins = login_hash
|
37
|
+
end
|
38
|
+
def self.add_login_data(login_hash)
|
39
|
+
@logins.update(login_hash)
|
40
|
+
end
|
41
|
+
|
42
|
+
def self.path
|
43
|
+
File.expand_path(File.dirname(__FILE__)) + '/'
|
44
|
+
end
|
45
|
+
|
46
|
+
@pg_server = 'localhost'
|
47
|
+
@pg_port = 5432
|
48
|
+
|
49
|
+
def self.pg_server
|
50
|
+
@pg_server
|
51
|
+
end
|
52
|
+
def self.pg_port
|
53
|
+
@pg_port
|
54
|
+
end
|
55
|
+
def self.pg_server=(s)
|
56
|
+
@pg_server = s
|
57
|
+
end
|
58
|
+
def self.pg_port=(p)
|
59
|
+
@pg_port = p
|
60
|
+
end
|
61
|
+
|
62
|
+
def self.user_for(dbname)
|
63
|
+
begin
|
64
|
+
@logins[dbname.to_s][0].to_s
|
65
|
+
rescue ::Exception => excep
|
66
|
+
raise ::Exception.new('Unable to resolve user for database ' << dbname.inspect)
|
67
|
+
end
|
68
|
+
end
|
69
|
+
def self.pass_for(dbname)
|
70
|
+
@logins[dbname.to_s][1].to_s
|
71
|
+
end
|
72
|
+
|
73
|
+
def self.disable_cache
|
74
|
+
@cache_entities = false
|
75
|
+
end
|
76
|
+
|
77
|
+
def self.enable_cache
|
78
|
+
@cache_entities = true
|
79
|
+
end
|
80
|
+
|
81
|
+
def self.cache_enabled?
|
82
|
+
@cache_entities
|
83
|
+
end
|
84
|
+
|
85
|
+
def self.on_connect_commands()
|
86
|
+
"set client_encoding to Unicode; set datestyle to 'European'"
|
87
|
+
end
|
88
|
+
|
89
|
+
end
|
90
|
+
|
91
|
+
require('lore/validation/parameter_validator')
|
92
|
+
require('lore/exception/invalid_parameter')
|
93
|
+
require('lore/exception/invalid_klass_parameters')
|
94
|
+
require('lore/connection')
|
data/migration.rb
ADDED
@@ -0,0 +1,48 @@
|
|
1
|
+
|
2
|
+
module Lore
|
3
|
+
|
4
|
+
|
5
|
+
# Usage:
|
6
|
+
#
|
7
|
+
# Using auto-bootstrap of models:
|
8
|
+
#
|
9
|
+
# class My_Model < Lore::Model
|
10
|
+
# extend Lore::Migration
|
11
|
+
#
|
12
|
+
# table :my_model, :public
|
13
|
+
# primary_key :key_a, :key_a_seq
|
14
|
+
# primary_key :key_b
|
15
|
+
#
|
16
|
+
# has_attributes {
|
17
|
+
# :foo, Lore::Type.integer, { :unique => true, :default => 1 }
|
18
|
+
# :bar, Lore::Type.integer, { :not_null => true, :check => 'bar < 1000' }
|
19
|
+
# }
|
20
|
+
#
|
21
|
+
# def self.up
|
22
|
+
# bootstrap()
|
23
|
+
# My_Model.create(:foo => 23, :bar => 123)
|
24
|
+
# end
|
25
|
+
#
|
26
|
+
# end
|
27
|
+
#
|
28
|
+
module Migration
|
29
|
+
|
30
|
+
def has_attributes(attrib_hash)
|
31
|
+
@model_schema = attrib_hash
|
32
|
+
end
|
33
|
+
|
34
|
+
def update_schema
|
35
|
+
@factory = Model_Factory.new(self.class.to_s)
|
36
|
+
@model_schema.each_pair { |attrib_name, attrib_props|
|
37
|
+
@factory.add_attribute(attrib_name.to_s, attrib_props)
|
38
|
+
}
|
39
|
+
end
|
40
|
+
|
41
|
+
def bootstrap
|
42
|
+
@factory.build_table
|
43
|
+
end
|
44
|
+
|
45
|
+
end
|
46
|
+
|
47
|
+
end
|
48
|
+
|
data/model.rb
ADDED
@@ -0,0 +1,139 @@
|
|
1
|
+
|
2
|
+
require('logger')
|
3
|
+
|
4
|
+
require('lore/aspect');
|
5
|
+
require('lore/table_selector');
|
6
|
+
require('lore/table_inserter');
|
7
|
+
require('lore/table_updater');
|
8
|
+
require('lore/table_deleter');
|
9
|
+
require('lore/table_instance');
|
10
|
+
require('lore/query_shortcuts');
|
11
|
+
require('lore/validation');
|
12
|
+
require('lore/migration');
|
13
|
+
require('lore/validation/parameter_validator');
|
14
|
+
require('lore/exception/invalid_parameter');
|
15
|
+
require('lore/exception/invalid_klass_parameters');
|
16
|
+
require('lore/cache/cacheable');
|
17
|
+
require('lore/table_accessor.rb')
|
18
|
+
|
19
|
+
module Lore
|
20
|
+
|
21
|
+
# For API details see Lore::Table_Accessor
|
22
|
+
#
|
23
|
+
#
|
24
|
+
# =How to define models
|
25
|
+
#
|
26
|
+
# Example:
|
27
|
+
#
|
28
|
+
# require 'lore/model'
|
29
|
+
#
|
30
|
+
# class Vehicle < Lore::Model
|
31
|
+
# end
|
32
|
+
#
|
33
|
+
# class Car < Vehicle
|
34
|
+
# end
|
35
|
+
#
|
36
|
+
# Sets following defaults:
|
37
|
+
#
|
38
|
+
# class Vehicle
|
39
|
+
# table :vehicle, :vehicle_id
|
40
|
+
# primary_key :id # or :vehicle_id if :id is not present
|
41
|
+
# end
|
42
|
+
#
|
43
|
+
# class Car < Vehicle
|
44
|
+
# table :car, :public
|
45
|
+
# primary_key :id # or :car_id if :id is not present
|
46
|
+
# is_a Vehicle, :vehicle_id
|
47
|
+
# end
|
48
|
+
#
|
49
|
+
# = How to use models
|
50
|
+
#
|
51
|
+
# == Creating entities (INSERTs)
|
52
|
+
#
|
53
|
+
# manuf_1 = Manufacturer.create(:name => 'Audi')
|
54
|
+
# manuf_2 = Manufacturer.create(:name => 'BMW')
|
55
|
+
# car = Car.create(:manufacturer => manuf, :name => 'TT')
|
56
|
+
#
|
57
|
+
# == Changing entities (UPDATEs)
|
58
|
+
#
|
59
|
+
# car['name'] = 'BMW318i'
|
60
|
+
# car.manufacturer = manuf_2 # same as car[:manufacturer_id] = manuf_2.manufacturer_id
|
61
|
+
# car.commit
|
62
|
+
#
|
63
|
+
# == Deleting entities (DELETEs)
|
64
|
+
#
|
65
|
+
# car.delete!
|
66
|
+
# is the same as
|
67
|
+
# Car.delete.where(Car.car_id == car.car_id).perform
|
68
|
+
# is the same as
|
69
|
+
# Lore.perform Car.delete.where(Car.car_id == car.car_id)
|
70
|
+
# is the same as
|
71
|
+
# Car.delete { |c|
|
72
|
+
# c.where(c.car_id = car.car_id)
|
73
|
+
# }
|
74
|
+
#
|
75
|
+
# =How to disable/enable features
|
76
|
+
#
|
77
|
+
# Lore::Model extends
|
78
|
+
# * Lore::Cache::Cacheable
|
79
|
+
# * Lore::Query_Shortcuts
|
80
|
+
# * Lore::Validation
|
81
|
+
# * Lore::Aspect
|
82
|
+
#
|
83
|
+
# Each of them is optional. If you want, for example, a minimalistic
|
84
|
+
# version of Lore::Model with comfortable query interfaces you can define
|
85
|
+
# your own Model class that extends the Lore::Query_Shortcuts module only:
|
86
|
+
#
|
87
|
+
# class Slim_Model < Lore::Table_Accessor
|
88
|
+
# extend Lore::Query_Shortcuts
|
89
|
+
# end
|
90
|
+
#
|
91
|
+
# You can use it as base class for other Model classes, too:
|
92
|
+
#
|
93
|
+
# class Cache_Model < Slim_Model
|
94
|
+
# extend Lore::Query_Shortcuts
|
95
|
+
# extend Lore::Cacheable
|
96
|
+
# end
|
97
|
+
#
|
98
|
+
# You also can define this differently for every model by deriving them
|
99
|
+
# from Lore::Table_Accessor and extending every single one of them:
|
100
|
+
#
|
101
|
+
# class User < Lore::Table_Accessor
|
102
|
+
# extend Lore::Query_Shortcuts
|
103
|
+
# extend Lore::Aspect
|
104
|
+
# extend Lore::Validation
|
105
|
+
#
|
106
|
+
# table :user, :public
|
107
|
+
# primary_key :user_id
|
108
|
+
#
|
109
|
+
# end
|
110
|
+
#
|
111
|
+
# =How to use Lore::Model in a Rails app
|
112
|
+
#
|
113
|
+
# By default, Lore::Model doesn't extend Rails interface bridges. You
|
114
|
+
# either can define your own Model base class (see: How to disable/enable
|
115
|
+
# features) and extend it by Lore::Rails::Model
|
116
|
+
#
|
117
|
+
# class My_Model < Lore::Model
|
118
|
+
# extend Lore::Rails::Model
|
119
|
+
# end
|
120
|
+
#
|
121
|
+
# ... or extend Lore::Model directly:
|
122
|
+
#
|
123
|
+
# Lore::Model.extend Lore::Rails_Bridge
|
124
|
+
#
|
125
|
+
# In this case, every Model in your app will include Rails interfaces.
|
126
|
+
#
|
127
|
+
class Model < Table_Accessor
|
128
|
+
extend Lore::Cache::Cacheable
|
129
|
+
extend Lore::Query_Shortcuts
|
130
|
+
extend Lore::Validation
|
131
|
+
extend Lore::Aspect
|
132
|
+
extend Lore::Migration
|
133
|
+
|
134
|
+
def by_id(pkey_id)
|
135
|
+
_by_id(pkey_id).first # Auto-defined in Lore::Table_Accessor.primary_key
|
136
|
+
end
|
137
|
+
end
|
138
|
+
|
139
|
+
end
|