Pour assurer une revue continue du code PHP, il faut deux outils : une référence de programmation, avec des recommendations claires et adaptées. Celle-ci peut se constituer aisément à partir des recommandations du manuel officiel, des bonnes pratiques et des traditions PHP. L'autre outil est un auditeur statique, qui repasse chaque ligne au peigne fin et traque inlassablement ce qui doit être amélioré. Nous verrons comment ils fonctionnent ensemble, et jusqu'où ils peuvent mener votre code sur le chemin de la qualité.
3. Un projet à relire
On ne sait pas ce que ca fait
On ne l'a jamais vu
On ne l'execute pas
On ne connait pas ses auteurs
Peut-on se former une opinion ?
4. Comment relire du code?
Relire est humainement possible et artisanal
Les tests unitaires sont peu adaptés à la relecture
L'analyse dynamique est peu adaptée à la relecture
Il faut explorer le code
ne pas se contenter des situations actuelles
9. Checked 5982 files in 28.4 seconds
Syntax error found in 4 files
------------------------------------------------------------
Parse error: /vendor2/symfony/symfony/src/Symfony/Component/Validator/Constraints/False.php:22
20| * @api
21| */
> 22| class False extends IsFalse
23| {
24| }
Fatal error: Cannot use 'False' as class name as it is reserved
------------------------------------------------------------
Parse error: /vendor2/symfony/symfony/src/Symfony/Component/Validator/Constraints/Null.php:22
20| * @api
21| */
> 22| class Null extends IsNull
23| {
24| }
Fatal error: Cannot use 'Null' as class name as it is reserved
------------------------------------------------------------
Parse error: /vendor2/symfony/symfony/src/Symfony/Component/Validator/Constraints/True.php:22
20| * @api
21| */
> 22| class True extends IsTrue
23| {
24| }
Fatal error: Cannot use 'True' as class name as it is reserved
------------------------------------------------------------
Parse error: /vendor_user/windid_client/src/windid/service/base/WindidUtility.php:93
91| $imageInfo = @getimagesize($file);
92| $exts = array('1'=>'gif', '2'=>'jpg', '3'=>'png');
> 93| if (!isset($exts[$imageInfo[2]])) continue;
94| $ext = $exts[$imageInfo[2]];
95| $filename = rand(1000,9999). '.'.$ext;
Fatal error: 'continue' not
PHP LINT - 7.0/1/2
10. Checked 5982 files in 29.7 seconds
Syntax error found in 1 file
------------------------------------------------------------
Parse error: /vendor2/mockery/mockery/tests/Mockery/MockingVariadicArgumentsTest.php
50| abstract class TestWithVariadicArguments
51| {
> 52| public function foo(...$bar)
53| {
54| return $bar;
Unexpected '.', expecting '&' or variable (T_VARIABLE)
PHP LINT - 5.5
PHP LINT - 5.6
Checked 5982 files in 31 seconds
No syntax error found
11. PHP LINT
Pas compatible avec PHP 7.0 +
Pas compatible avec PHP 5.5-
Utilise Symfony
@getimagesize ? vendor2 ?
5982 fichiers
12. Calcul de métriques
PHPloc, PHPmetrics, PHP MD
Donne des notes d'ensemble au code
Complexité cyclomatique, nombre de LOC…
13. PHPLOCDirectories 1143
Files 5982
Size
Lines of Code (LOC) 835199
Comment Lines of Code (CLOC) 252075 (30.18%)
Non-Comment Lines of Code (NCLOC) 583124 (69.82%)
Logical Lines of Code (LLOC) 195283 (23.38%)
Classes 178062 (91.18%)
Average Class Length 29
Minimum Class Length 0
Maximum Class Length 3141
Average Method Length 4
Minimum Method Length 0
Maximum Method Length 879
Functions 1477 (0.76%)
Average Function Length 1
Not in classes or functions 15744 (8.06%)
Cyclomatic Complexity
Average Complexity per LLOC 0.30
Average Complexity per Class 10.82
Minimum Class Complexity 1.00
Maximum Class Complexity 1177.00
Average Complexity per Method 2.65
Minimum Method Complexity 1.00
Maximum Method Complexity 387.00
[...]
17. Revue de code automatisée
Relecture du code par une application
regex relit PHP
Extraction de points intéressants
Fonctionnement par mots clé
PHP7cc
18. php7cc
File: /vendor_user/windid_client/wind/convert/WindGeneralConverter.php
> Line 33: PHP 4 constructors are now deprecated
public function WindGeneralConverter($sourceLang = '', $targetLang = '', $forceTable = false)
{
}
File: /vendor2/symfony/symfony/src/Symfony/Component/Validator/Constraints/Null.php
> Line 22: Reserved name "null" used as a class, interface or trait name
class Null extends SymfonyComponentValidatorConstraintsIsNull
{
}
File: /vendor_user/windid_client/wind/filter/WindHandlerInterceptorChain.php
> Line 61: Function argument(s) returned by "func_get_args" might have been modified
func_get_args();
File: /vendor_user/windid_client/wind/http/session/handler/WindSessionHandler.php
> Line 156: Check that callbacks that are passed to "session_set_save_handler" and return false or -1 (if any) operate
correctly
session_set_save_handler(array($this, 'open'), array($this, 'close'), array($this, 'read'), array($this, 'write'),
array($this, 'destroy'), array($this, 'gc'));
File: /vendor_user/windid_client/wind/security/WindMcryptCbc.php
> Line 31: Removed function "mcrypt_cbc" called
mcrypt_cbc(MCRYPT_DES, $key, $string, MCRYPT_ENCRYPT, $iv);
> Line 49: Removed function "mcrypt_cbc" called
mcrypt_cbc(MCRYPT_DES, $key, $string, MCRYPT_DECRYPT, $iv);
Total : 83 rapports
23. Sémantique et définitions
PHP7mar : nikic/php5-ast
PHAN : ext/ast (PHP 7 only)
Exakat : AST en base de données
SonarQube : AST maison
PHPstorm : AST interne à l'IDE
24. Sémantique et définitions
Suppression espaces, commentaires, documentations
Suppression des délimiteurs
( ) { } [ ] " ' ` ; :
Capacité à relier définitions et usage
25. PHAN
src/Org/OrgBundle/Controller/OrgController.php:12
PhanTypeMismatchArgument Argument 1 (data) is bool but OrgOrgBundleControllerOrgController::createJsonResponse() takes
array defined at src/Topxia/WebBundle/Controller/BaseController.php:120
Total : 13315 résultats
1235 issues
vendor_user/windid_client/wind/mail/protocol/WindPop3.php:186
PhanUndeclaredTypeParameter Parameter of undeclared type baoolean
276 issues
vendor_user/windid_client/wind/base/WindFactory.php:325
PhanTypeArraySuspicious Suspicious array access to bool
184 issues
vendor2/imagine/imagine/lib/Imagine/Image/AbstractLayers.php:49
PhanParamSignatureMismatch Declaration of function get($offset) should be compatible with function get(int $offset) :
ImagineImageImageInterface defined in vendor2/imagine/imagine/lib/Imagine/Image/LayersInterface.php:97
src/Classroom/ClassroomBundle/Controller/ClassroomAdminController.php:84
PhanUndeclaredMethod Call to undeclared method ClassroomClassroomBundleController
ClassroomAdminController::createErrorResponse
1919 issues
808 issues
34. Et PHP dans tout ça?
La majorité des analyses portent sur des concepts
informatiques
Il existe des analyses qui portent sur PHP lui-même
Les pratiques courantes
Les spécificités du langage
39. Et mon application ?
Découvrez les inventaires
Liste des valeurs utilisées dans le code
Liste des entiers, décimaux, chaines, tableaux
Liste de noms de classes, interfaces, variables,
méthodes
43. Les comparaisons
none 9
vip 10
.. 10
yes 10
material 11
coin 11
created 11
teacher 12
closed 12
error 13
1 14
RMB 15
0 16
paid 16
lesson 18
liveOpen 19
trend 19
cloud 19
ok 20
Coin 21
classroom 22
video 25
self 25
testpaper 27
success 32
live 32
course 39
published 43
_empty_ 71
POST 237
Chaines utilisées dans une
comparaison
$a == 'ok'
On compte juste les b
44. Pour aller plus loin
Deptrac
Vérifie que les classes restent bien dans leurs
couches
Deptrac traque les dépendances entre classes qui
doivent rester indépendantes
Configuré manuellement
45. Pour aller plus loin
Le code dynamique
40% du code est en fait statique
Transpilage : https://github.com/jaytaph/Transphpile
PHP inspections : Intégrées à l'éditeur phpStorm
sensio labs insight : SCA pour le framework
Intégrer l'analyse statique dans son IC
46. Liste des SCAP cités
Deptrac
Exakat
PHP7mar
Phan
PHP Inspections
Phploc
PHPMD
PHP 7 cc
PHPmetrics
RIPS
Transphpile