# Un Worker. Tous les clients.

Un starter full-stack pour le web et le mobile. TanStack Start, Expo et une API typée sur Cloudflare.

## Déjà en marche.

Tâches, fichiers, sécurité et agents connectés. Les vrais écrans du template avec des données de démonstration.

[Docs](/docs) · [Changelog](/docs/changelog)

## Les pièces en place.

Gardez ce dont votre produit a besoin. Toutes les intégrations sont incluses ; les services optionnels restent inactifs avant leur configuration.

### Produit

- Authentification (Prêt): E-mail et mot de passe, passkeys, codes à deux facteurs, vérification de l'e-mail et gestion des sessions.
- Organisations (Prêt): Membres, invitations et rôles. Les todos et les fichiers appartiennent à l'organisation active.
- Fichiers (Prêt): Envois multipart vers R2, aperçus, liens de partage et corbeille.
- Admin (Prêt): Gestion des utilisateurs, usurpation d'identité, feature flags et journal d'audit.
- Exemple de todos (Prêt): Tableau, kanban et calendrier, avec files d’import à baux et brouillons proposés par les agents IA.
- Paiements (Désactivé par défaut): Stripe et Polar sur le web, RevenueCat sur mobile. Inactifs avant la configuration des fournisseurs et des flags de paiement.

### Plateforme

- Base de données (Prêt): Drizzle sur Neon Postgres, atteint via Hyperdrive.
- E-mail (Prêt): E-mails transactionnels via Cloudflare Email, affichés dans la console en développement.
- i18n et SEO (Prêt): Anglais, allemand et français, hreflang, sitemap et images OG générées avec Takumi.
- Assistant intégré (Désactivé par défaut): Chat en streaming avec TanStack AI et des outils MCP communs. Désactivé tant qu'un fournisseur n'est pas configuré et que le flag de l'assistant n'est pas activé.
- Tâches planifiées (Prêt): Effect aux interfaces externes : cron et envois, avec des baux Postgres pour les tâches en file.
- Consentement aux cookies (Prêt): Une bannière de consentement qui retient les scripts d'analyse et de marketing.

### Mobile

- App Expo (Prêt): iOS et Android avec le même client API, la même session et les passkeys.
- Notifications push (En cours): Enregistrement push Expo et file de livraison. Désactivées tant que les identifiants ne sont pas configurés.
- Widgets d'écran d'accueil (Désactivé par défaut): Widgets de todos pour iOS et Android, derrière une option de build natif.
- Publicités (Désactivé par défaut): Utilitaires AdMob conservés en bibliothèque autonome, non importés par l'app.

## Un seul contrat.

Le navigateur et Expo appellent le même routeur oRPC. Le Worker vérifie la session avant tout accès à Postgres ou R2.

- Web: TanStack Start, React, Tailwind CSS, shadcn/ui

- Mobile: Expo, Expo Router, React Native

- API: oRPC, Zod, Effect

- Auth: Better Auth

- Données et fichiers: Drizzle ORM, Neon Postgres, Hyperdrive, R2

- Plateforme et outillage: Cloudflare Workers, GitHub Actions, Turborepo, pnpm

### apps/web/src/routes/index.tsx

```ts
import { useQuery } from "@tanstack/react-query";
import { orpc } from "@/utils/orpc";

const { data: apiOk, isLoading: apiLoading } =
  useQuery(orpc.healthCheck.queryOptions());
```

Extrait de la route d’accueil. Le client généré conserve le typage de la requête.

### apps/mobile/src/app/(tabs)/(home)/index.tsx

```ts
import { useQuery } from "@tanstack/react-query";
import { orpc } from "@/lib/orpc";

const healthCheck = useQuery(
  orpc.healthCheck.queryOptions(),
);
```

L’écran d’accueil Expo appelle la même procédure de vérification.

### packages/api/src/routers/index.ts

```ts
healthCheck: publicProcedure.handler(() => {
  return "OK";
}),
```

Une vérification publique. Les procédures protégées exigent aussi une session.

## Le serveur reste à part.

Partagez les contrats avec vos clients. Trois contrôles indépendants protègent connexions, secrets et code serveur.

- oxlint: Les imports de valeurs depuis des modules serveur font échouer le lint dans apps/web, apps/mobile et packages/ui. Les imports de types sont autorisés.

- Exports explicites: Chaque package liste ses points d'entrée publics. Pas de jokers, donc un nouvel import entre packages est un choix délibéré.

- Scan du bundle client: Le build web lit les assets client et échoue sur des chaînes qui n'existent que dans le code serveur.

## Un aperçu par PR.

Chaque pull request reçoit un Worker de preview et une branche Neon. Testez son URL avant de fusionner.

- Le merge part en production: Un push sur main lance le workflow de production séparé, avec les secrets et la base de données de production.

- Un nettoyage exact: Il vérifie le projet, la pull request et la branche parente, supprime d'abord le Worker et accepte les ressources déjà supprimées.

## Un catalogue d’outils.

TanStack AI et le serveur MCP utilisent les mêmes outils autorisés. Les agents de code disposent des règles du dépôt et des décisions d’architecture.

- AGENTS.md: Les règles que tout agent de code lit en premier : la frontière client et serveur, Effect côté serveur, l'i18n.

- docs/adr: Les décisions d'architecture avec leur contexte, pour qu'un agent ne les défasse pas.

- .agents/skills: Setup, démarrage, déploiement et vérifications navigateur sous forme de skills pas à pas.

- /api/mcp: Les agents lisent vos données et proposent des brouillons via OAuth. Les brouillons attendent que vous les appliquiez.

- /llms.txt: Du Markdown public sur /index.md et un annuaire /llms.txt à lire avant de connecter un agent.

## À vous de construire.

Clonez votre copie du dépôt. Installez, configurez et lancez le web et le mobile ensemble.

### Cloner

Partez de votre copie du dépôt du template.

```sh
git clone <your-repo-url> my-app
```

### Installer

Installe chaque workspace du monorepo.

```sh
pnpm install
```

### Configurer

Nomme le projet et écrit les fichiers d'env, Wrangler, la base de données, l'e-mail et le stockage.

```sh
pnpm setup
```

### Lancer

Le web sur localhost:3005, plus le serveur de dev Expo pour le mobile.

```sh
pnpm run dev
```

## Avant de cloner.

### Que puis-je essayer dans la démo ?

Créez un compte et utilisez la vraie app : todos, fichiers, organisations, passkeys, double authentification et réglages. Elle tourne sur le même Worker que cette page.

### Pourquoi Cloudflare Workers ?

Un seul déploiement sert les pages, l'API, l'auth et les tâches planifiées. Chaque pull request a son propre Worker, donc la revue se fait sur une vraie URL.

### Pourquoi Neon Postgres plutôt que D1 ?

L'auth, les organisations et les files de tâches s'appuient sur les transactions et les verrous de Postgres. Hyperdrive mutualise la connexion, et chaque pull request a sa propre branche Neon.

### Puis-je retirer le mobile, les paiements ou les publicités ?

Oui. optional-features.json liste chaque package optionnel et ses points d'entrée, et docs/optional-features.md explique comment les retirer.

### Comment changer l'identité visuelle ?

Les couleurs, les rayons et les polices vivent dans un seul fichier de tokens. Les noms et les textes vivent dans les fichiers de langue. Les écrans n'utilisent que des tokens, donc changer la palette change toutes les pages.

### Dois-je connaître Effect ?

Seulement pour modifier les tâches serveur. Effect coordonne l'exécution dans le Worker ; les contrats utilisent Zod, les requêtes oRPC, l'auth Better Auth et l'accès aux données Drizzle.

### Comment connecter un agent IA ?

Pointez n'importe quel client MCP vers /api/mcp. Vous accordez l'accès via OAuth, la lecture et l'écriture sont des scopes séparés, et l'écriture ne crée que des brouillons que vous confirmez dans l'app.

### Le template inclut-il un assistant IA ?

Oui. L'assistant et MCP partagent un catalogue d'outils limité à votre organisation. Les modifications nécessitent une approbation. Configurez Anthropic, OpenAI ou Gemini et activez le flag de l'assistant pour afficher le chat. Il est désactivé par défaut.
