Slide 1

Slide 1 text

@kotomin_m #phpstudy Eloquentとクエリビルダを 両方使った実装の失敗例 ことみん 第150回 PHP勉強会@東京 @kotomin_m #phpstudy

Slide 2

Slide 2 text

@kotomin_m #phpstudy ことみん @kotomin_m
 所属:  株式会社ウィルゲート 21卒 趣味:  LT会とカンファレンス 特技:  懇親会で仲良くなる


Slide 3

Slide 3 text

@kotomin_m #phpstudy 1. 用語を知ろう
 2. 実装の失敗例
 Eloquentとクエリビルダを
 両方使った実装の失敗例


Slide 4

Slide 4 text

@kotomin_m #phpstudy 用語を知ろう
 ● Eloquent
 ● アクセサ
 ● ミューテタ
 ● クエリビルダ


Slide 5

Slide 5 text

@kotomin_m #phpstudy Eloquent


Slide 6

Slide 6 text

@kotomin_m #phpstudy Eloquent
 ● データベース操作を楽しくする、オブジェクトリ レーショナルマッパー(ORM)
 ● 各データベーステーブルに対応する「モデル」 を使用
 ● レコードの取得、挿入、更新、削除が可能
 https://readouble.com/laravel/10.x/ja/eloquent.html

Slide 7

Slide 7 text

@kotomin_m #phpstudy アクセサ


Slide 8

Slide 8 text

@kotomin_m #phpstudy アクセサ
 Eloquentの属性値にアクセスがあった時に、その 値を変換するもの
 https://readouble.com/laravel/10.x/ja/eloquent-mutators.html

Slide 9

Slide 9 text

@kotomin_m #phpstudy アクセサ(Laravel 5.6)
 アクセスしたいカラム名がFooの場合、 getFooAttributeメソッドをモデルに作成
 https://readouble.com/laravel/5.6/ja/eloquent-mutators.html

Slide 10

Slide 10 text

@kotomin_m #phpstudy アクセサ(Laravel 5.6)
 class User extends Model
 {
 /**
 * @param string $value
 * @return string
 */
 public function getFirstNameAttribute($value)
 {
 // 復号する
 return decrypt($value);
 }
 }


Slide 11

Slide 11 text

@kotomin_m #phpstudy アクセサ(Laravel 10.x)
 ● メソッド名はカラム名の「キャメルケース」で protectedなメソッドをモデルに作成
 ● 戻り値のタイプヒントは Illuminate\Database\Eloquent\Casts\Attribute
 ○ Attributeクラスのコンストラクタにget引数を与えます。
 https://readouble.com/laravel/10.x/ja/eloquent-mutators.html

Slide 12

Slide 12 text

@kotomin_m #phpstudy class User extends Model
 {
 /**
 * ユーザの名前取得
 */
 protected function firstName(): Attribute
 {
 return Attribute::make(
 get: fn (string $value) => ucfirst($value),
 );
 }
 }
 アクセサ(Laravel 10.x)


Slide 13

Slide 13 text

@kotomin_m #phpstudy ミューテタ


Slide 14

Slide 14 text

@kotomin_m #phpstudy ミューテタ
 Eloquentの属性値を設定するときに、その値を変 換するもの
 https://readouble.com/laravel/10.x/ja/eloquent-mutators.html

Slide 15

Slide 15 text

@kotomin_m #phpstudy ミューテタ(Laravel 5.6)
 アクセスしたいカラム名がFooの場合、 setFooAttributeメソッドをモデルに作成
 https://readouble.com/laravel/5.6/ja/eloquent-mutators.html

Slide 16

Slide 16 text

@kotomin_m #phpstudy ミューテタ(Laravel 5.6)
 class User extends Model
 {
 /**
 * @param string $value
 * @return void
 */
 public function setFirstNameAttribute($value)
 {
 // 暗号化する
 $this->attributes['first_name'] = encrypt($value);
 }
 }
 


Slide 17

Slide 17 text

@kotomin_m #phpstudy ミューテタ(Laravel 10.x)
 属性を定義するときに set という引数を指定する
 https://readouble.com/laravel/10.x/ja/eloquent-mutators.html

Slide 18

Slide 18 text

@kotomin_m #phpstudy class User extends Model
 {
 protected function firstName(): Attribute
 {
 return Attribute::make(
 get: fn (string $value) => ucfirst($value),
 set: fn (string $value) => strtolower($value),
 );
 }
 }
 ミューテタ(Laravel 10.x)


Slide 19

Slide 19 text

@kotomin_m #phpstudy クエリビルダ


Slide 20

Slide 20 text

@kotomin_m #phpstudy クエリビルダ
 ● クエリを作成し実行するために使用
 ● アプリケーションで行われるほとんどのデータ ベース操作が可能
 ○ select, where ……
 https://readouble.com/laravel/5.6/ja/queries.html

Slide 21

Slide 21 text

@kotomin_m #phpstudy クエリビルダ
 $users = DB::table('users')
 ->select('name','email as user_email')
 ->get();


Slide 22

Slide 22 text

@kotomin_m #phpstudy Eloquentとクエリビルダ
 組み合わせた実装の失敗例


Slide 23

Slide 23 text

@kotomin_m #phpstudy // クエリビルダでデータベースから値を取得
 $users = DB::table('users')
 ->select('id','first_name', 'last_name')
 ->get();
 
 // EloquentのupdateOrCreate()を利用してDBを更新
 $this->userHistory->updateOrCreate(
 ['user_id' => $users->id],
 [
 'last_name' => $users->last_name,
 'first_name' => $users->first_name,
 ]
 );
 


Slide 24

Slide 24 text

@kotomin_m #phpstudy // クエリビルダでデータベースから値を取得
 $users = DB::table('users')
 ->select('id','first_name', 'last_name')
 ->get();
 
 // EloquentのupdateOrCreate()を利用してDBを更新
 $this->userHistory->updateOrCreate(
 ['user_id' => $users->id],
 [
 'last_name' => $users->last_name,
 'first_name' => $users->first_name,
 ]
 );
 


Slide 25

Slide 25 text

@kotomin_m #phpstudy // クエリビルダでデータベースから値を取得
 $users = DB::table('users')
 ->select('id','first_name', 'last_name')
 ->get();
 
 // EloquentのupdateOrCreate()を利用してDBを更新
 $this->userHistory->updateOrCreate(
 ['user_id' => $users->id],
 [
 'last_name' => $users->last_name,
 'first_name' => $users->first_name,
 ]
 );
 


Slide 26

Slide 26 text

@kotomin_m #phpstudy // クエリビルダでデータベースから値を取得
 $users = DB::table('users')
 ->select('id','first_name', 'last_name')
 ->get();
 
 // EloquentのupdateOrCreate()を利用してDBを更新
 $this->userHistory->updateOrCreate(
 ['user_id' => $users->id],
 [
 'last_name' => $users->last_name,
 'first_name' => $users->first_name,
 ]
 );
 
 getメソッドは、クエリの結果を含む 
 Illuminate\Support\Collection 
 インスタンスを返す


Slide 27

Slide 27 text

@kotomin_m #phpstudy // クエリビルダでデータベースから値を取得
 $users = DB::table('users')
 ->select('id','first_name', 'last_name')
 ->get();
 
 // EloquentのupdateOrCreate()を利用してDBを更新
 $this->userHistory->updateOrCreate(
 ['user_id' => $users->id],
 [
 'last_name' => $users->last_name,
 'first_name' => $users->first_name,
 ]
 );
 
 Eloquentで使用するモデル 


Slide 28

Slide 28 text

@kotomin_m #phpstudy // クエリビルダでデータベースから値を取得
 $users = DB::table('users')
 ->select('id','first_name', 'last_name')
 ->get();
 
 // EloquentのupdateOrCreate()を利用してDBを更新
 $this->userHistory->updateOrCreate(
 ['user_id' => $users->id],
 [
 'last_name' => $users->last_name,
 'first_name' => $users->first_name,
 ]
 );
 
 第一引数に指定したカラムのモデルが 存在していたら更新、なかったら追加す る


Slide 29

Slide 29 text

@kotomin_m #phpstudy // クエリビルダでデータベースから値を取得
 $users = DB::table('users')
 ->select('id','first_name', 'last_name')
 ->get();
 
 // EloquentのupdateOrCreate()を利用してDBを更新
 $this->userHistory->updateOrCreate(
 ['user_id' => $users->id],
 [
 'last_name' => $users->last_name,
 'first_name' => $users->first_name,
 ]
 );
 
 ユーザ履歴テーブル(user_history)の 
 user_idと$users->idが一致するモデルが あれば更新、なかったら追加する 


Slide 30

Slide 30 text

@kotomin_m #phpstudy // クエリビルダでデータベースから値を取得
 $users = DB::table('users')
 ->select('id','first_name', 'last_name')
 ->get();
 
 // EloquentのupdateOrCreate()を利用してDBを更新
 $this->userHistory->updateOrCreate(
 ['user_id' => $users->id],
 [
 'last_name' => $users->last_name,
 'first_name' => $users->first_name,
 ]
 );
 


Slide 31

Slide 31 text

@kotomin_m #phpstudy // クエリビルダでデータベースから値を取得
 $users = DB::table('users')
 ->select('id','first_name', 'last_name')
 ->get();
 
 // EloquentのupdateOrCreate()を利用してDBを更新
 $this->userHistory->updateOrCreate(
 ['user_id' => $users->id],
 [
 'last_name' => $users->last_name,
 'first_name' => $users->first_name,
 ]
 );
 
 ミューテタが使われるので、暗号化されて 保存


Slide 32

Slide 32 text

@kotomin_m #phpstudy // クエリビルダでデータベースから値を取得
 $users = DB::table('users')
 ->select('id','first_name', 'last_name')
 ->get();
 
 // EloquentのupdateOrCreate()を利用してDBを更新
 $this->userHistory->updateOrCreate(
 ['user_id' => $users->id],
 [
 'last_name' => $users->last_name,
 'first_name' => $users->first_name,
 ]
 );
 
 クエリビルダで取得しているので、アク セサが使われない
 →複合されていない名前を取得してい る


Slide 33

Slide 33 text

@kotomin_m #phpstudy // クエリビルダでデータベースから値を取得
 $users = DB::table('users')
 ->select('id','first_name', 'last_name')
 ->get();
 
 // EloquentのupdateOrCreate()を利用してDBを更新
 $this->userHistory->updateOrCreate(
 ['user_id' => $users->id],
 [
 'last_name' => $users->last_name,
 'first_name' => $users->first_name,
 ]
 );
 
 すでに暗号化された状態のデータを さらに暗号化して保存 


Slide 34

Slide 34 text

@kotomin_m #phpstudy // クエリビルダでデータベースから値を取得
 $users = DB::table('users')
 ->select('id','first_name', 'last_name')
 ->get();
 
 // EloquentのupdateOrCreate()を利用してDBを更新
 $this->userHistory->updateOrCreate(
 ['user_id' => $users->id],
 [
 'last_name' => $users->last_name,
 'first_name' => $users->first_name,
 ]
 );
 
 失敗→二重で暗号化されてデータ ベースに保存されていた


Slide 35

Slide 35 text

@kotomin_m #phpstudy Eloquentとクエリビルダを 両方使った実装の失敗例 ことみん 第150回 PHP勉強会@東京 @kotomin_m #phpstudy