你们会在__construct 初始化模型嘛?

比如一个控制器A。 这里面的所有方法频繁使用到了数据模型。

你们会在__construct初始化模型吗?
如果在__construct初始化了模型,整个控制器到底是加快了速度 还是减慢了速度?

比如

use App\Http\Models\AModels;
use App\Http\Models\BModels;

class AController extends Controller
{

    protected $AModels;
    protected $BModels;

    public function __construct()
    {
        $this->AModels = new AModels();
        $this->BModels = new BModels();
    }

    public function index()
    {
        ....
         $this->aModels.....
    }
附言 1  ·  4年前

我好想看看你们的写法。
我总觉得自己的想法很低级。
想看看你们使用数据模型的时候是怎么样的。

《L04 微信小程序从零到发布》
从小程序个人账户申请开始,带你一步步进行开发一个微信小程序,直到提交微信控制台上线发布。
《L03 构架 API 服务器》
你将学到如 RESTFul 设计风格、PostMan 的使用、OAuth 流程,JWT 概念及使用 和 API 开发相关的进阶知识。
playmaker
最佳答案
public function __construct(AtmRepository $atm, CardRepository $card)
{
    $this->atm = $atm;
    $this->card = $card;
}
都是按需注入资源
4年前 评论
讨论数量: 23
playmaker
public function __construct(AtmRepository $atm, CardRepository $card)
{
    $this->atm = $atm;
    $this->card = $card;
}
都是按需注入资源
4年前 评论
playmaker
public function __construct(AtmRepository $atm, CardRepository $card)
{
    $this->atm = $atm;
    $this->card = $card;
}
都是按需注入资源
4年前 评论

高内聚、低耦合。除非每个方法都用到,不然不会这样做的。

4年前 评论
LOST

一个控制器里面可能引用多个模型,一般也会有多个方法,但是不是每个方法都需要所有的这些模型,所以在构造函数中就实例化所有模型,并不是很好的一种做法。

4年前 评论

在控制器方法里,,通过类型提示直接注入不好吗,,,还自己手动 new 个鬼哦,,,

4年前 评论
hackxiaoya (楼主) 4年前
hackxiaoya (楼主) 4年前
largezhou (作者) 4年前
hackxiaoya (楼主) 4年前
可乐加冰 4年前
Sunn 4年前
largezhou (作者) 4年前

一般不这么做,一般情况下都是楼上这种的依赖注入……

4年前 评论

我会动态在controller(父类)注入 子类控制器直接$this->model::all();

file

4年前 评论

此种做法亦可以

public function __construct()
{
    $this->atm = app()->make(AtmRepository::class);
    $this->card = app()->make(CardRepository::class);
}
4年前 评论
playmaker

@悲剧不上演 【按需】是说楼主根据自己的实际需求来依赖注入, 跟laravel没关系 不要连累laravel哟 嘻嘻

4年前 评论
悲剧不上演 4年前
playmaker (作者) 4年前

Laravel 是一个注重设计的框架。

new AtmRepository() 在我们看来是一个很平常的操作,但是当你 new 一个实例的时候。就意味着你的 AControllerAtmRepository 两个类强耦合。这就是依赖。
如何解决依赖:Laravel 给我们的解决方案就是 依赖注入。最简单依赖注入的代码就是 new AController(new AtmRepository())

Laravel 中就是如 @vino 代码中所写的。他是通过 IOC 容器,来帮我们实例化 AtmRepository 类的。至于说按需注入资源,我不这么认为。我认为它的效率上并不如楼主写的代码效率快。因为需要通过 IOC 容器来通过反射去实例化 AtmRepository 类的。但是这样做的好处就是解决了依赖。也算是给自己的代码添加了设计的思想 :grin:

public function __construct(AtmRepository $atm, CardRepository $card)
{
    $this->atm = $atm;
    $this->card = $card;
}
4年前 评论

@Complicated
原先我们也写在一起,后来分离了,现在又在想是不是过度设计了 :joy:

4年前 评论
Complicated

@songxue77 学习了!你们分的更细了,我们把Result 和 Service写在一起了

4年前 评论

@Complicated
我们这边后端API用了Laravel,但是还在摸索,代码主要分散在Controller, Result, Service, Model中
Controller主要用于连接路由和商务逻辑,基本没有代码
Result用于验证接收到的参数等等,用Try{}Catch{} 抓取Exception
Service里注入了Model,也就是处理逻辑的中心,各种乱七八糟的代码都写在这里
Model里面就是ORM相关的代码了,主要由Service调用

代码如下,仅供参考

// Controller
class CouponController extends Controller
{
    protected $couponResult;

    public function __construct(couponResult $couponResult)
    {
        $this->couponResult = $couponResult;
    }

    public function addByPin(Request $request)
    {
        return $this->couponResult->addByPin();
    }
}

// Result
class couponResult
{
    protected $addByPinService;

    public function __construct(AddByPinService $addByPinService)
    {
        $this->addByPinService = $addByPinService;
    }

    public function addByPin()
    {
        $memberIdx = request()->route('memberIdx');
        $pinNo = request()->route('pinNo');

        try {
            $result = $this->addByPinService->start($memberIdx, $pinNo);

            $responseResult = Util::responseResult('0000', 'success');
            $responseResult['data'] = $result;

        } catch (ValidationException $e) {
            $responseResult = Util::responseResult('9001', 'validation errors');
        } catch (\Exception $e) {
            $responseResult = Util::responseResult('9003', 'db errors');
        }

        return $responseResult;
    }
}

// Service
class AddByPinService
{
    protected $memberCoupon;

    public function __construct(MemberCoupon $memberCoupon)
    {
        $this->memberCoupon = $memberCoupon;
    }

    public function start($memberIdx, $pinNo)
    {
        $bindingParams = array(
            'MemberIdx' => $memberIdx,
            'PinNo' => $pinNO
        );

        $result = $this->memberCoupon->insertMemberCoupon($bindingParams);

        return $result;
    }
}

// Model
class MemberCoupon extends BaseModel
{
    protected $connection = 'coupon';

    public $timestamps = false;
    public $incrementing = false;

    public function insertMemberCoupon($bindingParams)
    {
        return $this->insertGetId($bindingParams);
    }
}

临时便凑的,可能逻辑不通,能看出思路就好

4年前 评论

如果不想初始化传入就这样

public function __construct(AtmRepository $atm = null, CardRepository $card = null)
{
    $this->atm = $atm ?: new AtmRepository;
    $this->card = $card ?: new CardRepository;
}
4年前 评论
playmaker

@Complicated @songxue77 是的 ,Controller 里就应该保持一个方法 最多执行一句的语法 :joy:

4年前 评论
Complicated

@songxue77 兄台,能贴一丢丢 你的 controller 和 Service 或者 Repository 的代码吗?想看看

4年前 评论

一般是用注入处理,还有一点是我不会在Controller里写Model相关代码,一般写在更下一级的Service或者Repository中。

4年前 评论
____ 4年前
Complicated

以前这么写,但是现在不这么做了!主要是 中间件里面的代码会在controller 的 construct后面执行,会导致一些问题(5.3以后的会这样)! 而且,就算是 在construct里用依赖注入也不是“按需分配”吧,只要new controller,就会new model,区别就是不用自己new了吧

4年前 评论
yema

我一般不喜欢,除非这个模型在这个控制器里的每个action里都用到了。并且在action里是必须用到的。否则我就强迫症犯了,要把他移到该用的地方。

4年前 评论
puzzle9 4年前

不是有 命名空间?要用什么可以use 啊,模型静态调用

4年前 评论
panda-sir

TP5.1好像不支持吧 并没有用到反射类来解析类的构造方法 :joy:

4年前 评论

单例一般不这样处理

4年前 评论

不会。都是model直接写

User::query()->where([])->paginate();
User::create([]);
user::where('id', $id)->update([]);

增删改查都是

4年前 评论
playmaker 4年前
puzzle9 4年前
aen233 (作者) 4年前
playmaker 4年前
mokeyjay 4年前

一般注入manager,而且这些速度快慢都不是事

4年前 评论

讨论应以学习和精进为目的。请勿发布不友善或者负能量的内容,与人为善,比聪明更重要!