Permalink
Browse files

Merge pull request #15307 from sgrif/sg-type-cast-for-write

Add an interface for type objects to control Ruby => SQL
  • Loading branch information...
2 parents 7a2b37f + b5c4ef2 commit d075c84320fab51992a1ab7d020c62ff1bad0b4e @senny senny committed May 26, 2014
@@ -65,6 +65,8 @@ def serialize(attr_name, class_name_or_coder = Object)
end
class Type # :nodoc:
+ delegate :type, :type_cast_for_database, to: :@column
+
def initialize(column)
@column = column
end
@@ -77,10 +79,6 @@ def type_cast(value)
end
end
- def type
- @column.type
- end
-
def accessor
ActiveRecord::Store::IndifferentHashAccessor
end
@@ -2,6 +2,8 @@ module ActiveRecord
module AttributeMethods
module TimeZoneConversion
class Type # :nodoc:
+ delegate :type, :type_cast_for_database, to: :@column
+
def initialize(column)
@column = column
end
@@ -10,10 +12,6 @@ def type_cast(value)
value = @column.type_cast(value)
value.acts_like?(:time) ? value.in_time_zone : value
end
-
- def type
- @column.type
- end
end
extend ActiveSupport::Concern
@@ -47,6 +47,15 @@ def type_cast(value, column)
return value.id
end
+ # FIXME: The only case we get an object other than nil or a real column
+ # is `SchemaStatements#add_column` with a PG array that has a non-empty default
+ # value. Is this really the only case? Are we missing tests for other types?
+ # We should have a real column object passed (or nil) here, and check for that
+ # instead
+ if column.respond_to?(:type_cast_for_database)
+ value = column.type_cast_for_database(value)
+ end
+
case value
when String, ActiveSupport::Multibyte::Chars
value = value.to_s
@@ -18,7 +18,8 @@ module Format
alias :encoded? :coder
- delegate :type, :precision, :scale, :limit, :klass, :text?, :number?, :binary?, :type_cast_for_write, to: :cast_type
+ delegate :type, :precision, :scale, :limit, :klass, :text?, :number?, :binary?,
+ :type_cast_for_write, :type_cast_for_database, to: :cast_type
# Instantiates a new column in the table.
#
@@ -21,6 +21,10 @@ def type_cast_for_write(value)
value
end
+ def type_cast_for_database(value)
+ type_cast_for_write(value)
+ end
+
def text?
false
end
@@ -122,7 +122,6 @@ def test_composite_mapping
assert_equal "Champs-Élysées", composite.address.street
composite.address = FullAddress.new("Paris", "Rue Basse")
- skip "Saving with custom OID type is currently not supported."
composite.save!
assert_equal 'Paris', composite.reload.address.city

0 comments on commit d075c84

Please sign in to comment.