datamapper 0.1.1 → 0.2.0

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.
Files changed (131) hide show
  1. data/CHANGELOG +65 -0
  2. data/README +193 -1
  3. data/do_performance.rb +153 -0
  4. data/environment.rb +45 -0
  5. data/example.rb +119 -22
  6. data/lib/data_mapper.rb +36 -16
  7. data/lib/data_mapper/adapters/abstract_adapter.rb +8 -0
  8. data/lib/data_mapper/adapters/data_object_adapter.rb +360 -0
  9. data/lib/data_mapper/adapters/mysql_adapter.rb +30 -179
  10. data/lib/data_mapper/adapters/postgresql_adapter.rb +90 -199
  11. data/lib/data_mapper/adapters/sql/coersion.rb +32 -3
  12. data/lib/data_mapper/adapters/sql/commands/conditions.rb +97 -128
  13. data/lib/data_mapper/adapters/sql/commands/load_command.rb +234 -231
  14. data/lib/data_mapper/adapters/sql/commands/loader.rb +99 -0
  15. data/lib/data_mapper/adapters/sql/mappings/associations_set.rb +30 -0
  16. data/lib/data_mapper/adapters/sql/mappings/column.rb +68 -6
  17. data/lib/data_mapper/adapters/sql/mappings/schema.rb +6 -3
  18. data/lib/data_mapper/adapters/sql/mappings/table.rb +71 -42
  19. data/lib/data_mapper/adapters/sql/quoting.rb +8 -2
  20. data/lib/data_mapper/adapters/sqlite3_adapter.rb +32 -201
  21. data/lib/data_mapper/associations.rb +21 -7
  22. data/lib/data_mapper/associations/belongs_to_association.rb +96 -80
  23. data/lib/data_mapper/associations/has_and_belongs_to_many_association.rb +158 -67
  24. data/lib/data_mapper/associations/has_many_association.rb +96 -78
  25. data/lib/data_mapper/associations/has_n_association.rb +64 -0
  26. data/lib/data_mapper/associations/has_one_association.rb +49 -79
  27. data/lib/data_mapper/associations/reference.rb +47 -0
  28. data/lib/data_mapper/base.rb +216 -50
  29. data/lib/data_mapper/callbacks.rb +71 -24
  30. data/lib/data_mapper/{session.rb → context.rb} +20 -8
  31. data/lib/data_mapper/database.rb +176 -45
  32. data/lib/data_mapper/embedded_value.rb +65 -0
  33. data/lib/data_mapper/identity_map.rb +12 -4
  34. data/lib/data_mapper/support/active_record_impersonation.rb +12 -8
  35. data/lib/data_mapper/support/enumerable.rb +8 -0
  36. data/lib/data_mapper/support/serialization.rb +13 -0
  37. data/lib/data_mapper/support/string.rb +1 -12
  38. data/lib/data_mapper/support/symbol.rb +3 -0
  39. data/lib/data_mapper/validations/unique_validator.rb +1 -2
  40. data/lib/data_mapper/validations/validation_helper.rb +18 -1
  41. data/performance.rb +109 -34
  42. data/plugins/can_has_sphinx/LICENSE +23 -0
  43. data/plugins/can_has_sphinx/README +4 -0
  44. data/plugins/can_has_sphinx/REVISION +1 -0
  45. data/plugins/can_has_sphinx/Rakefile +22 -0
  46. data/plugins/can_has_sphinx/init.rb +1 -0
  47. data/plugins/can_has_sphinx/install.rb +1 -0
  48. data/plugins/can_has_sphinx/lib/acts_as_sphinx.rb +123 -0
  49. data/plugins/can_has_sphinx/lib/sphinx.rb +460 -0
  50. data/plugins/can_has_sphinx/scripts/sphinx.sh +47 -0
  51. data/plugins/can_has_sphinx/tasks/acts_as_sphinx_tasks.rake +41 -0
  52. data/plugins/dataobjects/REVISION +1 -0
  53. data/plugins/dataobjects/Rakefile +7 -0
  54. data/plugins/dataobjects/do.rb +246 -0
  55. data/plugins/dataobjects/do_mysql.rb +179 -0
  56. data/plugins/dataobjects/do_postgres.rb +181 -0
  57. data/plugins/dataobjects/do_sqlite3.rb +153 -0
  58. data/plugins/dataobjects/spec/do_spec.rb +150 -0
  59. data/plugins/dataobjects/spec/spec_helper.rb +81 -0
  60. data/plugins/dataobjects/swig_mysql/do_mysql.bundle +0 -0
  61. data/plugins/dataobjects/swig_mysql/extconf.rb +33 -0
  62. data/plugins/dataobjects/swig_mysql/mysql_c.c +18800 -0
  63. data/plugins/dataobjects/swig_mysql/mysql_c.i +8 -0
  64. data/plugins/dataobjects/swig_mysql/mysql_supp.i +46 -0
  65. data/plugins/dataobjects/swig_postgres/Makefile +146 -0
  66. data/plugins/dataobjects/swig_postgres/extconf.rb +29 -0
  67. data/plugins/dataobjects/swig_postgres/postgres_c.bundle +0 -0
  68. data/plugins/dataobjects/swig_postgres/postgres_c.c +8185 -0
  69. data/plugins/dataobjects/swig_postgres/postgres_c.i +73 -0
  70. data/plugins/dataobjects/swig_sqlite/db +0 -0
  71. data/plugins/dataobjects/swig_sqlite/extconf.rb +9 -0
  72. data/plugins/dataobjects/swig_sqlite/sqlite3_c.c +4725 -0
  73. data/plugins/dataobjects/swig_sqlite/sqlite_c.i +168 -0
  74. data/rakefile.rb +45 -23
  75. data/spec/acts_as_tree_spec.rb +39 -0
  76. data/spec/associations_spec.rb +220 -0
  77. data/spec/attributes_spec.rb +15 -0
  78. data/spec/base_spec.rb +44 -0
  79. data/spec/callbacks_spec.rb +45 -0
  80. data/spec/can_has_sphinx.rb +6 -0
  81. data/spec/coersion_spec.rb +34 -0
  82. data/spec/conditions_spec.rb +49 -0
  83. data/spec/conversions_to_yaml_spec.rb +17 -0
  84. data/spec/count_command_spec.rb +11 -0
  85. data/spec/delete_command_spec.rb +1 -1
  86. data/spec/embedded_value_spec.rb +23 -0
  87. data/spec/fixtures/animals_exhibits.yaml +2 -0
  88. data/spec/fixtures/people.yaml +18 -1
  89. data/spec/{legacy.rb → legacy_spec.rb} +3 -3
  90. data/spec/load_command_spec.rb +157 -20
  91. data/spec/magic_columns_spec.rb +9 -0
  92. data/spec/mock_adapter.rb +20 -0
  93. data/spec/models/animal.rb +1 -1
  94. data/spec/models/animals_exhibit.rb +6 -0
  95. data/spec/models/exhibit.rb +2 -0
  96. data/spec/models/person.rb +26 -1
  97. data/spec/models/project.rb +19 -0
  98. data/spec/models/sales_person.rb +1 -0
  99. data/spec/models/section.rb +6 -0
  100. data/spec/models/zoo.rb +3 -1
  101. data/spec/query_spec.rb +9 -0
  102. data/spec/save_command_spec.rb +65 -1
  103. data/spec/schema_spec.rb +89 -0
  104. data/spec/single_table_inheritance_spec.rb +27 -0
  105. data/spec/spec_helper.rb +9 -55
  106. data/spec/{symbolic_operators.rb → symbolic_operators_spec.rb} +9 -5
  107. data/spec/{validates_confirmation_of.rb → validates_confirmation_of_spec.rb} +4 -3
  108. data/spec/{validates_format_of.rb → validates_format_of_spec.rb} +5 -4
  109. data/spec/{validates_length_of.rb → validates_length_of_spec.rb} +8 -7
  110. data/spec/{validates_uniqueness_of.rb → validates_uniqueness_of_spec.rb} +7 -10
  111. data/spec/{validations.rb → validations_spec.rb} +24 -6
  112. data/tasks/drivers.rb +20 -0
  113. data/tasks/fixtures.rb +42 -0
  114. metadata +181 -42
  115. data/lib/data_mapper/adapters/sql/commands/advanced_load_command.rb +0 -140
  116. data/lib/data_mapper/adapters/sql/commands/delete_command.rb +0 -113
  117. data/lib/data_mapper/adapters/sql/commands/save_command.rb +0 -141
  118. data/lib/data_mapper/adapters/sql/commands/table_exists_command.rb +0 -33
  119. data/lib/data_mapper/adapters/sql_adapter.rb +0 -163
  120. data/lib/data_mapper/associations/advanced_has_many_association.rb +0 -55
  121. data/lib/data_mapper/support/blank_slate.rb +0 -3
  122. data/lib/data_mapper/support/proc.rb +0 -69
  123. data/lib/data_mapper/support/struct.rb +0 -26
  124. data/lib/data_mapper/unit_of_work.rb +0 -38
  125. data/spec/basic_finder.rb +0 -67
  126. data/spec/belongs_to.rb +0 -47
  127. data/spec/has_and_belongs_to_many.rb +0 -25
  128. data/spec/has_many.rb +0 -34
  129. data/spec/new_record.rb +0 -24
  130. data/spec/sub_select.rb +0 -16
  131. data/spec/support/string_spec.rb +0 -7
@@ -1,194 +1,45 @@
1
- require 'data_mapper/adapters/sql_adapter'
2
- require 'data_mapper/support/connection_pool'
3
-
1
+ require 'data_mapper/adapters/data_object_adapter'
4
2
  begin
5
- require 'mysql'
6
- rescue LoadError
7
- STDERR.puts <<-EOS.gsub(/^(\s+)/, '')
8
- This adapter currently depends on the \"mysql\" gem.
9
- If some kind soul would like to make it work with
10
- a pure-ruby version that'd be super spiffy.
11
- EOS
12
-
13
- raise
3
+ require 'do_mysql'
4
+ rescue
5
+ STDERR.puts <<-EOS
6
+ You must install the DataObjects::Mysql driver.
7
+ rake dm:install:mysql
8
+ EOS
9
+ exit
14
10
  end
15
11
 
16
12
  module DataMapper
17
13
  module Adapters
18
14
 
19
- class MysqlAdapter < SqlAdapter
20
-
21
- def initialize(configuration)
22
- super
23
-
24
- create_connection = lambda do
25
- Mysql.new(configuration.host, configuration.username, configuration.password, configuration.database)
26
- end
27
-
28
- # Initialize the connection pool.
29
- if single_threaded?
30
- @connection_factory = create_connection
31
- @active_connection = create_connection[]
32
- else
33
- @connections = Support::ConnectionPool.new(&create_connection)
34
- end
35
- end
36
-
37
- # Yields an available connection. Flushes the connection-pool if
38
- # the connection returns an error.
39
- def connection
40
-
41
- if single_threaded?
42
- begin
43
- # BUG: Single_threaded mode totally breaks shit right now. No real idea why just from
44
- # eyeballing this. Probably should move this into the SqlAdapter anyways and just
45
- # force derived adapters to implement a #create_connection() and #close_connection(conn) methods.
46
- yield(@active_connection)
47
- rescue Mysql::Error => me
48
- @configuration.log.fatal(me)
49
-
50
- begin
51
- @active_connection.close
52
- rescue => se
53
- @configuration.log.error(se)
54
- end
55
-
56
- @active_connection = @connection_factory[]
57
- end
58
- else
59
- begin
60
- @connections.hold { |dbh| yield(dbh) }
61
- rescue Mysql::Error => me
62
-
63
- @configuration.log.fatal(me)
64
-
65
- @connections.available_connections.each do |sock|
66
- begin
67
- sock.close
68
- rescue => se
69
- @configuration.log.error(se)
70
- end
71
- end
72
-
73
- @connections.available_connections.clear
74
- raise me
75
- end
76
- end
77
- end
78
-
79
- def execute(*args)
80
- connection do |db|
81
- reader = db.query(escape_sql(*args))
82
- result = yield(reader, reader.fetch_fields.map { |field| field.name })
83
- reader.free
84
- result
85
- end
86
- end
87
-
88
- def query(*args)
89
-
90
- execute(*args) do |reader, fields|
91
- struct = Support::Struct::define(fields)
92
-
93
- results = []
94
-
95
- reader.each do |row|
96
- results << struct.new(row)
97
- end
98
- results
99
-
100
- end
15
+ class MysqlAdapter < DataObjectAdapter
16
+ def create_connection
17
+
18
+ connection_string = ""
19
+ builder = lambda { |k,v| connection_string << "#{k}=#{@configuration.send(v)} " unless @configuration.send(v).blank? }
20
+
21
+ builder['host', :host]
22
+ builder['user', :username]
23
+ builder['password', :password]
24
+ builder['dbname', :database]
25
+ builder['socket', :socket]
26
+
27
+ conn = DataObject::Mysql::Connection.new(connection_string.strip)
28
+ conn.open
29
+ cmd = conn.create_command("SET NAMES UTF8")
30
+ cmd.execute_non_query
31
+ return conn
101
32
  end
102
33
 
103
- TABLE_QUOTING_CHARACTER = '`'.freeze
104
- COLUMN_QUOTING_CHARACTER = '`'.freeze
105
-
106
- TRUE_ALIASES.unshift('1'.freeze)
107
- FALSE_ALIASES.unshift('0'.freeze)
108
-
109
- module Commands
110
-
111
- class TableExistsCommand
112
- def call
113
- sql = to_sql
114
- @adapter.log.debug(sql)
115
- reader = @adapter.connection { |db| db.query(sql) }
116
- result = reader.num_rows > 0
117
- reader.free
118
- result
119
- end
120
- end
121
-
122
- class DeleteCommand
123
-
124
- def execute(sql)
125
- @adapter.connection do |db|
126
- @adapter.log.debug(sql)
127
- db.query(sql)
128
- db.affected_rows > 0
129
- end
130
- end
131
-
132
- def execute_drop(sql)
133
- @adapter.log.debug(sql)
134
- @adapter.connection { |db| db.query(sql) }
135
- true
136
- end
137
-
138
- end
139
-
140
- class SaveCommand
141
-
142
- def execute_insert(sql)
143
- @adapter.connection do |db|
144
- @adapter.log.debug(sql)
145
- db.query(sql)
146
- db.insert_id
147
- end
148
- end
149
-
150
- def execute_update(sql)
151
- @adapter.connection do |db|
152
- @adapter.log.debug(sql)
153
- db.query(sql)
154
- db.affected_rows > 0
155
- end
156
- end
157
-
158
- def execute_create_table(sql)
159
- @adapter.log.debug(sql)
160
- @adapter.connection { |db| db.query(sql) }
161
- true
162
- end
163
-
164
- end
34
+ module Mappings
165
35
 
166
- class LoadCommand
167
- def eof?(reader)
168
- reader.num_rows == 0
169
- end
170
-
171
- def close_reader(reader)
172
- reader.free
36
+ def to_create_table_sql
37
+ @to_create_table_sql || @to_create_table_sql = begin
38
+ "CREATE TABLE #{to_sql} (#{columns.map { |c| c.to_long_form }.join(', ')}) Type=MyISAM CHARACTER SET utf8"
173
39
  end
174
-
175
- def execute(sql)
176
- @adapter.log.debug(sql)
177
- @adapter.connection { |db| db.query(to_sql) }
178
- end
179
-
180
- def fetch_one(reader)
181
- fetch_all(reader).first
182
- end
183
-
184
- def fetch_all(reader)
185
- load_instances(reader.fetch_fields.map { |field| field.name }, reader)
186
- end
187
-
188
40
  end
189
41
 
190
- end
191
-
42
+ end # module Mappings
192
43
  end # class MysqlAdapter
193
44
 
194
45
  end # module Adapters
@@ -1,242 +1,133 @@
1
- require 'data_mapper/adapters/sql_adapter'
2
- require 'data_mapper/support/connection_pool'
3
-
1
+ require 'data_mapper/adapters/data_object_adapter'
4
2
  begin
5
- require 'postgres'
6
- rescue LoadError
7
- STDERR.puts <<-EOS.gsub(/^(\s+)/, '')
8
- This adapter currently depends on the \"postgres\" gem.
9
- If some kind soul would like to make it work with
10
- a pure-ruby version that'd be super spiffy.
11
- EOS
12
-
13
- raise
3
+ require 'do_postgres'
4
+ rescue
5
+ STDERR.puts <<-EOS
6
+ You must install the DataObjects::PostgreSQL driver.
7
+ rake dm:install:postgresql
8
+ EOS
9
+ exit
14
10
  end
15
11
 
16
12
  module DataMapper
17
13
  module Adapters
18
14
 
19
- class PostgresqlAdapter < SqlAdapter
15
+ class PostgresqlAdapter < DataObjectAdapter
20
16
 
21
- def initialize(configuration)
22
- super
23
- # Initialize the connection pool.
24
- @connections = Support::ConnectionPool.new do
25
- # add port parameter to configuration
26
- pg_conn = PGconn.connect(configuration.host, 5432, "", "", configuration.database, configuration.username, configuration.password)
27
- end
28
- end
29
-
30
-
31
- # Returns an available connection. Flushes the connection-pool if
32
- # the connection returns an error.
33
- def connection
34
- raise ArgumentError.new('PostgresqlAdapter#connection requires a block-parameter') unless block_given?
35
- begin
36
- @connections.hold { |connection| yield connection }
37
- rescue PGError => me
38
-
39
- @configuration.log.fatal(me)
40
-
41
- @connections.available_connections.each do |sock|
42
- begin
43
- sock.close
44
- rescue => se
45
- @configuration.log.error(se)
46
- end
17
+ def schema_search_path
18
+ @schema_search_path || @schema_search_path = begin
19
+ if @configuration.schema_search_path
20
+ @configuration.schema_search_path.split(',').map do |part|
21
+ part.blank? ? nil : part.strip.ensure_wrapped_with("'")
22
+ end.compact
23
+ else
24
+ []
47
25
  end
48
-
49
- @connections.available_connections.clear
50
- raise me
51
26
  end
52
27
  end
53
28
 
54
- def query(*args)
55
- pg_result = connection { |db| db.exec(escape_sql(*args)) }
56
-
57
- struct = Struct.new(*pg_result.fields.map { |field| Inflector.underscore(field).to_sym })
58
- results = []
59
-
60
- pg_result.each do |row|
61
- results << struct.new(*row)
29
+ def create_connection
30
+ conn = DataObject::Postgres::Connection.new("dbname=#{@configuration.database}")
31
+ conn.open
32
+ return conn
33
+
34
+ unless schema_search_path.empty?
35
+ execute("SET search_path TO #{schema_search_path}")
62
36
  end
63
37
 
64
- pg_result.clear
65
- return results
38
+ return connection
66
39
  end
67
-
40
+
68
41
  TABLE_QUOTING_CHARACTER = '"'.freeze
69
42
  COLUMN_QUOTING_CHARACTER = '"'.freeze
70
-
71
- def type_cast_boolean(value)
72
- case value
73
- when TrueClass, FalseClass then value
74
- when "t", "true", "TRUE" then true
75
- when "f", nil then false
76
- else "Can't type-cast #{value.inspect} to a boolean"
77
- end
78
- end
79
-
80
- def type_cast_datetime(value)
81
- case value
82
- when DateTime then value
83
- when Date then DateTime.new(value)
84
- when String then DateTime::parse(value)
85
- else "Can't type-cast #{value.inspect} to a datetime"
86
- end
87
- end
88
-
89
- def sequence_name(table)
90
- quote_table_name(table.to_sql.gsub('"', '') + "_id_seq")
91
- end
92
43
 
93
44
  TYPES.merge!({
94
45
  :integer => 'integer'.freeze,
95
- :string => 'varchar'.freeze,
96
- :text => 'text'.freeze,
97
- :class => 'varchar'.freeze,
98
46
  :datetime => 'timestamp with time zone'.freeze
99
47
  })
100
-
101
- module Commands
102
48
 
103
- class TableExistsCommand
104
- def to_sql
105
- # TODO cache this somewhere
106
- schema_list = @adapter.connection { |db| db.exec('SHOW search_path').result[0][0].split(',').collect { |s| "'#{s}'" }.join(',') }
107
- "SELECT tablename FROM pg_tables WHERE schemaname IN (#{schema_list}) AND tablename = #{table_name}"
49
+ module Mappings
50
+ class Table
51
+ def sequence_sql
52
+ @sequence_sql ||= quote_table("_id_seq").freeze
108
53
  end
109
54
 
110
- def call
111
- sql = to_sql
112
- @adapter.log.debug(sql)
113
- reader = @adapter.connection { |db| db.exec(sql) }
114
- result = reader.entries.size > 0
115
- reader.clear
116
- result
117
- end
118
- end
119
-
120
- class DeleteCommand
121
-
122
- def execute(sql)
123
- @adapter.connection do |db|
124
- @adapter.log.debug(sql)
125
- db.exec(sql).status == PGresult::COMMAND_OK
126
- end
127
- end
128
-
129
- def to_truncate_sql
130
- table = @adapter[@klass_or_instance]
131
- sequence = @adapter.sequence_name(table)
132
- # truncate the table and reset the sequence value
133
- "DELETE FROM " << table.to_sql << "; SELECT setval('#{sequence}', (SELECT COALESCE(MAX(id)+(SELECT increment_by FROM #{sequence}), (SELECT min_value FROM #{sequence})) FROM #{table.to_sql}), false)"
134
- end
135
-
136
- def execute_drop(sql)
137
- @adapter.log.debug(sql)
138
- @adapter.connection { |db| db.exec(sql) }
139
- true
140
- end
141
-
142
- end
143
-
144
- class SaveCommand
145
-
146
- def execute_insert(sql)
147
- @adapter.connection do |db|
148
- @adapter.log.debug(sql)
149
- db.exec(sql)
150
- # Current id or latest value read from sequence in this session
151
- # See: http://www.postgresql.org/docs/8.1/interactive/functions-sequence.html
152
- @instance.key || db.exec("SELECT last_value from #{@adapter.sequence_name(@adapter[@instance.class])}")[0][0]
153
- end
154
- end
55
+ def to_create_table_sql
56
+ schema_name = name.index('.') ? name.split('.').first : nil
57
+ schema_list = @adapter.query('SELECT nspname FROM pg_namespace').join(',')
155
58
 
156
- def execute_update(sql)
157
- @adapter.connection do |db|
158
- @adapter.log.debug(sql)
159
- db.exec(sql).cmdstatus.split(' ').last.to_i > 0
59
+ sql = if schema_name and !schema_list.include?(schema_name)
60
+ "CREATE SCHEMA #{@adapter.quote_table_name(schema_name)}; "
61
+ else
62
+ ''
160
63
  end
161
- end
162
-
163
- def execute_create_table(sql)
164
- @adapter.log.debug(sql)
165
- @adapter.connection { |db| db.exec(sql) }
166
- true
167
- end
64
+
65
+ sql << "CREATE TABLE " << to_sql
168
66
 
169
- def to_create_table_sql
170
- table = @adapter[@instance]
171
-
172
- sql = "CREATE TABLE " << table.to_sql
173
-
174
- sql << " (" << table.columns.map do |column|
175
- column_long_form(column)
67
+ sql << " (" << columns.map do |column|
68
+ column.to_long_form
176
69
  end.join(', ') << ")"
177
-
178
- return sql
179
- end
180
-
181
- def column_long_form(column)
182
-
183
- long_form = if column.key?
184
- "#{column.to_sql} serial primary key"
185
- else
186
- "#{column.to_sql} #{@adapter.class::TYPES[column.type] || column.type}"
187
- end
188
- long_form << " NOT NULL" unless column.nullable?
189
- long_form << " default #{column.options[:default]}" if column.options.has_key?(:default)
190
-
191
- return long_form
192
- end
193
- end
194
-
195
- class LoadCommand
196
- def eof?(pg_result)
197
- pg_result.result.entries.empty?
198
- end
199
70
 
200
- def close_reader(pg_result)
201
- pg_result.clear
71
+ return sql
202
72
  end
203
73
 
204
- def execute(sql)
205
- @adapter.log.debug(sql)
206
- @adapter.connection { |db| db.exec(to_sql) }
74
+ def to_exists_sql
75
+ @to_exists_sql || @to_exists_sql = <<-EOS.compress_lines
76
+ SELECT TABLE_NAME
77
+ FROM INFORMATION_SCHEMA.TABLES
78
+ WHERE TABLE_NAME = #{@adapter.quote_value(name)}
79
+ AND TABLE_CATALOG = #{@adapter.quote_value(@adapter.schema.name)}
80
+ EOS
207
81
  end
208
82
 
209
- def fetch_one(pg_result)
210
- load(process_row(columns(pg_result), pg_result.result[0]))
211
- end
83
+ private
212
84
 
213
- def fetch_all(pg_result)
214
- load_instances(pg_result.fields, pg_result)
85
+ def quote_table(table_suffix = nil)
86
+ parts = name.split('.')
87
+ parts.last << table_suffix if table_suffix
88
+ parts.map { |part|
89
+ @adapter.quote_table_name(part) }.join('.')
215
90
  end
91
+ end # class Table
92
+
93
+ class Column
94
+ def serial_declaration
95
+ "SERIAL"
96
+ end
97
+
98
+ def to_long_form
99
+ @to_long_form || begin
100
+ @to_long_form = "#{to_sql}"
101
+
102
+ if serial? && !serial_declaration.blank?
103
+ @to_long_form << " #{serial_declaration}"
104
+ else
105
+ @to_long_form << " #{type_declaration}"
106
+
107
+ unless nullable? || not_null_declaration.blank?
108
+ @to_long_form << " #{not_null_declaration}"
109
+ end
110
+
111
+ if key? && !primary_key_declaration.blank?
112
+ @to_long_form << " #{primary_key_declaration}"
113
+ end
216
114
 
217
- private
218
-
219
- def columns(pg_result)
220
- columns = {}
221
- pg_result.fields.each_with_index do |name, index|
222
- columns[name] = index
223
- end
224
- columns
225
- end
226
-
227
- def process_row(columns, row)
228
- hash = {}
229
- columns.each_pair do |name,index|
230
- hash[name] = row[index]
115
+ if default && !default_declaration.blank?
116
+ @to_long_form << " #{default_declaration}"
117
+ end
118
+ end
119
+
120
+ @to_long_form
231
121
  end
232
- hash
233
122
  end
234
123
 
235
- end
236
-
237
- end
124
+ def size
125
+ nil
126
+ end
127
+ end # class Column
128
+ end # module Mappings
238
129
 
239
130
  end # class PostgresqlAdapter
240
131
 
241
132
  end # module Adapters
242
- end # module DataMapper
133
+ end # module DataMapper