我想我可能已经找到了一个代码的怪癖,它允许静态调用Laravel Eloquent模型方法,但可以提供一些帮助。
我有一个名为FormSubmission
的模型,它扩展了Eloquent\Model
。
namespace App;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Support\Collection;
class FormSubmission extends Model
{
/**
* Should always return a Collection of FormSubmissions
*
* @param $formSubmissionIds
*
* @return Collection
*/
protected function getFormSubmissions(array $formSubmissionIds) : Collection
{
return FormSubmission::whereIn('id', $formSubmissionIds)->get();
}
}
我需要一个地方来放置一些仅对1种FormSubmission唯一的逻辑。由于它与所有表单无关,因此我不想污染FormSubmission
模型,因此我将EmployeeFormSubmission
扩展为FormSubmission
。
namespace App;
class EmployeeFormSubmission extends FormSubmission
{
/**
*
*/
public function getTest()
{
$employeeFormSubmission = new EmployeeFormSubmission();
// The resulting Collection will contain instances
// of EmployeeFormSubmission (not FormSubmission).
return $employeeFormSubmission->getFormSubmissions([86]);
}
}
雄辩模型 - >通过 FormSubmission 扩展 - >由 EmployeeFormSubmission
扩展问题......
我无法理解的奇怪行为是,如果我在whereIn()
内FormSubmission
上调用EmployeeFormSubmission
方法,就像上面的getTest()示例中那样,生成的集合将会包含EmployeeFormSubmission
的实例,即使我在whereIn()
模型上明确调用FormSubmission
方法。
如果我使用parent::whereIn()
但是,如果我将FormSubmission::getFormSubmissions()
方法更改为公共静态,它将按预期工作并返回FormSubmission
实例的集合。
就像在FormSubmission
上的非静态方法中,Laravel / PHP将“FormSubmission ::”替换为“self ::”。
当非静态时,它会继续执行代码的上下文,并在该类的实例中初始化项目。但是当静态时,它会尊重代码行中引用的模型名称。
请帮助我有点难过。
答案 0 :(得分:1)
原因是调用未定义的静态方法(如FormSubmission::whereIn()
)不会由__callStatic()
处理,而是由__call()
(PHP is handling incorrectly my static call)处理。
这有效:
return FormSubmission::query()->whereIn('id', $formSubmissionIds)->get();