如何寫一個屬于自己的數據庫封裝(5)

基本思路

在開始代碼之前, 我們需要回想一些日常面對的難題, 或則說不良體驗

在實現業務邏輯時, 我們往往都會遇到以下類似場景

確認A先生(id=233)是否會員, 如果是, 修改字段’status’為’active’, 否則刪除它

在沒有框架的時候一般都會這么寫的(以下代碼略過所有框架邏輯)

// 首先查詢A先生的數據, 獲取他的身份  $a = 'select * from users where id = 233';  // 判定是否為會員  if($a->member === true)      // 是就修改字段     $b = 'update users set status = 'active' where id = 233';  else     // 否就刪除數據     $b= 'delete from users where id = 233';

注意,這是因為我們簡略了pdo的所有步驟, 試想想更復雜的業務邏輯, 曾經見過滿滿上千行都是SQL語句的, 代碼可讀性等于0, 重構無能
所以,憑什么我們需要寫的這么多呢, 可以簡化啊!

可再操作的數據

當數據返回后,將其轉化為實例, 該實例附帶框架, 可以進行某些操作

這就是查詢篇中為什么數據返回后會被放入函數cast()當中進行轉化的原因

使用封裝后可以這么做

// 首先查詢A先生的數據, 獲取他的身份  $a = User::find(233);  // 判定是否存在該id和該id是否為會員  if($a & $a->member)      // 是就修改字段     $b = $a->update(['status'=>'active']);  else     // 否就刪除數據     $b= $a->delete();

接下來我們需要思考

如何對數據庫數據進行修改?

這是我自己的膚淺答案

常見的情況我們需要用到條件語法, 對需要修改的數據指定范圍, 過濾無需改寫的數據

根據以上的說明, 有三種例子

  1. 完全不指定范圍, 框架內所有數據

    update Actor set first_name = 'new data'
  2. 指定范圍, 修改匹配條件的多條數據

    update Actor set first_name = 'new data' where first_name like '%L%'
  3. 指定范圍, 依據表的 identity 框架 或 unique key 修改指定單條數據

    update Actor set first_name = 'new data' where actor_id = 10

根據以上的三種類型, 我們可以開始開發update函數了,
PS:過于高級的update語句我因為經驗尚淺無法理解/不曾使用, 歡迎留言


Builder.php

在最后一行添加update函數

// 改寫數據庫數據      public function update(array $values) {          // 如果寫保護已經開啟,跳出錯誤          if($this->writeLock) throw new Exception("data is not allow to update");            // 編譯update語句          $sql = $this->grammar->compileUpdate($this, $values);            // 將所有變量的值合成一個數組, 其中包括條件語句部分          $bindings = array_values(array_merge($values, $this->getBindings()));            // 返回改寫結果,成功true失敗false          return $this->connector->update($sql, $bindings);      }

Grammar.php

在最后一行添加compileUpdate函數

    public function compileUpdate(Builder $query, $values) {          // 循環$values, 記得引用          foreach ($values as $key => &$value)               // 將所有$value改成對應的$key=?              $value = $key.' = ?';            // 將$values中的之全部掏出在連接起來          $columns = implode(', ', array_values($values));            // 附上where語句如果有          // 由于更復雜的sql update語句我還沒試過, 為了不坑人, 所以限制只有where語法有效          // 歡迎提供更復雜的where語句          $where = is_null($query->wheres) ? '' : $this->compileWheres($query);            // 返回update語句          return trim("update $query->from set $columns $where");      }

框架.php

添加函數save, 用法見下面例子

// 一種更快捷的update方式      public function save() {          return $this->update((array)$this->data);      }

例子

  • 修改指定數據

$a = Actor::where('first_name', 'ANGELINA')      ->update(['last_name'=>'changed']);  dd($a);
  • 再操作數據實例

$a = Actor::where('first_name', 'ANGELINA')      ->first();  dd($a->update(['last_name'=>'again']));
  • 再操作數據實例, 另一種用法

$a = Actor::where('first_name', 'ANGELINA')      ->first();    $a->last_name = 'save';  dd($a->save());

返回結果

boolean true  // 失敗返回false

? 版權聲明
THE END
喜歡就支持一下吧
點贊13 分享