D’abord « Sensio Framework », la première version de Symfony sort en 2007.
Il s’agit d’un Framework PHP structuré sur le design pattern MVC et comporte de nombreux composants.
Symfony est considéré à la fois comme un Framework MVC (Modèle Vue Controller, architecture de projet très répandu dans le monde logiciel/web) et un ensemble de composant utiles, dont voici les principales briques :
- twig : Un moteur de template html permettant une syntaxe spécifique pour créer/construire des page web permettant notamment du data binding, des filtres à base de pipe, des structures conditionnels/itératives, etc.
- Doctrine : Un ORM, Object-Relationnal Mapping, permettant la création, l’utilisation et la mise à jour d’entité et leur correspondance en base de donnée (mysql, postgre, mariadb…)
- Composer : un gestionnaire de dépendance PHP
- CLI Symfony : facultatif, mais facilitera les opération sur Symfony (à l’instar du CLI Angular pour Angular)
- Et d’autres encore…
Construction du projet
Comme l’indique la documentation officiel de 05/2025, l’initialisation d’un projet est permise par deux moyens pratiques : Composer ou le CLI Symfony. Ici les instruction en ligne de commande via composer :
# Création d'un projet via Composer
dossier/ > composer create-project symfony/skeleton:"7.2.x" my_project_directory
cd my_project_directory
# Initialisation d'un projet de type webapp
dossier/ > composer require webapp
# Le dossier my_project_directory contiendra le squelette d'un projet Symfony.
# Puis, on y accède et on initialise une nouvelle application web.
Ces opérations peuvent être menée via une installation classique à l’aide d’un package à télécharger et installer ou même via le CLI Symfony qu’il faudra installé au préalable.
Architecture des dossiers
Comme toute architecture MVC (ou même MVVM en .NET) l’arborescence des dossiers du projet va révéler l’organisation d’une application web Symfony : une partie dédiée à la représentation de la structure des données (le Model), une partie dédiée à leur manipulation et à la gestion des intéraction avec elle (les Controllers) et une partie dédiée à l’affichage de l’application (les Views)
Fichiers et dossiers racines
A la racine on va notamment trouver deux fichiers :
- composer.json : propre au gestionnaire de package composer il va référencer toutes les dépendances du projet. Il identifiera notamment l’espace de nom « app » lié au dossier /src
- .env : comportant toutes les « variables d’environnement », c’est à dire les variable globales au projet. On y trouve notamment DATABASE_URL qui contiendra la chaine de connexion à la bdd.
Concernant les dossiers de bases :
- bin : il va comporter notamment l’accès à la console, executable en ligne de commande, permettant ainsi accès à des instructions issus de Doctrine, de Make et d’autre utilitaire en ligne de commande pour le projet
- config : rassemblant les fichier propre à la configuration global du projet tel que les routes et certains paramètres de sécurité
- migrations : listant les fichiers représentant chaque nouvel état de la base de données, facilitant ainsi les mise à jour et les rollback
- public : le dossier racine de l’application ; c’est à partir de ce dossier que le serveur faisant tourner PHP devra s’executé.
- src : Les Controllers et le Model, le coeur de l’application (voir plus bas)
- template : Les Views, l’aspect de l’application (voir plus bas)
/src
Le dossier des sources, src, va notamment contenir :
- un dossier dédiés aux controllers : Les controllers, dans une application MVC, permettent le pont entre le modele (les données brut) et la View (leur affichage) : on y trouve donc leur traitement, leur manipulation, leur découpage, des requêtes, la gestion des inputs côté view etc.
- un dossier entity : il va contenir les fichier de class php représentant les données. Un lien étroit existe entre cette donnée ET l’existence d’une table SQL. Il contiendra les methode permettant l’accès et la modification des données de l’entitée.
- un dossier repository : il contiendra notamment, pour chaque entité créée un fichier entityRepository.php permettant le SCRUD (Search, Create, Read, Update et Delete) de ces données.
/src/controllers
Les controller formes l’intelligence derrière l’affichage et devant les données en elle-même. On peut en créer via la ligne de commande :
php bin/console make:controller Element
Chaque controller sera créé avec sa view, page .html.twig associé.
//Class d'un controlleur héritant de la classe mère AbstractController
//comportant de nombreuse methode utile, dont "->render()"
final class ElementController extends AbstractController
{
//Attribut identifiant le chemin route
#[Route("/", name:"Element")]
function index(Request $request): Response
{
// On fournit un en paramètre un tableau associatif
// dont les clés seront les variables utilisable dans la vue
return $this->render("/home/index.html.twig",
["controller_name" => "ElementController"]);
}
}
/src/entity
Elles seront créé via le composant Doctrine, en ligne de commande
php bin/console make:entity element
Cela créera à la fois une classe « element » (représentant la donnée/table) et une classe elementRepository (dans un dossier ../Repository) pour le SCRUD.
Ici la classe Element :
#[ORM\Entity(repositoryClass: ElementRepository::class)]
class Element
{
#[ORM\Id]
#[ORM\GeneratedValue]
#[ORM\Column]
private ?int $id = null;
// Propriété définit lors de la création de l'entité
#[ORM\Column(length: 255)]
private ?string $title = null;
public function getId(): ?int
{
return $this->id;
}
//...
}
Ici, dans le controller, ce seront les methodes issus du service ElementRepository (utilisé via Injection de Dépendance) qui permettront notamment leur selection. Puis le service EntityManagerInterface permettra la mise à jour de la base des données en BD.
/template
C’est ici que seront stockés les views, c’est à dire les pages gérées par twig.
Elles utilisent un système d’heritage de template via la definition de block sous le format {% block blockname %}.
<!DOCTYPE html>
<html>
<head>(...)
{# Ici le block title définit le "title" de le la page #}
{% block title %}Titre de la page !{% endblock %}
</head>
<body>
<nav class="navbar navbar-expand-lg bg-body-tertiary">
<div class="container-fluid">
<a class="navbar-brand" href="#">Navbar</a>
</div>
</nav>
<div class="container my-4">
{# Ici le block body viendra définir une zone pouvant être
redefinit dans le template enfant qui héritera de celui la #}
{% block body %}
Le contenu
{% endblock %}
</div>
</body>
</html>
Le formatage twig permet d’utiliser entre {% %} differentes instruction : function, if, for etc. et entre {{ }} les données issues du controller (fournit explicitement à la vue)
{% for element in elements %}
<li>
<a href="{{ path("element.show",
{slug:element.getSlug(), id:element.getId()}) }}">
{{element.getTitle() }}</a>
</li>
{% endfor %}
Attention toutefois : dans un projet symfony va se mélanger un formalisme javascrip (element.getSlug()) et un formalisme php (element->getSlug()). Les deux technologies faisant parties des projets symfony et ne necessitant aucune compilation (contrairement à Angular qui compilera tout le code typescript en javascript).
Et c’est ces mécanismes, qui ont évolué depuis 2007 qui permettent aujourd’hui à Symfony de proposer des projet web solide, maintenable et évolutif grâce à une organisation claire. En 2017 Symfony avait dépassé la barre du milliard de téléchargement.