Support formation Rapports Power BI

Plusieurs tables de faits

Construire un modèle en constellation ; relier des faits de même granularité par des dimensions conformes ; gérer des faits plus agrégés (objectifs mensuels) ; utiliser TREATAS pour une relation virtuelle.

Modéliser - Plusieurs tables de faits

Pourquoi ?

Un modèle Power BI contient rarement une seule table de faits : ventes et objectifs, commandes et stocks, budget et réalisé. Ce modèle à plusieurs étoiles est appelé modèle en constellation (ou schéma en galaxie). Mal relier ces tables produit des résultats faux ou incompréhensibles. Source

Notions clés

Les règles de base

  • Chaque table de faits a sa propre granularité, constante sur toutes ses lignes (une ligne par ligne de commande, une ligne par mois et par catégorie). Source
  • Les tables de faits ne sont jamais reliées entre elles : elles communiquent par les dimensions qu'elles partagent.
  • Les dimensions partagées sont appelées dimensions conformes : même clé, mêmes attributs, utilisées par toutes les étoiles. La table de dates en est l'exemple type. Source
  • Les relations restent en un-à-plusieurs, à sens unique, de la dimension vers chaque table de faits.
  • Les colonnes numériques des tables de faits sont masquées : on ne présente que des mesures.

Exemple fil rouge

TableTypeGranularité
DimDateDimension conformeJour
DimProductDimension conformeProduit (avec Catégorie)
DimStoreDimension conformeMagasin
FactSalesFaitsJour × produit × magasin
FactInventoryFaitsJour × produit × magasin (photo du stock)
FactTargetFaitsMois × catégorie

Cas 1 | Même granularité : dimensions partagées

FactSales et FactInventory ont la même granularité.

Cas 1 | Même granularité : dimensions partagées
Cas 1 | Même granularité : dimensions partagées
  • Reliez DimDate, DimProduct et DimStore à chacune des deux tables de faits (1:*, sens unique).
  • Un segment sur DimProduct[Catégorie] filtre alors les ventes et les stocks en même temps.
  • Les axes et segments d'un visuel qui combine les deux tables doivent toujours provenir des dimensions, jamais d'une table de faits.
Ventes = SUM ( FactSales[Montant] )

Stock fin de période =
CALCULATE (
    SUM ( FactInventory[Quantité] ),
    LASTDATE ( DimDate[Date] )
)

Taux de rotation = DIVIDE ( [Ventes], [Stock fin de période] )

Un stock est un fait semi-additif : on ne l'additionne pas dans le temps, d'où LASTDATE ou LASTNONBLANK. Source

Cas 2 | Granularité différente : faits plus agrégés

FactTarget est stockée au mois et à la catégorie, à un niveau plus élevé que DimDate (jour) et DimProduct (produit).

Cas 2 | Granularité différente : faits plus agrégés
Cas 2 | Granularité différente : faits plus agrégés

Côté date

  • Stockez dans FactTarget le premier jour de la période (le 01/03/2026 pour mars 2026), en type Date.
  • Créez une relation 1:* classique entre DimDate[Date] et FactTarget[Mois]. Source

Côté produit

Trois solutions, de la plus recommandée à la plus ponctuelle :

  • Dimension Catégorie dédiée : créez DimCategory (une ligne par catégorie), reliée en 1:* à FactTarget et à DimProduct. C'est la solution la plus lisible.
  • Relation plusieurs-à-plusieurs DimProduct[Catégorie] *:* FactTarget[Catégorie], avec un filtrage unidirectionnel de DimProduct vers FactTarget. Source
  • Relation virtuelle avec TREATAS, sans relation physique (cas 3).

Contrôler l'agrégation

Sans précaution, un objectif mensuel affiché au jour ou au produit donne un résultat faux (vide ou dupliqué). La mesure doit renvoyer BLANK sous la granularité de la table :

Objectif =
IF (
    NOT ISFILTERED ( DimDate[Date] )
        && NOT ISFILTERED ( DimProduct[Produit] ),
    SUM ( FactTarget[Montant objectif] )
)

Écart à l'objectif = [Ventes] - [Objectif]
% Atteinte = DIVIDE ( [Ventes], [Objectif] )

Une variante consiste à répartir l'objectif au jour, au prorata du nombre de jours du mois. Ce calcul plus avancé est à réserver aux besoins avérés.

Cas 3 | Relation virtuelle avec TREATAS

TREATAS applique les valeurs d'une colonne comme filtre sur une autre colonne, sans relation dans le modèle. C'est utile pour un besoin ponctuel ou pour éviter une relation *:* ambiguë. Source

Cas 3 | Relation virtuelle avec TREATAS
Cas 3 | Relation virtuelle avec TREATAS
Objectif (TREATAS) =
CALCULATE (
    SUM ( FactTarget[Montant objectif] ),
    TREATAS ( VALUES ( DimProduct[Catégorie] ), FactTarget[Catégorie] )
)
  • Avantage : pas de relation supplémentaire, pas de risque d'ambiguïté.
  • Inconvénient : la logique doit être reprise dans chaque mesure, et une relation virtuelle est généralement moins efficace qu'une relation physique sur de gros volumes. Source

Pièges et bonnes pratiques

  • Ne reliez jamais deux tables de faits directement (relation *:* entre FactSales et FactTarget) : passez par des dimensions communes. Source
  • Ne fusionnez pas des faits de granularités différentes dans une même table.
  • N'activez pas le filtrage bidirectionnel pour « faire fonctionner » un visuel : chemins ambigus et performances dégradées. Source
  • N'utilisez pas une colonne d'une table de faits comme axe ou segment : elle ne filtre pas les autres tables de faits.

À retenir

  • Une table de faits, une granularité.
  • Les tables de faits communiquent uniquement par des dimensions conformes.
  • Un fait plus agrégé se relie par le premier jour de la période et une dimension dédiée, ou une relation *:* unidirectionnelle.
  • La mesure d'un fait agrégé renvoie BLANK sous sa granularité.

Pour aller plus loin

  • Conseils sur les relations plusieurs-à-plusieurs. Source (Microsoft Learn)
  • Modélisation dimensionnelle dans l'entrepôt Microsoft Fabric. Source (Microsoft Learn)
  • Les fonctions DAX liées aux relations (TREATAS, USERELATIONSHIP, CROSSFILTER) sont détaillées dans la page DAX et relations de la sous-partie Calculer avec DAX.

Exercice

À partir du modèle de vente du support :

  1. Importez une table d'objectifs mensuels par catégorie (Mois au 1er du mois, Catégorie, Montant objectif).
  2. Créez la dimension Catégorie ou la relation *:* unidirectionnelle.
  3. Écrivez les mesures Objectif, Écart à l'objectif et % Atteinte.
  4. Construisez une matrice Année / Mois × Catégorie et vérifiez qu'au jour ou au produit l'objectif est vide.
  5. Refaites la mesure Objectif avec TREATAS et comparez les résultats dans l'analyseur de performances.

L'exercice DAX « 6 | Objectifs (TREATAS) » de la sous-partie Calculer avec DAX prolonge ce travail.