簡體   English   中英

在PHP中獲取唯一的worker / thread / process / request ID

[英]Get unique worker/thread/process/request ID in PHP

在多線程環境中(像大多數Web平台一樣),我經常在我的應用程序的日志中包含某種線程ID。 這使我能夠確切地告訴哪些日志條目來自哪個請求/線程,當有多個請求同時寫入同一日志時。

在.NET / C#中,這可以通過log4net的格式化程序來完成,默認情況下包括當前線程的ManagedThreadId (數字)或Name (給定名稱)。 這些屬性唯一標識一個線程(例如:參見: 如何使用log4net使用Threadpool線程記錄正確的上下文?

在PHP中,我沒有發現任何類似的東西(我問谷歌,PHP文檔和SO)。 它存在嗎?

直到最近,我使用了apache_getenv(“UNIQUE_ID”),它與crc32或其他哈希函數完美配合。

現在我只是使用以下內容,以消除對Apache和此mod的依賴。

$uniqueid = sprintf("%08x", abs(crc32($_SERVER['REMOTE_ADDR'] . $_SERVER['REQUEST_TIME'] . $_SERVER['REMOTE_PORT'])));

它足夠獨特,可以了解哪些日志屬於哪個請求。 如果需要更高的精度,可以使用其他散列函數。

希望這可以幫助。

zend_thread_id()

 int zend_thread_id ( void ) 

此函數返回當前線程的唯一標識符。

雖然:

只有在使用ZTS(Zend線程安全)支持和調試模式(--enable-debug)構建PHP時,此功能才可用。


當您使用該API進行數據庫訪問時(或使用mysqli時的mysqli::$thread_id mysql_thread_id() ,您也可以嘗試調用mysql_thread_id() )。

我已經看到getmypid()用於此目的,但它似乎在不同的系統上表現不同。 在某些情況下,ID對每個請求都是唯一的,但在其他情況下,它是共享的。

因此,您可能更好地使用其中一個答案來確保可移植性。

PHP似乎沒有可用的功能,但您的Web服務器可能能夠通過環境變量傳遞標識符。 例如,一個名為“mod_unique_id”[1]的Apache模塊為每個請求生成唯一標識符,並將其存儲為環境變量。 如果變量存在,則應通過$ _SERVER ['unique_id'] [2]顯示該變量

“純PHP”解決方案可能是編寫一個生成合適的隨機標識符的腳本,通過define(“unique_id”,val)存儲它,然后在php.ini中使用auto_prepend_file [3]選項將其包含在每個執行的腳本中。 這樣,當請求開始處理時將創建唯一ID,並且在處理請求期間它將可用。

分配ID以識別提供請求的記錄數據可能就像創建UUID版本4(隨機)並將其寫入日志的每一行一樣簡單。

甚至還有軟件幫助: ramsey / uuidphp-middleware / request-id

通過將UUID放入LoggerMDC數據並使用適當的LogFormatter來使用log4php ,可以輕松地將其添加到每個日志記錄行。 對於PSR-3記錄儀,它可能有點復雜,YMMV。

隨機創建的UUID將適合於識別單個請求,並且通過在子請求的HTTP頭中和響應中使用該UUID,甚至可以跨服務器場內的多個系統和平台跟蹤一個請求。 但是,將它作為標題並不是我提到的任何軟件包的任務。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM