Laravel容器默认是单例吗

wen PHP项目 1

本文目录导读:

Laravel容器默认是单例吗

  1. 默认行为:每次都是新实例
  2. 如何变成单例?
  3. 常见的单例案例

不是默认的

Laravel 的容器(Service Container)在默认情况下,每次通过 app()resolve() 解析一个类时,都会创建一个全新的实例

它只是默认行为,除非你显式地告诉容器要将某个类绑定为单例(Singleton)。


默认行为:每次都是新实例

如果你只是将类绑定到容器,没有额外设置,每次解析都会产生新对象。

示例:

// 在 ServiceProvider 中
$this->app->bind(LoggerInterface::class, function () {
    return new FileLogger();
});
// 在使用时
$logger1 = app(LoggerInterface::class);
$logger2 = app(LoggerInterface::class);
var_dump($logger1 === $logger2); // 输出:false (两个不同的实例)

如何变成单例?

如果你希望容器只创建一次实例,后续都返回同一个,你需要使用 singleton 方法。

示例 1:使用 singleton

$this->app->singleton(LoggerInterface::class, function () {
    return new FileLogger();
});
$logger1 = app(LoggerInterface::class);
$logger2 = app(LoggerInterface::class);
var_dump($logger1 === $logger2); // 输出:true (同一个实例)

示例 2:使用 instance(直接注入已存在的对象)

$logger = new FileLogger();
$this->app->instance(LoggerInterface::class, $logger);
$logger1 = app(LoggerInterface::class);
$logger2 = app(LoggerInterface::class);
var_dump($logger1 === $logger2); // 输出:true

常见的单例案例

Laravel 框架中很多核心服务确实使用了单例模式,但这是框架自己显式注册的,不是容器默认行为。

服务 绑定方式
app (容器本身) 本身就是单例
config 单例
request 单例(在同一个 HTTP 请求生命周期内)
db (数据库连接) 单例(同一个连接复用)
cache 单例
view (视图工厂) 单例
场景 行为
默认 bind() 每次解析返回新实例
显式 singleton() 只创建一次,后续复用
自动注入(无须绑定) 每次解析返回新实例(除非该类本身被定义为单例)
框架核心服务(如 app, config 显式注册为单例

Laravel 容器默认不是单例,只有当你主动使用 singletoninstance 或框架本身显式注册了单例时,它才是单例。

抱歉,评论功能暂时关闭!