Phalcon只更新改變的字段

前言

以前官網作了一次改版,運行一年多的時間,狀態良好。在性能和抗壓程度上都有了比較大的提高。php

然而,在對接了 TMS(第三方配送系統) 和電子發票以後,會常常發生訂單狀態異常的狀況。html

問題

通過老大和慧哥的分析(我參與了問題的解決,未參與分析),流程以下:sql

  • 配送員在 TMS 操做訂單完成(完成中);
  • 開電子發票的腳本獲取了訂單的信息;
  • TMS 更新完成,訂單狀態發生改變;
  • 開電子發票的腳本從新更新了訂單的信息,訂單被變動爲 TMS 更新以前的狀態。

正常的 Phalconupdate 流程以下:性能

$robot = Robots::findFirstById($id);
$robot->name = 'wali';
$robot->update();

// ------- or -------

$robot = Robots::findFirstById($id);
$robot->update(['name' => 'wali']);
複製代碼

理想中的 SQL 語句:this

UPDATE `robots` SET `name` = 'wali' WHERE `id` = 1
複製代碼

現實中的 SQL 語句:spa

UPDATE `robots` SET `name` = 'wali', `model` => '1' WHERE `id` = 1
複製代碼

也就是說 Phalcon 會將取到的全部數據都更新一次。code

若是在A取到結果以後,B也操做並更新了這個記錄以後,A再更新,那麼B的操做就至關於沒有作,這就形成了上面的尷尬一幕。htm

解決

解決方案有好幾個,我會從最不建議的方式開始。blog

使用白名單

Phalcon 更新一條記錄的過程當中,會調用 model 類中的 save 方法,而 save 方法提供了一個參數 whiteList,在 whiteList 以內的字段是不會被更新的。get

優勢: 能夠限制某些字段的更新。

缺點: 針對當前狀況,須要在每一處操做限制,並且須要更改 update 的方式爲 save,工做量太大。

本身寫SQL

能夠獲取寫服務以後,直接 execute SQL 語句,這樣能夠避免全部字段更新的狀況。

優勢: 適合批量更新或者多表更新的狀況。

缺點: 和第一種方案同樣,須要修改每一處地方,工做量大。

設置只更新變化的字段

Phalcon 自己仍是提供了只更新變化字段的方法的,調用也很簡單,在 Model 初始化時,調用 useDynamicUpdate 方法,參數爲 true

public function initialize() {
    $this->useDynamicUpdate(true); // 就是它,神奇的方法
    $this->setReadConnectionService('slave');
    $this->setWriteConnectionService('master');
    $this->setSource($this->_tableName);
}
複製代碼

優勢: 便捷,快速,改動地方少。

缺點: 固然是有的,不過我沒有想到...

總結

有些雷,會在不知不覺中埋下,因此對於未知的東西,仍是要多瞭解,纔可以做出更加正確的決定。

-- EOF --

本文轉載自IMJCW

原文連接:Phalcon只更新改變的字段

相關文章
相關標籤/搜索