Retour aux articles
Vue 3TypeScript20 juin 2026

Arrêtez de modéliser l'état de l'UI avec des booléens

isLoading, isError, hasData - trois booléens décrivent huit combinaisons possibles, et seulement quatre sont des états dans lesquels votre composant devrait réellement se trouver. Les quatre autres sont des bugs qui attendent qu'une condition réseau les déclenche.

Mauvais - des indicateurs indépendants qui peuvent se contredire

const isLoading = ref(false);
const isError = ref(false);
const data = ref<Invoice[] | null>(null);

async function load() {
  isLoading.value = true;
  isError.value = false;
  try {
    data.value = await api.get<Invoice[]>("/invoices");
  } catch {
    isError.value = true;
  } finally {
    isLoading.value = false;
  }
}

Rien n'empêche isLoading et isError d'être vrais en même temps après une course entre deux appels à load(). Le template finit avec des chaînes de v-if qui vérifient les indicateurs dans un ordre précis pour masquer des états qui n'auraient jamais dû être représentables.

Bon - un statut, une forme par statut

type RequestState<T> =
  | { status: "idle" }
  | { status: "loading" }
  | { status: "error"; message: string }
  | { status: "success"; data: T };

const state = ref<RequestState<Invoice[]>>({ status: "idle" });

async function load() {
  state.value = { status: "loading" };
  try {
    state.value = { status: "success", data: await api.get<Invoice[]>("/invoices") };
  } catch (e) {
    state.value = { status: "error", message: toMessage(e) };
  }
}

Le template fait un switch sur state.value.status, et TypeScript ne fait exister data et message que là où ils sont valides - il n'y a aucune branche où vous pouvez lire data pendant que status vaut "error". Les combinaisons impossibles ne sont pas gérées, elles sont irreprésentables.

Le compromis : une union discriminée demande plus de lecture que trois lignes ref(false), et chaque consommateur doit faire un switch sur status plutôt que vérifier un indicateur. Ça vaut le coup dès qu'un état de chargement et un état d'erreur peuvent réellement se chevaucher en pratique - ce qui est le cas la plupart du temps dès qu'un appel réseau est impliqué.