我在Rails 4.2.6應用程序中有內存泄漏。控制器分配一個大的GaragesPresenter
對象作爲實例變量,在請求完成後應該取消引用並進行垃圾回收。但是,我發現這種情況從未發生過。Rails內存泄漏:持有對實例的引用的控制器類
def show
@garage = GaragesPresenter.new(@garage, view_context)
respond_to do |format|
format.html
end
end
我看到的GaragesPresenter
實例的引用正在舉行由GaragesController
實例,一個實例是由GaragesController
類舉行。在請求完成並且已調用GC.start
很久之後,情況就是如此。 爲什麼GaragesController
類持有對實例的引用?
我知道這是因爲我成立了一個堆轉儲:
require 'objspace'
...
GC.start
file = File.open("/tmp/dumpfile", 'w')
ObjectSpace.dump_all(output: file)
而生成的文件我看到以下三個對象:
以下對象是GaragesPresenter,這是非常大:
{"address":"0x7fd077217e20", "type":"OBJECT", "class":"0x7fd074a04618", "ivars":7, "references":["0x7fd0772bf940", "0x7fd077711480", "0x7fd077748188", "0x7fd077772898", "0x7fd07720c778", "0x7fd0771ef8d0", "0x7fd0771ef8d0"], "file":"/Users/dyoung/workspace/commutyble/site-app/app/controllers/garages_controller.rb", "line":19, "method":"new", "generation":35, "memsize":56, "flags":{"wb_protected":true, "old":true, "marked":true}}
於上述對象的引用被保持由GaragesController實例(預計,隨着顯示方法分配呈現者作爲一個實例變量):
{"address":"0x7fd0727559f0", "type":"OBJECT", "class":"0x7fd0727865a0", "ivars":22, "references":["0x7fd0727558b0", "0x7fd072755888", "0x7fd072755838", "0x7fd0732400e0", "0x7fd072754a50", "0x7fd0734c5658", "0x7fd07704e878", "0x7fd0732ab020", "0x7fd072785ee8", "0x7fd077217e20", "0x7fd0771ffe10", "0x7fd07720cde0", "0x7fd0732a82d0"], "file":"/Users/dyoung/.rvm/gems/ruby-2.1.0/gems/actionpack-4.2.6/lib/action_controller/metal.rb", "line":237, "method":"new", "generation":35, "memsize":176, "flags":{"wb_protected":true, "old":true, "marked":true}}
甲參考上述GaragesController實例是由GaragesController類保存,可能會阻止garabage的收集。爲什麼??
{"address":"0x7fd0727865a0", "type":"CLASS", "class":"0x7fd0726a7260", "name":"GaragesController", "references":["0x7fd0727559f0", "0x7fd0726a72b0"], "file":"/Users/dyoung/.rvm/gems/ruby-2.1.0/gems/activesupport-4.2.6/lib/active_support/callbacks.rb", "line":435, "method":"instance_exec", "generation":35, "memsize":672, "flags":{"wb_protected":true, "old":true, "marked":true}}
似乎'[WeakRef](紅寶石-doc的。 org/stdlib-1.9.3/libdoc/weakref/rdoc/WeakRef.html)'可以幫助 – oklas