Php Laravel:目标在构建时不可实例化
抱歉,如果该问题重复,但我在StackOverflow中阅读了很多相关问题,但没有一个解决了我的问题: 我创建了一个Artisan命令,该命令起作用,其中我注入了一个Kafka客户端服务作为第一个参数,注入了一个具体类BudgetTransformer作为第二个参数Php Laravel:目标在构建时不可实例化,php,laravel,laravel-artisan,service-provider,Php,Laravel,Laravel Artisan,Service Provider,抱歉,如果该问题重复,但我在StackOverflow中阅读了很多相关问题,但没有一个解决了我的问题: 我创建了一个Artisan命令,该命令起作用,其中我注入了一个Kafka客户端服务作为第一个参数,注入了一个具体类BudgetTransformer作为第二个参数 class ConsumeBudgetsCommand extends Command { public function __construct(FKafka $kafkaClient, BudgetsTransforme
class ConsumeBudgetsCommand extends Command {
public function __construct(FKafka $kafkaClient, BudgetsTransformer $transformer)
{
$this->kafkaClient = $kafkaClient;
$this->transformer = $transformer;
parent::__construct();
}
}
AppServiceProvider类看起来像:
class AppServiceProvider extends ServiceProvider
{
public function register()
{
$this->app->bind('kafka.client', function ($app) {
return new \Weq\FKafka\FKafka();
});
$this->app->bind('budget.transformer', function ($app) {
return new BudgetsTransformer();
});
}
public function boot()
{
$this->app->bind('consume:budgets', function ($app) {
return new ConsumeBudgetsCommand($app['kafka.client'], $app['budget.transformer']);
});
$this->commands('consume:budgets');
}
}
到目前为止一切正常。。。然后我决定创建一个Transformer接口
,由预算变压器
实现(其他未来变压器将实现它):
我更改了命令中的签名以注入接口,而不是具体类:
class ConsumeBudgetsCommand extends Command {
public function __construct(FKafka $kafkaClient, TransformerInterface $transformer)
{
$this->kafkaClient = $kafkaClient;
$this->transformer = $transformer;
parent::__construct();
}
}
但是,当我尝试运行一些artisan
命令时,会遇到以下问题
在Container.php第933行中:
生成[App\Console\Commands\ConsumerBudgetCommand]时,目标[App\Transformers\TransformerInterface]不可实例化
我之前运行了以下artisan命令,以防<代码>缓存:清除,清除编译的
,优化
等等,但没有运气
我做错了什么?我应该用我现在正在做的另一种方式绑定BudgetTransformer
来传递和接口,而不是具体的类吗
提前谢谢你的帮助
更新
正如@davit所建议的,我补充道
$this->app->bind(TransformerInterface::class, BudgetsTransformer::class);
在AppServiceProvider::register()中,我已删除
$this->app->bind('budget.transformer', function ($app) {
return new BudgetsTransformer();
});
然后,我在AppServiceProvider::boot()中更新命令绑定:
$this->app->bind('consume:budgets', function ($app) {
return new ConsumeBudgetsCommand($app['kafka.client'], $app[TransformerInterface::class]);
});
但仍然不起作用,无论如何,这种方法(即使起作用)也无法解决问题,因为当我想添加另一个不同的transformer实现时,比如说CostTransformer
,它实现了TransformerInterface
将始终注入BudgetTransformer
。因此,在阅读链接中的文档时,我发现上下文绑定
可能是解决方案,因此我选择了:
$this->app
->when(ConsumeBudgetsCommand::class)
->needs(TransformerInterface::class)
->give(function ($app) {
return new BudgetsTransformer();
});
这样,我就可以通过注入接口,将变压器的不同实现注入到不同的命令中。但仍然不起作用
有人能告诉我如何准确地声明命令绑定吗
$this->app->bind('consume:budgets', function ($app) {
return new ConsumeBudgetsCommand($app['kafka.client'], ???);
});
要为绑定接口使用
上下文绑定
?,必须使用此结构
及
对于绑定接口,必须使用此结构 及
您不需要任何
$this->app->bind(…
因为你的应用程序不使用它们中的任何一个来创建ConsumerBudgetCommand
对象。你只需要将TransformerInterface
绑定到BudgetTransformer
,这样应用程序就知道在执行命令时注入它。你不需要任何$this->app->bind(…
因为你的应用程序没有使用任何一个来创建ConsumerBudgetCommand
对象。你只需要将TransformerInterface
绑定到BudgetTransformer
,这样应用程序就会知道在执行命令时注入它。@Averias你在尝试吗?是的@Davit,我尝试过,请阅读我的u与前面一样更新上述问题:在生成[App\Console\Commands\ConsumerBudgetCommand]时,目标[App\Transformers\TransformerInterface]不可实例化。为什么尝试绑定?laravel必须自动绑定它。您是否在命令保护的$signature='consume:budgets'中使用?;我想绑定该命令,因为我正在注入Kafka服务(作为命令中的第一个参数)。无论如何,甚至删除命令的绑定:$this->app->bind('consume:budgets',..以及命令声明:$this->commands('consume:budgets');它不起作用(相同的错误),说实话,我想知道如何使用这两个绑定,因为这可能是我不久将要面对的一个用例future@Averias你尝试过这个吗?是的@Davit,我尝试过,请阅读我关于上述问题的更新,与之前一样:目标[App\Transformers\TransformerInterface]在构建时不可实例化[App\Console\Commands\ConsumerBudgetCommand]。为什么尝试绑定??laravel必须自动绑定它。您是否在命令保护的$signature='Consumer:budgets'中使用?;我想绑定该命令,因为我正在注入Kafka服务(作为命令中的第一个参数)。无论如何,即使删除该命令的绑定:$this->App->bind('consume:budgets',…以及命令声明:$this->commands('consume:budgets');它不起作用(相同的错误),老实说,我想知道如何使用这两个绑定,因为这可能是我在不久的将来将要面对的一个用例
$this->app->bind('consume:budgets', function ($app) {
return new ConsumeBudgetsCommand($app['kafka.client'], ???);
});
$this->app->bind(TransformerInterface::class, BudgetsTransformer::class);
$this->app->bind('consume:budgets', function ($app) {
return new ConsumeBudgetsCommand($app['kafka.client'], $app->make(TransformerInterface::class));
});