使用一個可以發送到Web並爬取各種服務的小Ruby腳本。我有一個內部有幾個類的模塊:Ruby - 在模塊/類中共享記錄器實例
module Crawler
class Runner
class Options
class Engine
end
我想在這些類中共享一個記錄器。一般情況下我只是把這個在一個恆定的模塊中引用它,像這樣:
Crawler::LOGGER.info("Hello, world")
的問題是,我無法創建我的記錄器實例,直到我知道那裏的輸出是怎麼回事。你可以通過命令行啓動爬行,在這一點上,你可以告訴它要在發展上運行(日誌輸出到stdout)或生產(日誌輸出爲一個文件,crawler.log):
crawler --environment=production
我有一個類Options
解析通過命令行傳入的選項。只有在那時,我才知道如何用正確的輸出位置實例化記錄器。
所以,我的問題是:如何/我在哪裏放置我的記錄器對象,以便我的所有類都可以訪問它?
我可以將我的記錄器實例傳遞給我創建的每個類實例的每個new()
調用,但是我知道必須有更好的Rubyish方法才能做到這一點。我正在想象模塊上的一些奇怪的類變量,與class << self
或其他一些魔法共享。 :)
更詳細一點:Runner
通過將命令行選項Options
類開始的一切,回來的對象有幾個實例變量:
module Crawler
class Runner
def initialize(argv)
@options = Options.new(argv)
# feels like logger initialization should go here
# @options.log_output => STDOUT or string (log file name)
# @options.log_level => Logger::DEBUG or Logger::INFO
@engine = Engine.new()
end
def run
@engine.go
end
end
end
runner = Runner.new(ARGV)
runner.run
我需要的代碼Engine
到能夠訪問記錄器對象(以及在Engine
內部初始化的更多類)。幫幫我!
如果您可以動態更改已經實例化的記錄器的輸出位置(類似於更改日誌級別),所有這些都可以避免。我將它實例化爲STDOUT,然後在生產環境中轉換爲文件。我在某處看到了一個關於更改Ruby的$ stdout全局變量的建議,這個變量會將輸出重定向到除STDOUT以外的其他位置,但這看起來很詭異。
謝謝!
謝謝查克!這正是我在結束一些測試後最終做的事情! – 2009-05-27 23:14:28