Quelles sont les différences entre PSR-0 et PSR-4?

225

Récemment, j'ai lu sur les espaces de noms et leurs avantages. Je suis en train de créer un projet dans Laravel et j'essaie de passer du chargement automatique de la carte de classe à l'espace de noms. Cependant, je n'arrive pas à comprendre quelle est la différence réelle entre PSR-0 et PSR-4.

Certaines ressources que j'ai lues sont ...

Ce que je comprends:

  • PSR-4 ne convertit pas les traits de soulignement en séparateurs de répertoires
  • Certaines règles spécifiques du compositeur rendent la structure de répertoires complexe, ce qui rend verbeux l'espace de noms PSR-0 et donc le PSR-4 a été créé

Des exemples expliquant la différence seraient appréciés.

Varun Nath
la source
3
Lisez PSR0 et PSR4 . Ils expliquent chaque détail.
Sverri M. Olsen
4
☝️ Quelqu'un devrait saisir l'essentiel de ceci comme réponse ... :)
décompresser
1
OMI, la plupart des parties du PSR concernent ce qu'ils AIMENT pas ce qui est DROIT ...
Yousha Aleayoub

Réponses:

283

Ils sont très similaires, il n'est donc pas surprenant que ce soit un peu déroutant. Le résumé est que PSR-0 avait des fonctionnalités de compatibilité descendante pour les noms de classe de style PEAR que PSR-4 a supprimés, en tant que tel, il ne prend en charge que le code à espace de noms. En plus de cela, PSR-4 ne vous oblige pas à avoir tout l'espace de noms en tant que structure de répertoire, mais uniquement la partie suivant le point d'ancrage.

Par exemple, si vous définissez que l' Acme\Foo\espace de noms est ancré src/, avec PSR-0, cela signifie qu'il cherchera Acme\Foo\Bardans src/Acme/Foo/Bar.phptandis que dans PSR-4, il le recherchera src/Bar.php, permettant des structures de répertoire plus courtes. D'un autre côté, certains préfèrent avoir la structure de répertoires complète pour voir clairement dans quel espace de noms, vous pouvez donc également dire que Acme\Foo\c'est src/Acme/Fooavec PSR-4 qui vous donnera l'équivalent du comportement PSR-0 décrit ci-dessus.

Pour faire court pour de nouveaux projets et pour la plupart des intentions, vous pouvez utiliser PSR-4 et oublier tout sur PSR-0.

Seldaek
la source
17
Il choisit src/Bar.phpsi vous ditesAcme\Foo\ => src/
Seldaek
Merci beaucoup pour l'éxplication!
尤川豪
4
Le PSR-4 est plus lent que le PSR-0, n'est-ce pas?
Nguyen Linh
2
@NguyenLinh Je ne pense pas. Il fait la même chose, mais peut-être avec moins de niveaux de répertoires, donc cela pourrait être un peu plus rapide. Mesure le. Vous pouvez créer un package que vous pouvez basculer entre PSR-0 et PSR-4 - je ne pense pas que vous verrez une différence.
Sven
44

Voici les principales différences,

1. Par exemple, si vous définissez que l' Acme\Foo\espace de noms est ancré src/,

  • avec PSR-0, cela signifie qu'il cherchera Acme\Foo\Bardanssrc/Acme/Foo/Bar.php
  • tandis que dans PSR-4 il va chercher Acme\Foo\Bardans src/Bar.php(where Bar class is).

2. PSR-4 ne convertit pas les traits de soulignement en séparateurs de répertoires

3. Vous préférez utiliser PSR-4 avec des espaces de noms

4. PSR-0 ne fonctionnera pas même si le nom de classe est différent du nom de fichier, comme en considérant l'exemple ci-dessus:

  • Acme\Foo\Bar ---> src/Acme/Foo/Bar.php (pour la classe Bar) fonctionnera
  • Acme\Foo\Bar ---> src/Acme/Foo/Bar2.php(pour la classe Bar) ne fonctionnera pas
Adil Abbasi
la source
1
Vous pouvez certainement utiliser PSR-4 sans aucun script d'espace de noms, il n'y a pas une telle restriction et je l'utilise (pas mon choix)
Galvani
Dans votre 1. (premier point) d'où vient Bar pour le cas PSR-4?
cjmling
31

PSR-4 est quelque chose comme «chemin relatif», PSR-0, «chemin absolu».

par exemple

config:

'App\Controller' => 'dir/'

Chargement automatique PSR-0 :

App\Controller\IndexController --> dir/App/Controller/IndexController.php

Chargement automatique PSR-4 :

App\Controller\IndexController --> dir/IndexController.php

Et il y a encore plus de différence dans les détails entre PSR-0 et PSR-4, voir ici: http://www.php-fig.org/psr/psr-4/

wbswjc
la source
10

Convention d'espace de noms / dossier.

Les classes doivent être stockées dans des dossiers en fonction de leurs espaces de noms.

En général, vous allez créer un répertoire src / dans votre dossier racine, assis au même niveau que vendeur /, et y ajouter vos projets. Voici un exemple de la structure des dossiers:

.
+-- src
    |
    +-- Book 
    |   +-- History
    |   |   +-- UnitedStates.php - namespace Book\History;
    +-- Vehicle
    |   +-- Air
    |   |   +-- Wings
    |   |   |   +-- Airplane.php - namespace Vehicle\Air\Wings;
    |   +-- Road
    |   |   +-- Car.php - namespace Vehicle\Road;
+-- tests
    +-- test.php
+-- vendor

Différence entre psr-0 et psr-4

psr-0

Il est obsolète. En regardant le vendor/composer/autoload_namespaces.phpfichier, vous pouvez voir les espaces de noms et les répertoires auxquels ils sont mappés.

composer.json

"autoload": {
        "psr-0": {
            "Book\\": "src/",
            "Vehicle\\": "src/"
        }
} 
  • Recherche de Book \ History \ UnitedStates dans src / Book /History/UnitedStates.php
  • Vous cherchez un véhicule \ Air \ Wings \ Airplane dans src / Vehicle /Air/Wings/Airplane.php

psr-4

En regardant le vendor/composer/autoload_psr4.phpfichier, vous pouvez voir les espaces de noms et les répertoires auxquels ils sont mappés.

composer.json

"autoload": {
    "psr-4": {
        "Book\\": "src/",
        "Vehicle\\": "src/"
    }
}   
  • Recherche de Book \ History \ UnitedStates dans src /History/UnitedStates.php
  • Vous cherchez un véhicule \ Air \ Wings \ Airplane dans src /Air/Wings/Airplane.php

composer.json

"autoload": {
    "psr-4": {
        "Book\\": "src/Book/",
        "Vehicle\\": "src/Vehicle/"
    }
}    
  • Recherche de Book \ History \ UnitedStates src / Book /History/UnitedStates.php
  • Vous cherchez un véhicule \ Air \ Wings \ Airplane dans src / Vehicle /Air/Wings/Airplane.php
Udhav Sarvaiya
la source
-4

Même quand j'ai essayé mais Composer est un gâchis. Malheureusement, c'est la seule alternative du marché.
Pourquoi est-ce un gâchis?.
La saisie semi-automatique du compositeur fonctionne correctement si vous contrôlez le code. Cependant, si vous importez un autre projet, vous vous retrouvez avec de nombreux styles et façons de créer des dossiers. Par exemple, certains projets sont /company/src/class.php tandis que d'autres sont company / class.php et d'autres sont company / src / class / class.php

J'ai créé une bibliothèque qui le résout:

https://github.com/EFTEC/AutoLoadOne (c'est gratuit, MIT).

Il génère une auto-inclusion en analysant toutes les classes d'un dossier, il fonctionne donc dans tous les cas (psr-0 psr-4, classes sans espace de noms, fichier avec plusieurs classes ..

edit: Et encore, a voté sans aucune raison. ;-)

magallanes
la source
Renseignez-vous sur l'option classmap dans composer.json. getcomposer.org/doc/04-schema.md#classmap - pourrait être la raison du vote négatif de votre réponse.
Patrick