<NoMethodError:#Record :: ActiveRecord_Relation的未定义方法`read_attribute_for_serialization':
我收到了错误:
<NoMethodError: undefined method `read_attribute_for_serialization' for #>
该错误位于代码段的第三行。
def artist @records = Record.where('artist_id = ' + params[:artist_id]) render :json => @records, serializer: RecordSummarySerializer end
这是控制器RecordsContrller的备用序列化程序。 另一个,’RecordsSerializer,工作正常。
搜索此错误会带来一些解决方案。 有些人不清楚添加代码的位置。 另一位建议补充:
alias :read_attribute_for_serialization :send
到发生错误的类。 它对我不起作用。 我还查看了gem文档。 我找到了使用序列化器的一个例子: 很明显,任何其他代码都是必需的。
我正在使用Ruby 2.3.0和Rails 5.0.0。
调节器
class RecordsController @records end def artist @records = Record.where('artist_id = ' + params[:artist_id]) render :json => @records, serializer: RecordSummarySerializer end ... end
模型
class Record < ActiveRecord::Base belongs_to :artist belongs_to :label belongs_to :style has_many :tracks has_many :credits validates :title, presence: true validates :catalog, presence: true end
record_summary_serializer.rb
include ActiveModel::Serialization class RecordSummarySerializer < ActiveModel::Serializer attributes :id, :artist_id, :label_id, :style_id, :title, :catalog, :recording_date, :penguin, :category end
record_serializer.rb
class RecordSerializer < ActiveModel::Serializer attributes :id, :artist_id, :label_id, :style_id, :title, :catalog, :alternate_catalog, :recording_date, :notes, :penguin, :category has_one :artist has_many :tracks end
记录模式
create_table "records", unsigned: true, force: :cascade, options: "ENGINE=InnoDB DEFAULT CHARSET=utf8" do |t| t.string "title", limit: 50 t.string "catalog", limit: 20, null: false t.string "alternate_catalog", limit: 20 t.integer "artist_id", unsigned: true t.integer "label_id", null: false, unsigned: true t.integer "style_id", unsigned: true t.datetime "recording_date" t.text "notes", limit: 4294967295 t.string "penguin", limit: 50 t.string "category", limit: 50, default: "jazz" t.index ["artist_id"], name: "RecordHasOneArtist", using: :btree t.index ["label_id"], name: "RecordHasOneLabel", using: :btree t.index ["style_id"], name: "RecordHasOneStyle", using: :btree end
我刚注意到,主键id不会出现在架构中。 当我查看表结构时,我在Sequel Pro中看到它。
更新
我添加了@JMazzy建议的代码。 我现在得到错误:
<NoMethodError: undefined method `id' for #\nDid you mean? ids>
我有同样的错误,发现更改serializer:
到each_serializer:
在控制器中解决了问题。
调节器
class RecordsController < ApplicationController ... def artist @records = Record.where('artist_id = ' + params[:artist_id]) render :json => @records, each_serializer: RecordSummarySerializer end ... end
record_summary_serializer.rb – 可以删除包含行
class RecordSummarySerializer < ActiveModel::Serializer attributes :id, :artist_id, :label_id, :style_id, :title, :catalog, :recording_date, :penguin, :category end
来自active_model_serializers 文档 。
更新了链接。 谢谢洛瑞德
您需要在模型中添加include ActiveModel::Serialization
。 ActiveModel中默认不包括扩展序列化。 在GitHub上看到这个答案 。
当序列化的对象nil
时,可能会发生此错误。 考虑打印调试您正在序列化的对象以检查它是否nil
:
def show product = Product.find_by(id: params[:id]) p "Is product nil? #{product.nil?}" render json: product end
如果对象(上面代码段中的product
)为nil
,那么由于调用了NoMethodError
,您可能会看到NoMethodError
报告的nil.read_attribute_for_serialization
。
我通过将自定义序列化程序更改为RecordDetailSerializer并从控制器中的show方法调用它来解决我的问题。 当我删除包含@JMazzy建议它仍然有效。 还有些东西搞砸了。 如果我在索引方法中使用自定义方法:
def index @records = Record.order('title') render :json => @records, serializer: RecordDetailSerializer end
我收到上面问题底部显示的缺失ID的错误。 但是,当我在show方法中使用它时:
def show @record = Record.find(params[:id]) render :json => @record, serializer: RecordDetailSerializer end
如果我删除问题字段,列表中的下一个字段将成为问题。 这对我来说不再是问题,因为我总是可以将自定义序列化程序限制为单个元素。
- Rails 3.2,保存序列化哈希不会保存number_with_delimiter()
- ActiveModel Serializers:has_many在运行时有条件吗?
- 使用active_model_serializers序列化深层嵌套关联
- 在Rails中使用ActiveModel :: Serializer – JSON数据在json和index响应之间有所不同
- 活动模型序列化器和自定义JSON结构
- 如何通过Rails的Active模型序列化器呈现嵌套对象的父数据?
- 强制活动模型序列化程序返回关联
- 使用active_model_serializers实现API版本控制的正确方法
- 具有嵌入式ID和侧载的Ember-Data和Active Model Serializer的has_many配置