Diagnostics¶
missing_method
¶
Report if trying to call a class method which does not exist.
<?php
class Foobar
{
}
$f = new Foobar();
$f->bar();
Diagnostic(s):
ERROR
:Method "bar" does not exist on class "Foobar"
<?php
class Foobar
{
}
Foobar::bar();
Diagnostic(s):
ERROR
:Method "bar" does not exist on class "Foobar"
docblock_missing_return
¶
Report when a method has a return type should be augmented by a docblock tag
<?php
class Foobar
{
public function foo() {
return 'foobar';
}
}
Diagnostic(s):
WARN
:Method "foo" is missing docblock return type: string
docblock_missing_param
¶
Report when a method has a parameter with a type that should be augmented by a docblock tag.
<?php
class Foobar
{
public function foo(Closure $foobar) {
}
}
Diagnostic(s):
WARN
:Method "foo" is missing @param $foobar
<?php
/**
* @template TKey
* @template TValue of string
*/
class Generator {
}
class Foobar
{
public function foo(Generator $foobar) {
}
}
Diagnostic(s):
WARN
:Method "foo" is missing @param $foobar
<?php
class Foobar
{
public function foo(array $foobar) {
}
}
Diagnostic(s):
WARN
:Method "foo" is missing @param $foobar
assignment_to_missing_property
¶
Report when assigning to a missing property definition.
<?php
class Foobar {
public function baz(){
$this->bar = 'foo';
}
}
Diagnostic(s):
WARN
:Property "bar" has not been defined
missing_return_type
¶
Report if a method is missing a return type.
<?php
class Foobar {
public function foo()
{
return 'string';
}
}
Diagnostic(s):
WARN
:Missing return type `string`
<?php
class Foobar {
public function foo()
{
return foo();
}
}
function foo() {
}
Diagnostic(s):
WARN
:Method "foo" is missing return type and the type could not be determined
unresolvable_name
¶
Report if a name (class, function, constant etc) can not be resolved.
<?php
function foo(string $name)
}
foo(Foobar::class);
Diagnostic(s):
ERROR
:Class "Foobar" not found
<?php
class RpcCommand
{
public function __construct(
$inputStream = Foo::BAR
) {
}
}
Diagnostic(s):
ERROR
:Class "Foo" not found
<?php
foobar();
Diagnostic(s):
ERROR
:Function "foobar" not found
<?php
namespace Foo;
if ($f instanceof Foobar) {
}
Diagnostic(s):
ERROR
:Class "Foobar" not found
<?php
Foobar::class;
Diagnostic(s):
ERROR
:Class "Foobar" not found
<?php
namespace Foo;
foobar();
Diagnostic(s):
ERROR
:Function "foobar" not found
unused_import
¶
Report if a use statement is not required.
<?php
use Foobar as Barfoo;
use Bagggg as Bazgar;
new Barfoo();
Diagnostic(s):
WARN
:Name "Bazgar" is imported but not used
<?php
namespace One {
use Foo;
}
namespace Two {
new Foo();
}
Diagnostic(s):
WARN
:Name "Foo" is imported but not used
<?php
use Foobar\{Barfoo};
new Foobar();
Diagnostic(s):
WARN
:Name "Barfoo" is imported but not used
<?php
namespace Foo;
use Bar\Foobar;
use Bag\Boo;
new Boo();
Diagnostic(s):
WARN
:Name "Foobar" is imported but not used
<?php
use Foobar;
Diagnostic(s):
WARN
:Name "Foobar" is imported but not used
deprecated usage
¶
Report when a deprecated symbol (class, method, constant, function etc) is used.
<?php
/** @deprecated */
class Deprecated {
public static foo(): void {}
}
class NotDeprecated {
public static foo(): void {}
}
$fo = new Deprecated();
Deprecated::foo();
new NotDeprecated();
Diagnostic(s):
WARN
:Call to deprecated class "Deprecated"
WARN
:Call to deprecated class "Deprecated"
<?php
class Foobar
{
/** @deprecated This is deprecated */
const FOO = 'BAR';
const BAR = 'BAR';
public function foo(Closure $foobar) {
$fo = self::FOO;
$ba = self::BAR;
}
}
Diagnostic(s):
WARN
:Call to deprecated constant "FOO": This is deprecated
<?php
/** @deprecated */
enum Deprecated {
case FOO;
}
enum NotDeprecated {
case BAR;
}
$fo = Deprecated::FOO();
Deprecated::foo();
new NotDeprecated();
Diagnostic(s):
WARN
:Call to deprecated enum "Deprecated"
WARN
:Call to deprecated enum "Deprecated"
<?php
/** @deprecated */
function bar(): void {}
function notDeprecated(): void {}
bar();
notDeprecated();
Diagnostic(s):
WARN
:Call to deprecated function "bar"
<?php
class Foobar
{
public function foo(Closure $foobar) {
$this->deprecated();
$this->notDeprecated();
}
/** @deprecated This is deprecated */
public function deprecated(): void {}
public function notDeprecated(): void {}
}
Diagnostic(s):
WARN
:Call to deprecated method "deprecated": This is deprecated
<?php
trait FoobarTrait {
/** @deprecated This is deprecated */
public function deprecated(): void {}
}
class Foobar
{
use FoobarTrait;
public function foo(Closure $foobar) {
$this->deprecated();
$this->notDeprecated();
}
public function notDeprecated(): void {}
}
Diagnostic(s):
WARN
:Call to deprecated method "deprecated": This is deprecated
<?php
class Foobar
{
/** @deprecated This is deprecated */
public string $deprecated;
public string $notDeprecated;
public function foo(Closure $foobar) {
$fo = $this->deprecated;
$ba = $this->notDeprecated;
}
}
Diagnostic(s):
WARN
:Call to deprecated property "deprecated": This is deprecated
undefined_variable
¶
Report if a variable is undefined and suggest variables with similar names.
<?php
$zebra = 'one';
$foa = 'two';
if ($foo) {
}
Diagnostic(s):
ERROR
:Undefined variable "$foo", did you mean "$foa"
<?php
$foz = 'one';
$foa = 'two';
$fob = 'three';
if ($foo) {
}
Diagnostic(s):
ERROR
:Undefined variable "$foo", did you mean one of "$foz", "$foa", "$fob"
<?php
if ($foa) {
}
Diagnostic(s):
ERROR
:Undefined variable "$foa"
<?php
$plainArray = [];
$list = [];
foreach ($plainArray as $index => $data) {
$list[$index] = $data;
}
return $list;
docblock_missing_extends_tag
¶
Report when a class extends a generic class but does not provide an @extends tag.
<?php
/**
* @template T
*/
class NeedGeneric
{
}
class Foobar extends NeedGeneric
{
}
Diagnostic(s):
WARN
:Missing generic tag `@extends NeedGeneric<mixed>`
<?php
/**
* @template T
* @template P
*/
class NeedGeneric
{
}
/**
* @extends NeedGeneric<int>
*/
class Foobar extends NeedGeneric
{
}
Diagnostic(s):
WARN
:Generic tag `@extends NeedGeneric<int>` should be compatible with `@extends NeedGeneric<mixed,mixed>`
<?php
/**
* @template T of int
*/
class NeedGeneric
{
}
/**
* @extends NeedGeneric
*/
class Foobar extends NeedGeneric
{
}
Diagnostic(s):
WARN
:Generic tag `@extends NeedGeneric` should be compatible with `@extends NeedGeneric<int>`
<?php
/**
* @template T of int
*/
class NeedGeneric
{
}
/**
* @extends NeedGeneric<>
*/
class Foobar extends NeedGeneric
{
}
Diagnostic(s):
WARN
:Missing generic tag `@extends NeedGeneric<int>`
<?php
/**
* @template T of int
*/
class NeedGeneric
{
}
/**
* @extends NeedGeneic<int>
*/
class Foobar extends NeedGeneric
{
}
Diagnostic(s):
WARN
:Missing generic tag `@extends NeedGeneric<int>`
<?php
/**
* @template T
* @template P
* @template Q
*/
class NeedGeneric
{
}
/**
* @extends NeedGeneric<int>
*/
class Foobar extends NeedGeneric
{
}
Diagnostic(s):
WARN
:Generic tag `@extends NeedGeneric<int>` should be compatible with `@extends NeedGeneric<mixed,mixed,mixed>`
docblock_missing_implements_tag
¶
Report when a class extends a generic class but does not provide an @extends tag.
<?php
/**
* @template T
*/
interface NeedGeneric
{
}
class Foobar implements NeedGeneric
{
}
Diagnostic(s):
WARN
:Missing generic tag `@implements NeedGeneric<mixed>`
<?php
/**
* @template T
* @template P
*/
interface NeedGeneric
{
}
/**
* @implements NeedGeneric<int>
*/
class Foobar implements NeedGeneric
{
}
Diagnostic(s):
WARN
:Generic tag `@implements NeedGeneric<int>` should be compatible with `@implements NeedGeneric<mixed,mixed>`
<?php
/**
* @template T
*/
interface NeedGeneric1
{
}
/**
* @template T
*/
interface NeedGeneric2
{
}
/**
* @implements NeedGeneric1<int>
*/
class Foobar implements NeedGeneric1, NeedGeneric2
{
}
Diagnostic(s):
WARN
:Missing generic tag `@implements NeedGeneric2<mixed>`