Parser des fichiers Excel : feuilles, formules, cellules fusionnées et exemples dans différents langages

Analyse de fichiers Excel en code : feuilles, formules, cellules fusionnées, styles et exemples de lecture en Python, PHP, JavaScript et C#.

ÉW
Équipe Web-Scraping.fr
Collecte de données pour votre activité
Publié le: 6 mars 2025

Les fichiers Excel (.xlsx, plus rarement l'ancien .xls) sont le format le plus courant dans lequel les entreprises transmettent leurs données : listes de prix, stocks, rapports, exports de systèmes de gestion. Contrairement au CSV, Excel n'est pas du texte mais un document structuré : un fichier .xlsx est en réalité une archive ZIP contenant la description XML des feuilles, des styles et des formules. Impossible donc de le lire « ligne par ligne » comme du texte brut — il faut des bibliothèques qui comprennent la structure interne du classeur. Cet article poursuit notre tour d'horizon du parsing de documents.

Ce qui complique le parsing d'Excel

Contrairement à un CSV plat, un classeur Excel comporte plusieurs couches de complexité. Premièrement, plusieurs feuilles — les données peuvent être réparties entre les onglets, et il faut sélectionner explicitement la bonne feuille. Deuxièmement, les formules : une cellule peut contenir aussi bien la formule =B2*C2 que sa valeur calculée, et ce que vous obtiendrez dépend de la méthode de lecture. Troisièmement, les cellules fusionnées, à cause desquelles un en-tête « chevauche » plusieurs colonnes et des vides apparaissent dans les données. Quatrièmement, les formats : une date peut arriver non pas sous la forme 2026-06-01, mais comme le nombre 46184 (numéro de série de date Excel), et un prix comme un nombre associé à un format monétaire. Tout cela doit être pris en compte lors de l'extraction.

Python

L'outil de base pour le .xlsx est openpyxl. Il offre un contrôle complet sur le classeur : feuilles, cellules, fusions.

python
from openpyxl import load_workbook

wb = load_workbook("prices.xlsx", data_only=True)  # data_only=True → valeurs au lieu des formules
ws = wb["Tarifs"]                                   # sélection de la feuille par son nom

for row in ws.iter_rows(min_row=2, values_only=True):
    sku, name, price = row[0], row[1], row[2]
    print(sku, name, price)

Notez le paramètre data_only=True : sans lui, une cellule contenant une formule renverra le texte de la formule et non le résultat. Et rappelez-vous que la valeur calculée n'existe que si le fichier a été ouvert au moins une fois dans Excel — openpyxl ne calcule pas les formules lui-même.

Lorsqu'il faut non pas un parcours ligne par ligne mais de l'analyse — filtres, agrégats, jointures de tableaux — on utilise pandas, qui lit une feuille dans un DataFrame en une seule ligne (il s'appuie sur openpyxl en interne).

python
import pandas as pd

df = pd.read_excel("prices.xlsx", sheet_name="Tarifs")
print(df[df["price"] > 3000])

# si besoin — conversion en CSV
df.to_csv("prices.csv", index=False, encoding="utf-8-sig")

Pour l'ancien format binaire .xls, pandas utilise un moteur distinct, xlrd ; les fichiers modernes .xlsx sont traités via openpyxl.

JavaScript / Node.js

Dans l'écosystème JS, le standard de facto est SheetJS (paquet xlsx). Il fonctionne aussi bien dans Node que dans le navigateur, lit presque tous les formats de tableurs et transforme commodément une feuille en tableau d'objets.

javascript
const XLSX = require("xlsx");

const wb = XLSX.readFile("prices.xlsx");
const sheet = wb.Sheets[wb.SheetNames[0]];   // première feuille
const rows = XLSX.utils.sheet_to_json(sheet); // tableau d'objets d'après les en-têtes

for (const row of rows) {
  console.log(row.sku, row.name, row.price);
}

Lorsqu'il faut non seulement lire mais aussi générer des classeurs complexes avec des styles, ExcelJS fera l'affaire.

PHP

La bibliothèque principale est PhpSpreadsheet (successeur de l'ancienne PHPExcel). Elle lit et écrit les formats .xlsx et .xls, et comprend les formules et les formats.

php
<?php
require "vendor/autoload.php";
use PhpOffice\PhpSpreadsheet\IOFactory;

$spreadsheet = IOFactory::load("prices.xlsx");
$rows = $spreadsheet->getActiveSheet()->toArray(null, true, true, true);

foreach (array_slice($rows, 1) as $row) { // on saute l'en-tête
    echo $row["A"] . " — " . $row["B"] . " — " . $row["C"] . "\n";
}

Go

En Go, le standard de facto est excelize. Il lit les feuilles sous forme de lignes et prend en charge les formules, les styles et le streaming pour les gros fichiers.

go
package main

import (
    "fmt"
    "github.com/xuri/excelize/v2"
)

func main() {
    f, err := excelize.OpenFile("prices.xlsx")
    if err != nil {
        panic(err)
    }
    defer f.Close()

    rows, _ := f.GetRows("Tarifs")
    for _, row := range rows[1:] {
        fmt.Println(row[0], row[1], row[2])
    }
}

Conseils pratiques

Avant d'écrire un parseur, il est utile d'ouvrir le fichier et d'en comprendre la structure : où commencent les données (les premières lignes sont souvent occupées par un en-tête et un logo), y a-t-il des cellules fusionnées dans les intitulés, sur quelle feuille se trouvent les données recherchées. Si l'en-tête est atypique, il est plus simple d'indiquer au parseur la ligne de départ que d'essayer de la deviner. Il vaut mieux normaliser les dates et les nombres dès la lecture — les ramener à un format unique, car dans un même fichier ils sont souvent saisis de manières différentes.

Si les classeurs sont de structure identique mais multi-feuilles, avec des cellules fusionnées et des formules, et qu'ils arrivent régulièrement — nous mettrons en place un parsing Excel automatisé avec export vers une base de données ou en CSV pour un traitement ultérieur. Et lorsque les rapports n'arrivent pas en Excel mais sont mis en page pour l'impression, il s'agit alors de parsing de PDF — consultez l'article dédié.