我正在使用 SemanticLogger 進行日志記錄。它提供了一個Loggable
模塊,類可以包含該模塊以創建logger
回傳特定于類的記錄器物件的類和實體方法。
我正在使用我自己的代碼庫中的一個模塊,該模塊需要訪問logger
其實體方法中的方法。如果我include SemanticLogger::Loggable
在模塊中呼叫,它會使模塊“類”方法可以訪問記錄器方法,但不能訪問實體方法,因為模塊沒有實體,并且模塊實體方法成為包含類的方法。
因此,為了使記錄器呼叫不失敗,我需要確保包含我的模塊的任何類也包含 SemanticLogger::Loggable。處理這個問題的最佳方法是什么?也許這個?:
module MyModule
# ...
def included(_includer_module_or_class)
require 'semantic_logger'
include SemanticLogger::Loggable
end
...
end
uj5u.com熱心網友回復:
SemanticLogger 是一個類級別的 Mixin
SemanticLogger 是一段復雜的代碼,它的一些內部結構沒有很好的檔案記錄。理解它真正在做什么(以及為什么會遇到問題)的關鍵在于,它實際上是在創建類級別的物件,然后實體可以訪問這些物件。特別是,:logger
是在包含類的背景關系中定義的訪問器,這就是為什么您不能簡單地將其添加到 #included 塊中,而無需非常明確地說明self在您include SemanticLogger::Loggable
的 .
在包含類上呼叫 #class_exec
一旦理解了這一點,解決方案就變得不言而喻了:在包含模塊時,您必須在模塊方法內的包含類上呼叫Module#class_exec。換句話說,確保 #included 是一個模塊方法,并且方法內部的self是包含類而不是封閉模塊。例如::included
require "bundler/setup"
require "semantic_logger"
module MyModule
def self.included klass
klass.class_exec do
include SemanticLogger
include SemanticLogger::Loggable
SemanticLogger[klass]
# any other class-level configuration you want
# for SementicLogger or your :logger accessor
end
end
end
將您的自定義日志模塊混合到一個類中
一旦正確定義了 mixin,就可以輕松地將其混入任何類中。例如:
class Foo
include MyModule
end
@foo = Foo.new
both the Foo class and the @foo instance will have access to SemanticLogger capabilities, and you'll be able to call @foo.logger.info "Test Message"
on your instance from outside your class, or simply use :logger
as an accessor from within your Foo class.
If there's a more elegant way to do this, I haven't found it yet. This works consistently for me, and should at least get you started down the right path when using customized SemanticLogger mixins within your own classes.
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/508366.html
下一篇:js函式獲取欄位中的所有值