- Migrations 'organizations' (id, name, siret, monthly_volume_bucket, rubis_count, onboarding_completed_at) + alter users (organization_id FK + signature).
- Modèle Organization avec relation hasMany Users, User étendu avec belongsTo Organization.
- Signup transactionnel : crée une org vide ('') puis l'user, puis émet le access token. Le nom de l'org reste vide tant que l'utilisateur n'a pas franchi la première étape de l'onboarding (PATCH /organizations/me).
- Réponses /auth/* alignées sur le contrat SPA AuthSession : { data: { accessToken, expiresAt, user } }. Drop passwordConfirmation (le SPA n'envoie pas ce champ).
- Endpoints :
- GET /account/profile (déjà), PATCH /account/profile (nouveau, fullName/email/signature).
- GET /organizations/me + PATCH /organizations/me (name/siret/monthlyVolumeBucket).
- Pose automatique d'onboardingCompletedAt à la première mise en place du nom de l'org — remplace l'astuce 'signature !== null' utilisée côté MSW.
- Transformers convertissent les IDs en string (pour matcher packages/shared/src/types).
- HMR boundaries élargies : transformers/validators/services se rechargent maintenant à chaud (sinon les modifs ne sont pas vues sans restart manuel).
25 lines
987 B
TypeScript
25 lines
987 B
TypeScript
import { UserSchema } from '#database/schema'
|
|
import hash from '@adonisjs/core/services/hash'
|
|
import { compose } from '@adonisjs/core/helpers'
|
|
import { withAuthFinder } from '@adonisjs/auth/mixins/lucid'
|
|
import { type AccessToken, DbAccessTokensProvider } from '@adonisjs/auth/access_tokens'
|
|
import { belongsTo } from '@adonisjs/lucid/orm'
|
|
import type { BelongsTo } from '@adonisjs/lucid/types/relations'
|
|
import Organization from '#models/organization'
|
|
|
|
export default class User extends compose(UserSchema, withAuthFinder(hash)) {
|
|
static accessTokens = DbAccessTokensProvider.forModel(User)
|
|
declare currentAccessToken?: AccessToken
|
|
|
|
@belongsTo(() => Organization)
|
|
declare organization: BelongsTo<typeof Organization>
|
|
|
|
get initials() {
|
|
const [first, last] = this.fullName ? this.fullName.split(' ') : this.email.split('@')
|
|
if (first && last) {
|
|
return `${first.charAt(0)}${last.charAt(0)}`.toUpperCase()
|
|
}
|
|
return `${first.slice(0, 2)}`.toUpperCase()
|
|
}
|
|
}
|