添加:multipart => true throws未定义方法“名称”错误
我在这个上画了一个空白。 这是我的问题:
精简版
我的image#create
image.save
动作在image.save
调用时失败,并Undefined method "name" for nil:NilClass
抛出Undefined method "name" for nil:NilClass
。 Image模型包括通过paperclip
gem上传的文件。
扔我的部分:
只有在提交表单中包含:multipart => true
时才会出现错误
当我把它拿出来时,表单完美无缺,当然图像文件没有上传。 有关失败位置的详细信息,请参阅下面的堆栈跟踪。 在尝试为INSERT语句引用某些内容时,它看起来像是一个零值,但我无法弄清楚是什么。 我的控制器参数看起来没问题,我通过记录器检查以确保新的Image
实例在它到达保存调用之前正确构建。
额外细节
我将尝试包括我能想到的所有细节,按重要性排序:
-
我正在使用paperclip并试图通过S3进行存储,尽管当我在我的Image模型中完全注释掉
has_attached_file
行时仍然会出现这个问题。 -
Image是Collection中的嵌套资源,在其
to_param
方法中由slug引用。 -
我有多租户系统的基础知识(也就是Basecamp风格的用户子域,通过中心用户模型实现,范围所有组件)。
传递给控制器的参数
{"utf8"=>"✓", "authenticity_token"=>"JYCMky7851j5cW4ChSWUCCL/02iePf6i/QWAgR8q5tE=", "image"=>{"name"=>"My testerific image 2", "slug"=>"my-testerific-image-2", "description"=>"w", "collection_id"=>"2", "sort"=>"3", "picture_file_name"=>#<ActionDispatch::Http::UploadedFile:0x00000101b3f540 @original_filename="David's pic 005.jpeg", @content_type="image/jpeg", @headers="Content-Disposition: form-data; name=\"image[picture_file_name]\"; filename=\"David's pic 005.jpeg\"\r\nContent-Type: image/jpeg\r\n", @tempfile=#>}, "commit"=>"Create Image", "collection_id"=>"my-new-collection"}
完整堆栈跟踪
activesupport (3.0.9) lib/active_support/whiny_nil.rb:48:in 'method_missing' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:20:in 'block in initialize' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:22:in 'yield' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:22:in 'default' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:22:in 'block in initialize' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:22:in 'yield' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:22:in 'default' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:22:in 'block in initialize' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:22:in 'yield' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:22:in 'default' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:22:in 'block in initialize' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:22:in 'yield' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:22:in 'default' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:22:in 'block in initialize' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:63:in 'yield' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:63:in 'default' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:63:in 'accept' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:325:in 'block in dump_ivars' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:323:in 'each' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:323:in 'dump_ivars' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:85:in 'visit_Object' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:63:in 'accept' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/visitors/yaml_tree.rb:36:in '<<' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych.rb:165:in 'dump' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/psych/core_ext.rb:13:in 'psych_to_yaml' activerecord (3.0.9) lib/active_record/connection_adapters/abstract/quoting.rb:34:in 'quote' activerecord (3.0.9) lib/active_record/connection_adapters/sqlite3_adapter.rb:45:in 'quote' arel (2.0.10) lib/arel/visitors/to_sql.rb:327:in 'quote' arel (2.0.10) lib/arel/visitors/to_sql.rb:70:in 'block in visit_Arel_Nodes_Values' arel (2.0.10) lib/arel/visitors/to_sql.rb:69:in 'map' arel (2.0.10) lib/arel/visitors/to_sql.rb:69:in 'visit_Arel_Nodes_Values' arel (2.0.10) lib/arel/visitors/visitor.rb:15:in 'visit' arel (2.0.10) lib/arel/visitors/to_sql.rb:59:in 'visit_Arel_Nodes_InsertStatement' arel (2.0.10) lib/arel/visitors/visitor.rb:15:in 'visit' arel (2.0.10) lib/arel/visitors/visitor.rb:5:in 'accept' arel (2.0.10) lib/arel/visitors/to_sql.rb:18:in 'block in accept' activerecord (3.0.9) lib/active_record/connection_adapters/abstract/connection_pool.rb:111:in 'with_connection' arel (2.0.10) lib/arel/visitors/to_sql.rb:16:in 'accept' arel (2.0.10) lib/arel/tree_manager.rb:20:in 'to_sql' arel (2.0.10) lib/arel/select_manager.rb:217:in 'insert' activerecord (3.0.9) lib/active_record/relation.rb:14:in 'insert' activerecord (3.0.9) lib/active_record/persistence.rb:274:in 'create' activerecord (3.0.9) lib/active_record/timestamp.rb:47:in 'create' activerecord (3.0.9) lib/active_record/callbacks.rb:277:in 'block in create' activesupport (3.0.9) lib/active_support/callbacks.rb:414:in '_run_create_callbacks' activerecord (3.0.9) lib/active_record/callbacks.rb:277:in 'create' activerecord (3.0.9) lib/active_record/persistence.rb:250:in 'create_or_update' activerecord (3.0.9) lib/active_record/callbacks.rb:273:in 'block in create_or_update' activesupport (3.0.9) lib/active_support/callbacks.rb:429:in '_run_save_callbacks' activerecord (3.0.9) lib/active_record/callbacks.rb:273:in 'create_or_update' activerecord (3.0.9) lib/active_record/persistence.rb:40:in 'save' activerecord (3.0.9) lib/active_record/validations.rb:43:in 'save' activerecord (3.0.9) lib/active_record/attribute_methods/dirty.rb:21:in 'save' activerecord (3.0.9) lib/active_record/transactions.rb:240:in 'block (2 levels) in save' activerecord (3.0.9) lib/active_record/transactions.rb:292:in 'block in with_transaction_returning_status' activerecord (3.0.9) lib/active_record/connection_adapters/abstract/database_statements.rb:139:in 'transaction' activerecord (3.0.9) lib/active_record/transactions.rb:207:in 'transaction' activerecord (3.0.9) lib/active_record/transactions.rb:290:in 'with_transaction_returning_status' activerecord (3.0.9) lib/active_record/transactions.rb:240:in 'block in save' activerecord (3.0.9) lib/active_record/transactions.rb:251:in 'rollback_active_record_state!' activerecord (3.0.9) lib/active_record/transactions.rb:239:in 'save' app/controllers/images_controller.rb:42:in 'block in create' actionpack (3.0.9) lib/action_controller/metal/mime_responds.rb:264:in 'call' actionpack (3.0.9) lib/action_controller/metal/mime_responds.rb:264:in 'retrieve_response_from_mimes' actionpack (3.0.9) lib/action_controller/metal/mime_responds.rb:191:in 'respond_to' app/controllers/images_controller.rb:40:in 'create' actionpack (3.0.9) lib/action_controller/metal/implicit_render.rb:4:in 'send_action' actionpack (3.0.9) lib/abstract_controller/base.rb:150:in 'process_action' actionpack (3.0.9) lib/action_controller/metal/rendering.rb:11:in 'process_action' actionpack (3.0.9) lib/abstract_controller/callbacks.rb:18:in 'block in process_action' activesupport (3.0.9) lib/active_support/callbacks.rb:451:in '_run__867212960703161301__process_action__2360218484576085785__callbacks' activesupport (3.0.9) lib/active_support/callbacks.rb:410:in '_run_process_action_callbacks' activesupport (3.0.9) lib/active_support/callbacks.rb:94:in 'run_callbacks' actionpack (3.0.9) lib/abstract_controller/callbacks.rb:17:in 'process_action' actionpack (3.0.9) lib/action_controller/metal/instrumentation.rb:30:in 'block in process_action' activesupport (3.0.9) lib/active_support/notifications.rb:52:in 'block in instrument' activesupport (3.0.9) lib/active_support/notifications/instrumenter.rb:21:in 'instrument' activesupport (3.0.9) lib/active_support/notifications.rb:52:in 'instrument' actionpack (3.0.9) lib/action_controller/metal/instrumentation.rb:29:in 'process_action' actionpack (3.0.9) lib/action_controller/metal/rescue.rb:17:in 'process_action' actionpack (3.0.9) lib/abstract_controller/base.rb:119:in 'process' actionpack (3.0.9) lib/abstract_controller/rendering.rb:41:in 'process' actionpack (3.0.9) lib/action_controller/metal.rb:138:in 'dispatch' actionpack (3.0.9) lib/action_controller/metal/rack_delegation.rb:14:in 'dispatch' actionpack (3.0.9) lib/action_controller/metal.rb:178:in 'block in action' actionpack (3.0.9) lib/action_dispatch/routing/route_set.rb:62:in 'call' actionpack (3.0.9) lib/action_dispatch/routing/route_set.rb:62:in 'dispatch' actionpack (3.0.9) lib/action_dispatch/routing/route_set.rb:27:in 'call' rack-mount (0.6.14) lib/rack/mount/route_set.rb:148:in 'block in call' rack-mount (0.6.14) lib/rack/mount/code_generation.rb:93:in 'block in recognize' rack-mount (0.6.14) lib/rack/mount/code_generation.rb:68:in 'optimized_each' rack-mount (0.6.14) lib/rack/mount/code_generation.rb:92:in 'recognize' rack-mount (0.6.14) lib/rack/mount/route_set.rb:139:in 'call' actionpack (3.0.9) lib/action_dispatch/routing/route_set.rb:493:in 'call' warden (1.0.5) lib/warden/manager.rb:35:in 'block in call' warden (1.0.5) lib/warden/manager.rb:34:in 'catch' warden (1.0.5) lib/warden/manager.rb:34:in 'call' actionpack (3.0.9) lib/action_dispatch/middleware/best_standards_support.rb:17:in 'call' actionpack (3.0.9) lib/action_dispatch/middleware/head.rb:14:in 'call' rack (1.2.3) lib/rack/methodoverride.rb:24:in 'call' actionpack (3.0.9) lib/action_dispatch/middleware/params_parser.rb:21:in 'call' actionpack (3.0.9) lib/action_dispatch/middleware/flash.rb:182:in 'call' actionpack (3.0.9) lib/action_dispatch/middleware/session/abstract_store.rb:149:in 'call' actionpack (3.0.9) lib/action_dispatch/middleware/cookies.rb:302:in 'call' activerecord (3.0.9) lib/active_record/query_cache.rb:32:in 'block in call' activerecord (3.0.9) lib/active_record/connection_adapters/abstract/query_cache.rb:28:in 'cache' activerecord (3.0.9) lib/active_record/query_cache.rb:12:in 'cache' activerecord (3.0.9) lib/active_record/query_cache.rb:31:in 'call' activerecord (3.0.9) lib/active_record/connection_adapters/abstract/connection_pool.rb:354:in 'call' actionpack (3.0.9) lib/action_dispatch/middleware/callbacks.rb:46:in 'block in call' activesupport (3.0.9) lib/active_support/callbacks.rb:416:in '_run_call_callbacks' actionpack (3.0.9) lib/action_dispatch/middleware/callbacks.rb:44:in 'call' rack (1.2.3) lib/rack/sendfile.rb:107:in 'call' actionpack (3.0.9) lib/action_dispatch/middleware/remote_ip.rb:48:in 'call' actionpack (3.0.9) lib/action_dispatch/middleware/show_exceptions.rb:47:in 'call' railties (3.0.9) lib/rails/rack/logger.rb:13:in 'call' rack (1.2.3) lib/rack/runtime.rb:17:in 'call' activesupport (3.0.9) lib/active_support/cache/strategy/local_cache.rb:72:in 'call' rack (1.2.3) lib/rack/lock.rb:11:in 'block in call' :10:in 'synchronize' rack (1.2.3) lib/rack/lock.rb:11:in 'call' actionpack (3.0.9) lib/action_dispatch/middleware/static.rb:30:in 'call' railties (3.0.9) lib/rails/application.rb:168:in 'call' railties (3.0.9) lib/rails/application.rb:77:in 'method_missing' railties (3.0.9) lib/rails/rack/log_tailer.rb:14:in 'call' rack (1.2.3) lib/rack/content_length.rb:13:in 'call' rack (1.2.3) lib/rack/handler/webrick.rb:52:in 'service' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/webrick/httpserver.rb:111:in 'service' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/webrick/httpserver.rb:70:in 'run' /Users/daw/.rvm/rubies/ruby-1.9.2-p180/lib/ruby/1.9.1/webrick/server.rb:183:in 'block in start_thread'
更新
根据要求,型号代码:
class Image { # :thumb => '100x100>', # :full => '800x800>' #}, :storage => :s3, :s3_credentials => Rails.root.join( 'config', 's3.yml' ), :path => ":id/:style/:filename" def to_param self.name.parameterize end private def create_slug self.slug = self.to_param end end
更新2
我比较了用:multipart => true
构建的Image
实例:multipart => true
vs without,并确认唯一的区别是文件上传字段picture_file_name
。 没有:multipart => true
,它是一个带文件名的字符串(不奇怪)。 有了它,它是ActionDispatch::Http::UploadedFile
一个实例。 鉴于堆栈跟踪在to_yaml
调用期间显示其失败,可能问题在于UploadedFile
实例转换为YAML?
好吧,我终于屈服了,通过记录器输出跟踪了我的ActiveRecord源代码。 事实certificate,正如我所怀疑的那样,它无法保存UploadedFile
因为它无法将其转换为YAML。
但是,这是因为我犯了一个愚蠢的错误。 在我的提交表格中,我有:
<%= f.file_field :picture_file_name %>
什么时候应该是:
<%= f.file_field :picture %>
paperclip
gem理解:picture
是上传的文件,用于将文件名保存到正确的字段。 我只是低估了易用性!
通常情况下,我会删除这个微不足道的问题,但看到我犯了这个错误,其他人可能会在将来,而且很少有人指出解决方案。 因此,我将继续努力,以帮助将来搜索类似密集的开发人员!
经过大量的搜索和调试。 这个问题的主要症状是带有文件字段的表单被制作为多部分表单而rails 3.2无法保存数据,因为它试图保存数据库中不存在的其他参数(文件的归档)宾语)。
获取适当的值并将它们保存到某个变量并从params中删除文件哈希似乎解决了这个问题!
以下是使用rails 3.2保存在数据库中的工作代码示例
file = params[:document][:file].tempfile.read params[:document].delete(:file) @document = Document.new(params[:document]) respond_to do |format| if @document.save @document.file = file @document.save format.html { redirect_to @document, notice: 'Document was successfully created.' } format.json { render json: @document, status: :created, location: @document } else format.html { render action: "new" } format.json { render json: @document.errors, status: :unprocessable_entity } end end
你没有发布它,但我认为你应该使用:html => { :multipart => true }
而不只是:multipart => true
你的表单中有:multipart => true
,如:
form_for object, :html => { :multipart => true } do |o| ...
即使我有正确的字段,我也花了大约一个星期来处理相同的错误。
导致我所有头痛的愚蠢只是视图中标签的顺序。
导致错误
NoMethodError in DatenightsController#create undefined methodname' for nil:NilClass
:
<%= f.file_field :photo %> <%= f.text_field :name %>
以上引用错误的解决方案 (这里的序列/顺序很重要)
<%= f.text_field :name %> <%= f.file_field :photo %>
由于这个问题花了很多我的甜蜜时光,我认为它可能对你有所帮助。