Identité : utilisateurs anonymes et connectés
L'identité est portée par AppwinCore, pas par les produits. Un appareil, une session, un utilisateur : les modules Community, Support et Notifications lisent tous la même. C'est ce qui fait qu'une personne identifiée dans ton app est le même interlocuteur partout, sans que tu aies rien à recopier d'un produit à l'autre.
Trois états, dans cet ordre. Chacun est utilisable seul : tu peux t'arrêter au premier et avoir une intégration qui fonctionne.
1. Anonyme - rien à faire
Dès configure, le SDK reconnaît l'appareil : il génère un identifiant, le
persiste, et ouvre une session authentifiée en tâche de fond. L'end-user peut
lire et écrire sans inscription.
AppwinCore.configure(projectAppId: "ton-app-id")
print(AppwinCore.deviceId ?? "-") // stable d'un lancement à l'autre
L'identifiant est persisté dans le trousseau, donc il survit à une désinstallation. C'est ce qui évite qu'une personne perde son historique en changeant de version d'app.
Ce que voit cet end-user dépend du produit. Côté Community, son profil naît avec un pseudo généré stable (« Curious Otter 417 »), dérivé de son identifiant : s'il réinstalle l'app, il retrouve le même pseudo plutôt que de repartir avec une nouvelle identité aux yeux des autres. Côté Support, il ouvre une conversation comme visiteur.
Un membre anonyme peut se nommer lui-même depuis l'écran de profil du SDK. Il n'a pas besoin de toi pour ça.
2. Connecté - rattacher à ton utilisateur
Quand ton app sait qui est la personne, pousse ton identifiant, celui de ta base. Appwin ne l'interprète pas : il sert à reconnaître la même personne d'un appareil à l'autre et d'un produit à l'autre.
AppwinCore.identify(externalId: user.id)
try await AppwinCore.bootstrapSession(externalId: user.id)
Deux gestes plutôt qu'un : identify inscrit l'externalId dans l'identité
locale, bootstrapSession(externalId:) refrappe un jeton qui le porte. Sans le
second, la session ouverte reste celle du profil anonyme jusqu'au prochain
démarrage de l'app.
Les modules produit exposent un raccourci - AppwinCommunity.login(...),
AppwinSupport.loginIdentifiedUser(...) - qui pousse la même valeur dans Core
et rattache la personne côté serveur. C'est le chemin par défaut en React
Native, où Core n'expose pas la variante à externalId.
C'est là que se joue le partage : après ce rattachement, cette personne est la même pour Support et pour Community. Ses conversations et son profil appartiennent au même individu, et ton équipe le voit comme un seul interlocuteur.
Déconnexion
await AppwinCore.signOut()
signOut révoque la session côté serveur, vide le stockage local et repasse en
profil anonyme. À appeler quand l'utilisateur se déconnecte de ton app -
sinon la personne suivante sur le même appareil hériterait de son identité.
Il existe aussi clearIdentity(), qui oublie l'externalId localement sans
rien révoquer. C'est un outil de test, pas une déconnexion.
3. Enrichi - pousser les attributs
Ton app connaît souvent déjà un pseudo, une photo, un email. Les pousser épargne une saisie. Cette passerelle est propre à chaque produit, parce que les attributs ne sont pas les mêmes : un profil communautaire n'est pas une fiche client.
| Produit | Méthode | Champs |
|---|---|---|
| Community | AppwinCommunity.setUser(...) | nickname, avatarUrl, bio |
| Support | AppwinSupport.updateUser(...) | name, email, avatarUrl, language, timezone, location |
try await AppwinCommunity.setUser(
nickname: user.displayName,
avatarUrl: user.photoURL?.absoluteString
)
Deux règles :
- Tous les champs sont optionnels. Un champ omis n'est pas écrasé : une app qui ne connaît qu'un pseudo n'efface pas la bio saisie dans le SDK.
- Fournir un
nicknamesort le profil communautaire de l'anonymat. C'est l'acte qui donne une identité visible. Le membre peut y revenir explicitement depuis son profil.
Ces méthodes ne changent pas l'identité : elles enrichissent le profil. Pour rattacher à ton utilisateur, c'est l'étape 2.
Quand appeler quoi
Démarrage de l'app → AppwinCore.configure(...) toujours
Connexion dans TON app → identify + bootstrapSession rattachement
(ou le login du produit)
Juste après → setUser / updateUser attributs
Profil modifié chez toi → setUser / updateUser mise à jour
Déconnexion dans TON app → AppwinCore.signOut() retour anonyme
L'ordre compte : le rattachement avant les attributs. Poussés dans l'autre sens, ils partent sur le profil anonyme et sont perdus au rattachement.
Ce qui est partagé, et ce qui ne l'est pas
| Porté par Core, partagé | Propre à chaque produit |
|---|---|
| Identifiant d'appareil | Profil communautaire (pseudo, avatar, bio) |
| Session et jeton | Fiche client Support (email, langue, plan) |
externalId | Sanctions de modération |
| Métadonnées d'appareil | Jeton push et opt-in |
Modération
Trois sanctions existent côté Community, décidées depuis le dashboard : avertissement, ban en lecture seule, et shadow ban - le membre continue de publier et voit ses propres contenus, personne d'autre ne les voit, et il n'en est jamais informé, ni par l'UI ni par une réponse d'API. Le SDK est conçu pour ne rien en laisser filtrer. Le détail est dans Piloter Community.
Vie privée
Ce que le SDK envoie, et rien de plus :
- un identifiant d'appareil généré par le SDK - pas l'IDFA, pas l'IDFV, pas l'ID de publicité Android
- la plateforme, le modèle, la version d'OS et d'app
- la langue de l'appareil, pour la traduction des contenus
- l'
externalIdque tu fournis, si tu en fournis un
Le SDK ne lit ni le carnet d'adresses, ni la localisation, ni les identifiants
publicitaires. L'externalId étant choisi par toi, tu peux y mettre un
identifiant opaque plutôt qu'un email si tu préfères.
Suite
- Installation - dépendances, initialisation, API locale
- Community - afficher le fil et le personnaliser