🎄teratailクリスマスプレゼントキャンペーン2024🎄』開催中!

\teratail特別グッズやAmazonギフトカード最大2,000円分が当たる!/

詳細はこちら
PHP

PHPは、Webサイト構築に特化して開発されたプログラミング言語です。大きな特徴のひとつは、HTMLに直接プログラムを埋め込むことができるという点です。PHPを用いることで、HTMLを動的コンテンツとして出力できます。HTMLがそのままブラウザに表示されるのに対し、PHPプログラムはサーバ側で実行された結果がブラウザに表示されるため、PHPスクリプトは「サーバサイドスクリプト」と呼ばれています。

Laravel 5

Laravel 5は、PHPフレームワークLaravelの最新バージョンで、2014年11月に発表予定です。ディレクトリ構造がが現行版より大幅に変更されるほか、メソッドインジェクションやFormRequestの利用が可能になります。

Q&A

1回答

3726閲覧

Laravelフレームワークのメソッドをオーバーライドしたい

SakuTaka

総合スコア12

PHP

PHPは、Webサイト構築に特化して開発されたプログラミング言語です。大きな特徴のひとつは、HTMLに直接プログラムを埋め込むことができるという点です。PHPを用いることで、HTMLを動的コンテンツとして出力できます。HTMLがそのままブラウザに表示されるのに対し、PHPプログラムはサーバ側で実行された結果がブラウザに表示されるため、PHPスクリプトは「サーバサイドスクリプト」と呼ばれています。

Laravel 5

Laravel 5は、PHPフレームワークLaravelの最新バージョンで、2014年11月に発表予定です。ディレクトリ構造がが現行版より大幅に変更されるほか、メソッドインジェクションやFormRequestの利用が可能になります。

0グッド

0クリップ

投稿2019/09/18 01:36

編集2019/09/18 02:04

前提・実現したいこと

Laravelの論理削除で、他のカラムの値も更新したい。

そのためには
trait Illuminate\Database\Eloquent\SoftDeletes

メソッドrunSoftDelete()
をオーバーライドするという記事があったのでそれを参考にしましたが
どこに何を書いても何も変わりません。

基本的なLaravelフレームワークの理解ができていないと思うのですが
アドバイスいただければと思います。

該当のソースコード

####アプリケーションのModel

php

1namespace App\Models; 2 3use Illuminate\Database\Eloquent\Model; 4use Illuminate\Database\Eloquent\SoftDeletes; 5use App\Models\CommonTrait; 6 7class Test extends Model 8{ 9 use SoftDeletes,CommonTrait { 10 CommonTrait::runSoftDelete insteadof SoftDeletes; 11 } 12~略~ 13} 14

####オーバーライドメソッドを含むtrait

php

1namespace App\Models; 2 3trait CommonTrait 4{ 5 /** 6 * Perform the actual delete query on this model instance. 7 * 8 * @return void 9 */ 10 protected function runSoftDelete() 11 { 12 $query = $this->newModelQuery()->where($this->getKeyName(), $this->getKey()); 13 14 $time = $this->freshTimestamp(); 15 16 $columns = [$this->getDeletedAtColumn() => $this->fromDateTime($time)]; 17 18 $this->{$this->getDeletedAtColumn()} = $time; 19 20 if ($this->timestamps && ! is_null($this->getUpdatedAtColumn())) { 21 $this->{$this->getUpdatedAtColumn()} = $time; 22 23 $columns[$this->getUpdatedAtColumn()] = $this->fromDateTime($time); 24 } 25 //ここから追加*************************** 26 $columns['deleted_by'] = \Auth::user()->id; 27 28 \Log::debug('論理削除', [\Auth::user()->id]); 29 //ここまで追加*************************** 30 31 $query->update($columns); 32 } 33} 34

試したこと

  • フレームワークのコード自体を書き換え

vendor\laravel\framework\src\Illuminate\Database\Eloquent\SoftDeletes.php
を直接書き換えてみる。
→変化なし。(オリジナルの処理がされる)

  • フレームワークのコード自体にシンタックスエラーを埋め込み

vendor\laravel\framework\src\Illuminate\Database\Eloquent\SoftDeletes.phpや
vendor\laravel\framework\src\Illuminate\Database\Eloquent\Model.phpに
シンタックスエラーになるコードを埋め込み。
→エラーになる。

  • フレームワークのコード自体にランタイムエラーを埋め込み

vendor\laravel\framework\src\Illuminate\Database\Eloquent\SoftDeletes.phpや
vendor\laravel\framework\src\Illuminate\Database\Eloquent\Model.phpに
ランタイムエラーになるコードを埋め込み。
→変化なし。(エラーにならず正常に処理される)

  • insteadofを使わずtraitをuse

上記アプリケーションのModelでinsteadofを使わずuse。
→エラーになる。
Trait method runSoftDelete has not been applied, because there are collisions with other trait methods

  • アプリのModelに直接メソッドを記述

上記コードのクラスTest内に、メソッドrunSoftDeleteを記述。
SoftDeletesをuseする際
SoftDeletes::runSoftDeletea runSoftDeleteOriginal
と記述。
→変化なし。(オリジナルの処理がされる)

補足情報(FW/ツールのバージョンなど)

  • phpバージョン

PHP 7.3.5

  • Laravelバージョン

Laravel Framework 5.5.48

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

m.ts10806

2019/09/18 01:40

継承して同名メソッド定義ではだめなんでしょうか
SakuTaka

2019/09/18 01:48

ありがとうございます。”試したこと”に追記しましたが、おっしゃっているのはこういうことでしょうか。
guest

回答1

0

出先なので取り急ぎの回答になりますが

削除時に何か変更を加えたいのであれば
soft deleteをオーバーライドするのではなく
bootからdeletingをフックして対応してはどうでしょうか?
https://qiita.com/maruware/items/8b123d8f170e9ce3bea0

restoreingで復元時の処理もできます

投稿2019/09/18 02:48

mikkame

総合スコア5036

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

SakuTaka

2019/09/18 02:55

ありがとうございます。 その場合はupdateを2回発行することになるのですよね。 ワンタイムで済ませたいと思ったのですが、その方が適正なのでしょうか。 次善の策として考えたいと思います。
mikkame

2019/09/18 03:16

deletingならデリートされる前にモデルへの干渉ができるので発行されるupdate文は1回なはずですよ
mikkame

2019/09/18 07:40

あと経験上 if (auth()->check() {$model->deleted_at = auth()->user()->id} みたいにしないと、管理画面やCLIからの削除ができなくなる気がします。
SakuTaka

2019/10/15 00:51

職場が変わったためお返事大変遅くなり申し訳ありません。機会があれば試してみようと思います。ありがとうございました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだベストアンサーが選ばれていません

会員登録して回答してみよう

アカウントをお持ちの方は

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.36%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問