[Bug]: Helper phpDocs for date objects should be CarbonInterface|null not Carbon|null
Bug description
When using the helper code generator, it writes the @property for date and datetime cast properties to be Carbon|null, rather than CarbonInterface|null - this means phpstan and other static analysers throw up errors when you're using CarbonImmutable or custom Date classes set via Date::use() extending CarbonInterface
Plugin version
8.1.2.233
Operating system
Windows
Steps to reproduce
use Carbon\Carbon;
use Carbon\CarbonImmutable;
use Carbon\CarbonInterface;
class MyModel extends Model {
protected $fillable = ['date_at'];
protected $casts = ['date_at' => 'datetime'];
public function setDate(CarbonInterface $date) {
$this->date_at = $date;
}
}
$model = new MyModel();
$model->setDate(CarbonImmutable::now());
$model->setDate(Carbon::now());
- Run generate helper code
- Run phpstan (I ran it at level 8, but I think this triggers at 5 onwards)
phpstan: Property App\Models\MyModel::$date_at (Carbon\Carbon|null) does not accept Carbon\CarbonInterface.
This also errors if you force Laravel to use Immutable Dates by default:
use Carbon\CarbonImmutable;
use Illuminate\Support\Facades\Date;
class AppServiceProvider extends ServiceProvider
{
public function boot()
{
Date::use(CarbonImmutable::class);
}
}
Relevant log output
No response
Hello. Laravel Idea analyzes service providers and understands Date::use call. So, it should work.
Interestingly, if I delete the helper code, the types are correct:
Hello. Laravel Idea analyzes service providers and understands Date::use call. So, it should work.
Unfortunately, it does not, if you set it to Carbon it works for Carbon but not CarbonInterface. It does however work if you set it to CarbonImmutable (as in that instance you wouldn't want to accept CarbonInterface)
The generated helper file is missing the \Carbon\CarbonInterface as you can see in example above when I delete the helper files.
Well, if you put Date::use(CarbonInterface::class); to your service provider, it will change all date fields to use CarbonInterface. But it doesn't make sense, right?
We can fix that by setting in the settings "Date class to use". What do you think?
erm... You can't do Date::use(CarbonInterface::class);, it's an interface... Laravel won't be able to instantiate it when creating new models, A concrete implementation is required (at least something that resolves to one, be that a class-string, callback or a factory, all of which are supported, see src/Illuminate/Support/DateFactory.php L122 )
That's why I wrote "But it doesn't make sense, right?")
Well indeed! - more that it's fundamentally not possible, vs not making sense, but tamato, tomato ! :P
We can fix that by setting in the settings "Date class to use". What do you think?
That would be one way to resolve the issue, telling laravel-idea what date model is in use. However, given Date::use() exists, it can be read, if it isn't provided, the default can be assumed (\Carbon\Carbon|\Carbon\CarbonInterface|\Illuminate\Support\Carbon) and retain the normal detection to see if null needs to be added.
Jep, have the same problem...
New setting. I hope it will be enough. The update will be released soon.
10.1 is released.