Aller au contenu principal

Exercice 8

Wow ! On peut maintenant supprimer des enregistrements de notre base de donnĂ©es 🎉.

MĂȘme si nous n'avons pas encore d'implĂ©mentations pour les formules ou les jointures, il pourrait ĂȘtre chouette d'avoir la possibilitĂ© de crĂ©er des alias, non ?

Ne serait-ce que pour bien garder en tĂȘte qu'on est en train de manipuler des codes_pays quand bien mĂȘme c_iso_3166 signifie la mĂȘme chose !

aliases autocomplete

Rendez-vous dans le fichier 8-gestion-des-alias.ts et db.ts pour l'implémentation.

À vous de jouer !

Indice 1​

Déclarer un alias sur une table

Comment déclarer un alias (ou pas !) ? En effet, la subtilité ici est que dans la déclaration de sélection d'une table, on pourra avoir soit le_nom_de_la_table ou bien le_nom_de_la_table son_alias.

Avant de savoir comment nous utiliserons cet alias ensuite, nous pouvons dĂ©jĂ  tenter d'expliquer Ă  TypeScript que les deux formes peuvent ĂȘtre employĂ©es.

Indice 2​

Déclarer un alias sur champ

C'est un peu le mĂȘme cas que pour une table, il faut seulement prendre en compte la syntaxe as (qui sĂ©pare le nom du champ et son alias) en compte.

Indice 3​

Utiliser ces alias

Pour savoir si une syntaxe est acceptable, il va par exemple falloir déterminer si une table est aliasée ou non. Dans ce cas, on peut se demander si son invocation extends une structure du type le_nom_de_la_table son_alias ou non !

Solution​

Avant de déplier pour afficher la solution, n'hésitez pas à nous solliciter !

Alias sur les tables :

type AliasedTabled<TB> = `${TB & string} ${string}`;
// ^? la table ^? son alias
type TableOrAlias<TB> = TB | AliasedTabled<TB>;

type AnyTable<Ctx extends AnyEmptyContext> = TableOrAlias<keyof Ctx["$db"]>;

export const selectFrom = <
Ctx extends AnyEmptyContext,
TB extends AnyTable<Ctx>
>(
ctx: Ctx,
tableName: TB
) => ({
...ctx,
_operation: "select" as const,
_table: tableName,
});

Alias sur les champs

type AliasableField<T> = T | `${T & string} as ${string}`;

type FieldOrExplicitField<Table, Field> =
| AliasableField<Field>
| `${Table & string}.${AliasableField<Field> & string}`;

type ExplicitableField<Ctx extends AnySelectableContext> =
Ctx["_table"] extends `${infer Table} ${infer Alias}`
? FieldOrExplicitField<Alias, keyof Ctx["$db"][Table]>
: FieldOrExplicitField<Ctx["_table"], keyof Ctx["$db"][Ctx["_table"]]>;

export const selectFields = <Ctx extends AnySelectableContext>(
ctx: Ctx,
fieldNames: ExplicitableField<Ctx>[]
) => ({
...ctx,
_fields: fieldNames,
});