這個問題是更多的是「我該怎麼辦?」,而不是「我在做什麼錯?」。我有一個名爲的查詢處理器,它處理查詢(認爲CQRS)。該對象被注入到我的演示者中。 QueryProcessor需要使用內核來解析綁定。直接或通過工廠注入內核很容易。這樣做不會導致內存泄漏是訣竅。Ninject工廠擴展和處理內存泄漏
我已經使用內存分析器驗證過我的QueryProcessor對象沒有被垃圾收集。這個類看起來是這樣的:
public sealed class QueryProcessor : IQueryProcessor, IDisposable
{
private readonly IKernelFactory _container;
private bool _disposed;
public QueryProcessor(IKernelFactory container)
{
_container = container;
}
//[DebuggerStepThrough]
public TResult Process<TResult>(IQuery<TResult> query)
{
var handlerType = typeof(IQueryHandler<,>).MakeGenericType(query.GetType(), typeof(TResult));
dynamic handler = _container.RetrieveKernel().Get(handlerType);
return handler.Handle((dynamic)query);
}
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
private void Dispose(bool disposing)
{
if (disposing && !_disposed)
{
// dispose of stuff here
_disposed = true;
}
}
}
public interface IKernelFactory
{
IKernel RetrieveKernel();
}
我的作文根是相當簡單的。我正在使用Ninject的工廠擴展。
public void OnLoad(IKernel kernel)
{
// Auto-Register all the validators which are stored in the Service assembly.
AssemblyScanner.FindValidatorsInAssembly(_serviceAssembly).ForEach(
result => kernel.Bind(result.InterfaceType, result.ValidatorType)
);
ManualRegistrations(kernel);
kernel.Bind<IKernelFactory>().ToFactory();
AutoRegisterType(kernel, typeof(IQueryHandler<,>));
AutoRegisterType(kernel, typeof(ICommandHandler<>));
}
如上所述,注入正在工作,但它留下了內存泄漏。我該如何讓Ninject內核在我的QueryProcessor中解析內容而不會導致泄漏?
感謝
更新 - 新問題
我試圖通過創建一個新的模塊,新的內核,從根組成的主內核單獨解決這個問題。這些子內核將被創建並處理,其生命週期與QueryProcessors的生命週期相關聯。我把它掛在主模塊上:
kernel.Bind<IQueryProcessor>().ToMethod(ctx => new QueryProcessor(new StandardKernel(new ProcessorModule(_serviceAssembly)))).InTransientScope();
在內核第一次被處理之前它工作正常。但在那之後,我得到了以下錯誤消息:
Error loading Ninject component ICache
No such component has been registered in the kernel's component container.
Suggestions:
1) If you have created a custom subclass for KernelBase, ensure that you have properly
implemented the AddComponents() method.
2) Ensure that you have not removed the component from the container via a call to RemoveAll().
3) Ensure you have not accidentally created more than one kernel.
該死如果我這樣做,該死如果我不...
你如何綁定QueryProcessor?誰在處理查詢處理器? – BatteryBackupUnit
另請注意,如果沒有內存壓力,對於垃圾收集器*不收集對象*是完全合法的。等待,直到你沒有對對象的引用,然後把它當作內存泄漏是*無效*。那麼你有什麼證據證明實際上存在內存泄漏?由於您使用了內存分析器,因此請向我們展示所有到「QueryProcessor」的GC根目錄(應該收集但不是)的路徑。 – BatteryBackupUnit
@BatteryBackupUnit QueryProcessor與kernel.bind .To ()綁定,它由Presenters在其各自的Dispose方法中處理。但是,我不能處理內核,因爲它在其他地方是需要的。請注意,這不是一個Web項目,所以內核需要比HTTP請求/響應壽命更長。我會嘗試從今晚的探查器獲取一些數據。但它確實有一個強制GC的按鈕,並且該按鈕對所有其他第1代對象有效,這些對象在GC之後會從下一個內存快照中消失。使用此配置的 –
onefootswill