So erkennen Sie dynamisch deklarierte Felder auf Objekten mit Codesniffer in PHP

8

Nach einem Refactoring hatten wir so etwas in einer unserer Klassen:

%Vor%

Am Ende wurde $ this- & gt; foo ['blubb'] also nicht nur einmal gesetzt. Dies geschieht aufgrund der magischen Methoden von PHP. Wir wollen nicht, dass es möglich ist, dynamisch auf Felder zuzugreifen, also dachte ich, ich füge einfach eine Codesniffer-Regel hinzu. Aber ich habe keine gefunden und fragte mich warum.

PHPStorm zeigt ein Feld an, das dort dynamisch gemeldet wird, aber ich möchte, dass dies während des Bereitstellungszyklus automatisch mit Codesniffer (oder ähnlichem) fehlschlägt.

Hat jemand eine Idee dazu? Gibt es eine gute Regel? Soll ich selbst schreiben und wie? Oder wäre es eine schlechte Übung, es zu deaktivieren?

Disclaimer: Wir verwenden Tests, aber manchmal vermisst du Dinge ... Es wäre gut, dies von vornherein zu verhindern. Auch, bitte überlege dir nicht, die magischen Methoden zu überschreiben. Ich möchte in keiner Klasse eine Eigenschaft / Zusammenfassung haben.

    
Kasihasi 13.08.2015, 10:24
quelle

3 Antworten

2

Dies ist kein Codesniffer- oder PHP-Storm-Problem. Und Sie können dieses Problem nicht mit Codesniffer oder IDE beheben. IDE, codesniffer, phpdocumentor usw. - das wird "statisch" analysiert. Und für die dynamische Analyse können Sie z.B. phpunit.

Wenn Sie das Vorhandensein einer Eigenschaft prüfen möchten, müssen Sie die Funktion property_exists () verwenden.

%Vor%

Oder Sie können die Reflektion für die Eigenschaft Ссылка

verwenden

Wenn Sie nach "isset" suchen wollen, müssen Sie wissen:

%Vor%

Wenn Sie sich für diesen Fall der Überprüfung entscheiden, können Sie isset ()

verwenden

Aber Sie sollten immer zuerst nach der Existenz der Eigenschaft suchen. Andernfalls können Sie ein undefiniertes Verhalten Ihres Codes haben.

    
Deep 10.01.2016 15:36
quelle
2
  

Nach einem Refactoring

     

Es wäre gut, dies von vornherein zu verhindern.

Sie können diese Art von Refactoring-Fehlern nur durch Ausführen von Tests nach jedem Refactoring-Schritt erkennen. Dieser Fehler tritt auch auf, weil foo['blubb'] auf einen bestimmten Wert eingestellt ist und dies einen unerwünschten Effekt in einem anderen Test verursachen sollte - nicht nur im Test für die Setter-Logik.

  

Wir verwenden Tests, aber manchmal vermisst du Dinge ...

Ja, es ist ziemlich normal, dass die Abdeckung nicht hoch genug ist. Deshalb ist eine gute Testabdeckung der Ausgangspunkt für alle Refactorings.

Diese beiden Zeilen waren in Ihrem Deckungsbericht nicht "grün":

%Vor%
  

Auch, bitte überlege dir nicht, die magischen Methoden zu überschreiben. Ich möchte in keiner Klasse eine Eigenschaft / Zusammenfassung haben.

Sie haben es ausgeschlossen, aber das ist eine Möglichkeit, die Eigenschaften abzufangen: mit der magischen Funktion __set() (für nicht zugreifbare vars) oder property_exists() oder der Verwendung von Reflection* classes zu finden.

Nun, das ist zu spät, Sie wollen ein anderes Werkzeug, um den Fehler zu fangen, ok:

Das Tool müsste die PHP-Datei und ihre Eltern (aufgrund des Variablenbereichs) analysieren und $this->bla ohne vorherige public|private|protected -Variable (Klasseneigenschaft) -Deklaration finden. Dies zeigt nicht den genauen Fehlertyp an, nur dass auf "bla" ohne Deklaration zugegriffen wurde.

Es ist möglich, dies als CodeSniffer-Regel zu implementieren.

Sie können auch Ссылка oder Ссылка angeben ein Versuch. Und falls Sie PHP7 verwenden: Ссылка

tl; tr

Es ist kompliziert, den genauen Fehler und seinen Kontext zu ermitteln, ohne den zugrunde liegenden Code auszuführen, zu bewerten und zu analysieren. Denken Sie nur an "dynamische Variablennamen" und Sie wissen warum: Sie kennen den Namen der Eigenschaft nicht einmal, indem Sie sich den Quellcode anschauen, da dieser dynamisch während des Programmablaufs erstellt wird. Ein statischer Analysator würde das nicht verstehen.

Ein dynamischer Analysator muss alle Dinge verfolgen, hier $this-> greift zu und würde den Kontext berücksichtigen:! isset (x). Die Kontextauswertung kann viele häufige Programmierfehler finden. Am Ende können Sie einen Bericht erstellen: sagen, dass $ this- & gt; bla wurde nur einmal zugegriffen und das zeigt entweder, dass

  • Eine dynamisch deklarierte Eigenschaft wurde eingeführt, aber nie wieder verwendet, mit dem Vorschlag, sie zu löschen oder als Klasseneigenschaft zu deklarieren
  • ODER mit hinzugefügter Kontextevaluierung: dass und wenn auf diese Variable von innerhalb eines isset () zugegriffen wurde - dass auf einen nicht existierenden Schlüssel einer nicht deklarierten Eigenschaft zugegriffen wurde, ohne vorheriges set (), usw.
Jens A. Koch 13.01.2016 11:37
quelle
1

Jetzt im Jahr 2017 suchen Sie nach Tomáš Votruba 21.05.2017 22:44

quelle