diff options
author | Josh Goodall <joshua@qutonic.com> | 2013-07-15 11:55:24 +1000 |
---|---|---|
committer | Genadi Samokovarov <gsamokovarov@gmail.com> | 2014-02-17 00:40:16 +0200 |
commit | da3fec2ea3a6a13635500a667c105280c5357c14 (patch) | |
tree | ce2bea6364532c0c7126a8c39bb67af219abe68e /activerecord/lib/active_record | |
parent | 3e3ed1ede51f4d2f7f1d30b3754072b1121d5394 (diff) | |
download | rails-da3fec2ea3a6a13635500a667c105280c5357c14.tar.gz rails-da3fec2ea3a6a13635500a667c105280c5357c14.tar.bz2 rails-da3fec2ea3a6a13635500a667c105280c5357c14.zip |
Resolve encoding issues with arrays of hstore (bug 11135).
We didn't have enough encoding for the wire protocol to store an array
of hstore types. So, further encode any hstore that is an array member.
Whilst we're here, ensure it's an HashWithIndifferentAccess being
returned, to be consistent with other serialized forms, and add testing
for arrays of hstore.
So now the following migration:
enable_extension "hstore"
create_table :servers do |t|
t.string :name
t.hstore :interfaces, array: true
end
produces a model that can used like this, to store an array of hashes:
server = Server.create(name: "server01", interfaces: [
{ name: "bge0", ipv4: "192.0.2.2", state: "up" },
{ name: "de0", state: "disabled", by: "misha" },
{ name: "fe0", state: "up" },
])
More at http://inopinatus.org/2013/07/12/using-arrays-of-hstore-with-rails-4/
Diffstat (limited to 'activerecord/lib/active_record')
-rw-r--r-- | activerecord/lib/active_record/connection_adapters/postgresql/cast.rb | 12 | ||||
-rw-r--r-- | activerecord/lib/active_record/connection_adapters/postgresql/quoting.rb | 2 |
2 files changed, 7 insertions, 7 deletions
diff --git a/activerecord/lib/active_record/connection_adapters/postgresql/cast.rb b/activerecord/lib/active_record/connection_adapters/postgresql/cast.rb index 35ce881302..3a3b500b1f 100644 --- a/activerecord/lib/active_record/connection_adapters/postgresql/cast.rb +++ b/activerecord/lib/active_record/connection_adapters/postgresql/cast.rb @@ -35,11 +35,11 @@ module ActiveRecord end end - def hstore_to_string(object) + def hstore_to_string(object, array_member = false) if Hash === object - object.map { |k,v| - "#{escape_hstore(k)}=>#{escape_hstore(v)}" - }.join ',' + string = object.map { |k, v| "#{escape_hstore(k)}=>#{escape_hstore(v)}" }.join(',') + string = escape_hstore(string) if array_member + string else object end @@ -49,10 +49,10 @@ module ActiveRecord if string.nil? nil elsif String === string - Hash[string.scan(HstorePair).map { |k,v| + Hash[string.scan(HstorePair).map { |k, v| v = v.upcase == 'NULL' ? nil : v.gsub(/\A"(.*)"\Z/m,'\1').gsub(/\\(.)/, '\1') k = k.gsub(/\A"(.*)"\Z/m,'\1').gsub(/\\(.)/, '\1') - [k,v] + [k, v] }] else string diff --git a/activerecord/lib/active_record/connection_adapters/postgresql/quoting.rb b/activerecord/lib/active_record/connection_adapters/postgresql/quoting.rb index c1f978a081..210172cf32 100644 --- a/activerecord/lib/active_record/connection_adapters/postgresql/quoting.rb +++ b/activerecord/lib/active_record/connection_adapters/postgresql/quoting.rb @@ -121,7 +121,7 @@ module ActiveRecord end when Hash case column.sql_type - when 'hstore' then PostgreSQLColumn.hstore_to_string(value) + when 'hstore' then PostgreSQLColumn.hstore_to_string(value, array_member) when 'json' then PostgreSQLColumn.json_to_string(value) else super(value, column) end |