ডেটাবেসে হ্যাশ সংরক্ষণ করতে রেলগুলি সিরিয়ালাইজ ব্যবহার করে


135

আমি আমার রেল অ্যাপ্লিকেশনটিতে প্রচুর চেষ্টা করে একটি হ্যাশ ম্যাপিং আইডি সংরক্ষণ করার চেষ্টা করছি। এই নতুন কলামটি স্থায়ী করতে আমার ডাটাবেসে স্থানান্তর:

class AddMultiWrongToUser < ActiveRecord::Migration
  def self.up
    add_column :users, :multi_wrong, :string
  end

  def self.down
    remove_column :users, :multi_wrong
  end
end

আমার মডেলটিতে আমি:

class User < ActiveRecord::Base 
 serialize :multi_wrong, Hash
end

তবে যখন আমি এটি করে পরীক্ষা করার জন্য রেলস কনসোল ব্যবহার করি:

user = User.create()
user.multi_wrong = {"test"=>"123"}
user.save

আউটপুট মিথ্যা। এখানে কি ভুল হচ্ছে?


4
রেকর্ডটি সংরক্ষণের চেষ্টা করার পরে ব্যবহারকারীর মধ্যে কিছু আছে?
মার্টিজন

1
ভবিষ্যতে, আপনি ব্যতিক্রম বাড়াতে এবং একটি ত্রুটি বার্তা প্রদর্শন করতে ঠুং ঠুং শব্দটি (সংরক্ষণ করুন!) ব্যবহার করতে পারেন।
লেশম্যান

সেরা উত্তর এখন একটি JSON কলাম স্ট্যাকওভারফ্লো.com
ব্লেয়ার অ্যান্ডারসন

উত্তর:


174

কলামের ধরণটি ভুল। আপনার স্ট্রিংয়ের পরিবর্তে পাঠ্য ব্যবহার করা উচিত। সুতরাং, আপনার মাইগ্রেশনটি হওয়া উচিত:

 def self.up
   add_column :users, :multi_wrong, :text
 end

তারপরে রেলগুলি আপনার জন্য এটি যথাযথভাবে YAML এ রূপান্তর করবে (এবং সঠিক সিরিয়ালাইজেশন করবে)। স্ট্রিংস ক্ষেত্রগুলি আকারে সীমাবদ্ধ এবং কেবলমাত্র বিশেষত-ছোট মানগুলি ধারণ করবে।


1
@ বেনজামিটান এর পেছনের কারণ কী, আমি কেন 'স্ট্রিং' ডেটা টাইপে হ্যাশ সংরক্ষণ করতে পারি না।
লোহিথ এমভি

8
কারণ ডাটাবেসে স্ট্রিংয়ের নির্দিষ্ট দৈর্ঘ্য 255 থাকে (আমার মনে হয়)। আপনি যদি তুলনামূলক আকারের একটি হ্যাশকে সিরিয়ালাইজ করতে থাকেন তবে এটি সহজেই দৈর্ঘ্য ছাড়িয়ে যাবে। অ্যারে একই ক্ষেত্রে। পাঠ্যটি অনেক বড় দৈর্ঘ্যের অনুমতি দেয়।
বেনিয়ামিন তান ওয়েই হাও

72

আপডেট:

নির্ভুল বাস্তবায়ন আপনার ডাটাবেসের উপর নির্ভর করবে, তবে পোস্টগ্রিএসকিউএল এখন রয়েছে jsonএবং jsonbকলামগুলি রয়েছে যা আপনার হ্যাশ / অবজেক্ট ডেটা স্থানীয়ভাবে সঞ্চয় করতে পারে এবং আপনাকে অ্যাক্টিভেকর্ডের সাথে জেএসএনের বিরুদ্ধে জিজ্ঞাসা করার অনুমতি দেয় !

আপনার স্থানান্তর পরিবর্তন করুন এবং আপনি সম্পন্ন করেছেন।

class Migration0001
  def change
    add_column :users, :location_data, :json, default: {}
  end
end

মূল:

বিস্তারিত জানতে দেখুন: পাগল ডক্স && apidock

আপনার কলামটি কিনা :textতা নিশ্চিত করুন:string

মাইগ্রেশন:

$ rails g migration add_location_data_to_users location_data:text

তৈরি করা উচিত:

class Migration0001
  def change
    add_column :users, :location_data, :text
  end
end

আপনার ক্লাসটি দেখতে পছন্দ করবে:

class User < ActiveRecord::Base
  serialize :location_data
end

উপলব্ধ ক্রিয়া:

b = User.new
b.location_data = [1,2,{foot: 3, bart: "noodles"}]
b.save

আরও দুর্দান্ত ?!

postgresql hstore ব্যবহার করুন

class AddHstore < ActiveRecord::Migration  
  def up
    enable_extension :hstore
  end

  def down
    disable_extension :hstore
  end
end 

class Migration0001
  def change
    add_column :users, :location_data, :hstore
  end
end

Hstore এর সাহায্যে আপনি ক্রমিক ক্ষেত্রের বৈশিষ্ট্যগুলি সেট করতে পারেন

class User < ActiveRecord::Base  
  # setup hstore
  store_accessor :location_data, :city, :state
end

2
সত্যিই দুর্দান্ত! ধন্যবাদ!
আলেকজান্ডার গর্গ

18

4 রেলগুলিতে স্টোর নামে একটি নতুন বৈশিষ্ট্য রয়েছে , যাতে আপনি সহজেই আপনার সমস্যা সমাধানের জন্য এটি ব্যবহার করতে পারেন। আপনি এটির জন্য একটি অ্যাক্সেসর সংজ্ঞায়িত করতে পারেন এবং এটি প্রস্তাবিত হয় যে আপনি সিরিয়ালযুক্ত স্টোরের জন্য ব্যবহৃত ডাটাবেস কলামটি একটি পাঠ্য হিসাবে ঘোষণা করবেন, যাতে প্রচুর জায়গা রয়েছে। আসল উদাহরণ:

class User < ActiveRecord::Base
  store :settings, accessors: [ :color, :homepage ], coder: JSON
end

u = User.new(color: 'black', homepage: '37signals.com')
u.color                          # Accessor stored attribute
u.settings[:country] = 'Denmark' # Any attribute, even if not specified with an accessor

# There is no difference between strings and symbols for accessing custom attributes
u.settings[:country]  # => 'Denmark'
u.settings['country'] # => 'Denmark'
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.