使用 WordPress Hooks 清理代碼、激活和卸載

已發表: 2015-01-23

插件作者在他們產品的主要功能上投入了大量的時間和精力,以至於他們讓不太重要的東西被擱置一旁。

以激活和停用為例。 雖然激活鉤子很普遍——許多插件需要添加一些選項,刷新重寫規則,可能創建數據庫表,或者在安裝時檢查版本差異——停用和卸載鉤子遠不常見。

重點在這裡? 許多插件作者不會花時間自己清理。 WordPress 安裝真的需要你刪除插件後創建的自定義表嗎? 為什麼不在刪除插件之前清除一些插件獨有的選項?

在本文中,我將向您展示如何使用激活、停用和卸載掛鉤來初始化您的插件,並在用戶使用完您的產品後更輕鬆地進行清理。

  • 激活鉤子
    • 安裝順序
    • 刷新重寫規則
    • 創建數據庫表
    • 依賴檢查
  • 停用掛鉤
  • 卸載鉤子
  • 額外的安全性
  • 是時候清理了

注意:如果您打算瀏覽本文,我強烈建議您看一下最後的“附加安全性”部分,它通過一些有價值的安全檢查來補充代碼。 此外,如果您在 WordPress 插件掛鉤方面需要幫助,這裡是關於使用 WordPress 掛鉤以及如何在 WordPress 中激活功能的快速復習。

激活鉤子

雖然激活鉤子很簡單,但安裝它有點特殊,所以我們需要注意事件的順序。 在我們進入所有這些之前,這裡有一個簡單的例子:

加載要點 f356a899b7f009d136644383339db4f6

這一切的關鍵是register_activation_hook()函數。 第一個參數是主插件文件的路徑; 第二個參數定義要運行的函數。 在內部, register_activation_hook()函數是“activate_[plugin_name]”操作的包裝器,但由於它更易於使用,因此在插件中看到鉤子並不常見。

安裝順序

了解安裝順序很重要,因為它會阻止使用您可能習慣的方法。 register_activation_hook()在用戶點擊激活鏈接並因此看到激活通知之間被調用。 它在一個中間頁面上運行,該頁面在任何鉤子有機會運行之前立即重定向。

讓我們看一個例子,看看為什麼這是一個巨大的無賴:

刷新重寫規則

許多插件創建自定義帖子類型。 在激活時刷新重寫規則以確保用戶在訪問來自新自定義帖子類型的帖子時不會收到 404 錯誤是明智之舉。

下面的代碼似乎合乎邏輯,但會失敗。

加載要點 7c656623608efd1785437ebe7cdb7350

看起來非常好。 創建自定義帖子類型,並在激活時刷新重寫規則。 問題是當我們刷新重寫規則時還沒有創建自定義帖子類型。

以下是流程的外觀:

  1. 用戶安裝插件。
  2. 用戶單擊激活鏈接。
  3. 中間頁面只運行激活鉤子,沒有別的。 這會刷新重寫規則。
  4. 該插件處於活動狀態,代碼照常運行。 自定義帖子類型已註冊。

Stack Overflow 上發布的一個解決方案,得到了 WordPress Codex 的正式認可,解決了我們的小問題。 該解決方案涉及添加一個選項以指示該插件剛剛安裝。

如果存在此選項,我們會執行激活操作,然後將其刪除。

像這樣的東西:

加載要點 6f0927b3bf9807e426c8778a3bf3a797

就個人而言,我不太喜歡這種解決方案。 問題是第八行的檢查在每一個頁面加載時都會運行。 這沒什麼好擔心的,因為它不會給您的服務器帶來很大的負載,也不會減慢您用戶的網站速度。 這是一個非常快速的檢查,對性能的影響可以忽略不計。 然而,在 99.9% 的情況下,它是不必要的。

在 Codex 的文檔中, flush_rewrite_rules()函數有一個更好的解決方案。 在這個解決方案中,我們使用函數的模塊化分別在激活時註冊自定義帖子類型:

加載要點 b44bf08bf511277184a49de53c0c3ed8

我們不再依賴需要一直運行的檢查,而是使用激活函數來註冊我們的帖子類型。 請注意,一旦我們的插件被激活,帖子類型將始終從init鉤子中註冊。

這是法典無處不在的一個可悲的例子。 一般來說,WordPress 確實有很好的文檔,但如果有些東西看起來很浪費或不合邏輯,不要害怕自己做一些研究。

創建數據庫表

一些插件執行的另一項任務是創建數據庫表。 通常,這是不必要的,但有一些合法的用例。

Codex 關於創建表的文章中的這個示例顯示瞭如何使用多個激活調用:

加載要點 9a1d4757d023f2442093a9a158cdb6b4

第一個函數jal_install()創建一個新的數據庫表。 第二個函數jal_install_data將初始數據添加到表中。 我們可以多次使用register_activation_hook ,而不是使用register_activation_hook()添加一個包含所有這些代碼的函數。

這是模塊化的一個很好的實踐。 一方面,您不必添加初始測試數據——就像移除激活鉤子一樣簡單——因此您可以保持功能完好無損。 另一方面,您可以在任何地方自由地重用這些功能,因為它們是分開的。

依賴檢查

激活函數的另一個常見任務是檢查依賴關係。 您的插件可能依賴於特定版本的 WordPress、另一個插件,甚至是特定版本的 PHP。

下面的代碼檢查最低 WP 和 PHP 版本,並在必要時重定向用戶(不激活插件):

加載要點 79a2c5414969291ec90cac11c38b7522

停用掛鉤

停用掛鉤在用戶停用插件但在卸載(刪除)之前運行。 停用鉤子的使用方式與激活鉤子相同:

加載要點 6ed9bb66ee1863ab3e84db1f9f753792

停用意味著用戶僅停用了您的插件,因此您不會像卸載期間那樣做太多事情。 您可能想要刷新重寫規則,但在這個階段,您不會想要擺脫所有選項和數據庫表(如果有的話)。

這相當簡單,但我會特別注意刷新重寫規則,因為這些又是有問題的。

法典建議按如下所示進行操作,但這不起作用

加載要點 4440a0178b4e34506530e13d0ead8958

這不起作用的原因與以前相同。 運行停用會執行init掛鉤,這意味著當我們停用插件時,我們也在註冊我們的自定義帖子類型。 重寫規則已刷新,但它們考慮了自定義帖子類型。

有一張 Trac 票可以解決這個問題,但在那之前,我不能給你一個很好的方法來解決這個問題。 我發現可行的唯一方法是完全刪除重寫規則:

加載要點 98b496826278084a2f7a5ea27994f781

雖然這在過去對我有用,但我不推薦它。 與有一些額外的重寫規則的問題相比,它引入了更大的不確定性。 我寧願向用戶顯示一條註釋,要求他們在停用後訪問永久鏈接設置,這將刷新重寫規則。 在實施更好的解決方案之前,我們一直堅持這一點……抱歉!

卸載鉤子

卸載插件時有兩種運行代碼的方法。 您可以通過register_uninstall_hook()使用卸載鉤子,也可以在插件中使用專用的uninstall.php文件。 我將向您展示兩者,但首選方法是使用卸載文件。

卸載鉤子的主要問題是“它會阻止主插件文件在卸載期間運行,如果插件在全局空間中運行代碼,這可能會出現問題。 卸載代碼集中化也更好。” ——斯科特·萊利

下面的代碼顯示了使用基本掛鉤的卸載過程:

加載要點 040847db4739148900b1ee29d227d71d

如前所述,這不是最佳解決方案。 處理卸載的更好方法是使用uninstall.php文件。 您需要做的就是創建它,如果它可用,它將被使用。

加載要點 44dde25dcb57b4239be8586f4d04c765

如您所見,這實際上是一個更簡單的解決方案。 最重要的是,它是獨立的。

額外的安全性

我不想讓到目前為止顯示的示例與安全相關問題過於復雜,但您確實應該採取一些步驟來確保只有那些被允許這樣做的人才能運行這些操作。

在激活和停用時使用以下代碼段:

加載要點 357037989065f89c15f049314e9831bf

此代碼塊確保用戶有權執行此操作並且該操作源自正確的頁面。 這應該可以防止大多數惡意嘗試。

卸載過程很特殊,所以我們需要使用稍微不同的代碼:

加載要點 541c93cfa9b89e1e6c7b48b06732d31f

是時候清理了

如果您的插件將內容添加到 WordPress,那麼當用戶決定刪除您的插件時,您作為開發人員有責任將其刪除。

使用上述激活、停用和卸載方法,您可以構建一個安全可靠的系統。 我還強烈推薦閱讀這個 Stackexchange 線程,它概述了 OOP 環境中的這些過程。

如果您還不是 WPMU DEV 成員,請立即註冊免費試用,完全無風險。 作為會員,您將可以訪問我們所有出色的插件和超快的託管服務,以及針對您所有與 WordPress 相關的問題的專家 24/7 支持。

當您刪除插件時,您是否發現插件會使您的數據庫變得一團糟? 在下面的評論中讓我們知道您的想法。
標籤: