Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

ActiveRecord serialize sending nil to custom serializer for present attribute

I have the following custom serializer:

class ReportCardDataSerializer
  def self.dump(hash)
    hash.to_json
  end

  def self.load(json)
    # json.class == NilClass, why????
    hash = (json || {}).with_indifferent_access
  end
end

And the following class with a serialized data attribute with database column set to NOT NULL.

class ReportCardGroup < ActiveRecord::Base
  serialize :data, ReportCardDataSerializer # data is PostgreSQL jsonb column
end

The ReportCardDataSerializer dump method works as expected. But on trying to load ReportCardDataSerializer load method gets sent nil even though the database column is not nil.

Why is this happening?

like image 707
Favourite Onwuemene Avatar asked Oct 28 '25 17:10

Favourite Onwuemene


1 Answers

I figured it out by going through the ActiveRecord serialization class.

ActiveRecord serializer calls type_cast_from_database:

def type_cast_from_database(value)
    if default_value?(value)
      value
    else
      coder.load(super)
    end
end

def default_value?(value)
    value == coder.load(nil) # HERE: Calls Serializer with nil
end

I assumed ReportCardDataSerializer would never have to process nil, but ActiveRecord actually first tries loading nil to test for the default value.

like image 152
Favourite Onwuemene Avatar answered Oct 31 '25 06:10

Favourite Onwuemene