(PHP7.3)2つ以上のtrait に__contruct() を記載していて、どちらもuseしたclassで呼び出したい
課題:2つ以上のtrait に__contruct() を記載していて、どちらもuseしたclassで呼び出した時に、メソッド名のoverrideがうまくいかない
trait CanUpdateUserInfo {
protected $userService;
public function __construct(UserService $userService) {
$this->userService = $userService;
}
}
trait CanUpdateProductInfo {
protected $productService;
public function __construct(ProductService $productService) {
$this->productService = $productService;
}
}
class UserProductInfoUpdateUseCase {
use CanUpdateUserInfo { __construct as private trait_CanUpdateUserInfo_constructor; }
use CanUpdateProductInfo { __construct as private trait_CanUpdateProductInfo_constructor; }
protected $isForInitialize;
public function __construct(UserService $userService, ProductService $productService, bool $isForInitialize) {
$this->isForInitialize= $isForInitialize;
$this->trait_CanUpdateUserInfo_constructor($userService);
$this->trait_CanUpdateProductInfo_constructor($productService);
}
}
(__costruct() をもつ trait が1つだったときはこれで動いたのですが、、)
このケースでは、
Argument 1 passed to UserProductInfoUpdateUseCase::__construct() must be an instance of ProductService, instance of UserService given
と表示されてしまいました。継承先の__construct と2つのtraitの __constructが衝突するようでした。(stackoverflow には final をつける→なおるという記載がありましたが、私の環境ではうまく動きませんでした。
https://stackoverflow.com/questions/47269922/php-traits-how-to-circumvenient-constructors-or-force-them-to-be-called
)
解決方法:__costuruct() の中での処理を別名で作り直して呼び出す。
trait CanUpdateUserInfo {
protected $userService;
public function __construct(UserService $userService) {
$this->setUpCanUpdateUserInfoTrait($userService);
}
public function setUpCanUpdateUserInfoTrait(UserService $userService) {
$this->userService = $userService;
}
}
trait CanUpdateProductInfo {
protected $productService;
public function __construct(ProductService $productService) {
$this->setUpCanUpdateProductInfoTrait($productService);
}
public function setUpCanUpdateProductInfoTrait(ProductService $productService) {
$this->productService = $productService;
}
}
class UserProductInfoUpdateUseCase {
use CanUpdateUserInfo;
use CanUpdateProductInfo;
protected $isForInitialize;
public function __construct(UserService $userService, ProductService $productService, bool $isForInitialize) {
$this->isForInitialize= $isForInitialize;
$this->setUpCanUpdateUserInfoTrait($userService);
$this->setUpCanUpdateProductInfoTrait($productService);
}
}
これで__construct() の衝突エラーが生じずに 2つの trait の __contruct() を呼ぶ処理を行えます。
(並行方向に処理の共通化がうまくできるのは trait のいいところなのですが、 __construct を 別名でoverride がうまくできればと思ってしまいました。。)
(そもそも trait に __costruct() を入れるのはよろしくないようです。。)
https://qiita.com/hirossyi73/items/1f1864132e9cca3f8208
(construct を いれると IDEがうまく動く、からと言って使うのはよくないのかもしれません、、(construct の別エイリアスでの記載はいつか解決してほしいです。。))
前提条件
php -v
PHP 7.3.2-3+ubuntu18.04.1+deb.sury.org+1 (cli) (built: Feb 8 2019 15:43:57) ( NTS )
Copyright (c) 1997-2018 The PHP Group
Zend Engine v3.3.2, Copyright (c) 1998-2018 Zend Technologies
with Zend OPcache v7.3.2-3+ubuntu18.04.1+deb.sury.org+1, Copyright (c) 1999-2018, by Zend Technologies
with Xdebug v2.7.0RC2, Copyright (c) 2002-2019, by Derick Rethans
with blackfire v1.24.4~linux-x64-non_zts73, https://blackfire.io, by Blackfire
以上です。
Author And Source
この問題について((PHP7.3)2つ以上のtrait に__contruct() を記載していて、どちらもuseしたclassで呼び出したい), 我々は、より多くの情報をここで見つけました https://qiita.com/ttn_tt/items/f7934562584b7cdbc06b著者帰属:元の著者の情報は、元のURLに含まれています。著作権は原作者に属する。
Content is automatically searched and collected through network algorithms . If there is a violation . Please contact us . We will adjust (correct author information ,or delete content ) as soon as possible .