11import { entityNotFound , infrastructureError } from '../app.api/app.api.errors'
22import { AppResponse } from '../app.api/app.api.global'
3- import { MageEventId } from '../entities/events/entities.events'
4- import { Team , TeamId } from '../entities/teams/entities.teams'
5- import { User , UserId , UserRepository , UserRepositoryError } from '../entities/users/entities.users'
3+ import { UserRepository } from '../entities/users/entities.users'
64import { AdmitFromIdentityProviderOperation , AdmitFromIdentityProviderRequest , authenticationFailedError , EnrollMyselfOperation , EnrollMyselfRequest } from './ingress.app.api'
7- import { createEnrollmentCandidateUser , IdentityProvider , IdentityProviderRepository , IdentityProviderUser , UserIngressBindingRepository , UserIngressBindings } from './ingress.entities'
5+ import { IdentityProviderRepository , IdentityProviderUser , UserIngressBindingRepository } from './ingress.entities'
6+ import { ProcessNewUserEnrollment } from './ingress.services.api'
87import { LocalIdpCreateAccountOperation } from './local-idp.app.api'
98import { JWTService , TokenAssertion } from './verification'
109
1110
12- export function CreateEnrollMyselfOperation ( createLocalIdpAccount : LocalIdpCreateAccountOperation , idpRepo : IdentityProviderRepository , userRepo : UserRepository ) : EnrollMyselfOperation {
11+ export function CreateEnrollMyselfOperation ( createLocalIdpAccount : LocalIdpCreateAccountOperation , idpRepo : IdentityProviderRepository , enrollNewUser : ProcessNewUserEnrollment ) : EnrollMyselfOperation {
1312 return async function enrollMyself ( req : EnrollMyselfRequest ) : ReturnType < EnrollMyselfOperation > {
1413 const localAccountCreate = await createLocalIdpAccount ( req )
1514 if ( localAccountCreate . error ) {
1615 return AppResponse . error ( localAccountCreate . error )
1716 }
1817 const localAccount = localAccountCreate . success !
19- const candidateMageAccount : Partial < User > = {
18+ const candidateMageAccount : IdentityProviderUser = {
2019 username : localAccount . username ,
2120 displayName : req . displayName ,
21+ phones : [ ] ,
2222 }
2323 if ( req . email ) {
2424 candidateMageAccount . email = req . email
@@ -27,69 +27,17 @@ export function CreateEnrollMyselfOperation(createLocalIdpAccount: LocalIdpCreat
2727 candidateMageAccount . phones = [ { number : req . phone , type : 'Main' } ]
2828 }
2929 const localIdp = await idpRepo . findIdpByName ( 'local' )
30+ if ( ! localIdp ) {
31+ throw new Error ( 'local idp not found' )
32+ }
33+ const enrollmentResult = await enrollNewUser ( candidateMageAccount , localIdp )
34+
3035 // TODO: auto-activate account after enrollment policy
3136 throw new Error ( 'unimplemented' )
3237 }
3338}
3439
35- export interface AssignTeamMember {
36- ( member : UserId , team : TeamId ) : Promise < boolean >
37- }
38-
39- export interface FindEventTeam {
40- ( mageEventId : MageEventId ) : Promise < Team | null >
41- }
42-
43- async function enrollNewUser ( idpAccount : IdentityProviderUser , idp : IdentityProvider , userRepo : UserRepository , ingressBindingRepo : UserIngressBindingRepository , findEventTeam : FindEventTeam , assignTeamMember : AssignTeamMember ) : Promise < { mageAccount : User , ingressBindings : UserIngressBindings } > {
44- console . info ( `enrolling new user account ${ idpAccount . username } from identity provider ${ idp . name } ` )
45- const candidate = createEnrollmentCandidateUser ( idpAccount , idp )
46- const mageAccount = await userRepo . create ( candidate )
47- if ( mageAccount instanceof UserRepositoryError ) {
48- throw mageAccount
49- }
50- const ingressBindings = await ingressBindingRepo . saveUserIngressBinding (
51- mageAccount . id ,
52- {
53- userId : mageAccount . id ,
54- idpId : idp . id ,
55- idpAccountId : idpAccount . username ,
56- idpAccountAttrs : { } ,
57- // TODO: these do not have functionality yet
58- verified : true ,
59- enabled : true ,
60- }
61- )
62- if ( ingressBindings instanceof Error ) {
63- throw ingressBindings
64- }
65- const { assignToTeams, assignToEvents } = idp . userEnrollmentPolicy
66- const assignEnrolledToTeam = ( teamId : TeamId ) : Promise < { teamId : TeamId , assigned : boolean } > => {
67- return assignTeamMember ( mageAccount . id , teamId )
68- . then ( assigned => ( { teamId, assigned } ) )
69- . catch ( err => {
70- console . error ( `error assigning enrolled user ${ mageAccount . username } to team ${ teamId } ` , err )
71- return { teamId, assigned : false }
72- } )
73- }
74- const assignEnrolledToEventTeam = ( eventId : MageEventId ) : Promise < { eventId : MageEventId , teamId : TeamId | null , assigned : boolean } > => {
75- return findEventTeam ( eventId )
76- . then < { eventId : MageEventId , teamId : TeamId | null , assigned : boolean } > ( eventTeam => {
77- if ( eventTeam ) {
78- return assignEnrolledToTeam ( eventTeam . id ) . then ( teamAssignment => ( { eventId, ...teamAssignment } ) )
79- }
80- console . error ( `failed to find implicit team for event ${ eventId } while enrolling user ${ mageAccount . username } ` )
81- return { eventId, teamId : null , assigned : false }
82- } )
83- . catch ( err => {
84- console . error ( `error looking up implicit team for event ${ eventId } while enrolling user ${ mageAccount . username } ` , err )
85- return { eventId, teamId : null , assigned : false }
86- } )
87- }
88- await Promise . all ( [ ...assignToTeams . map ( assignEnrolledToTeam ) , ...assignToEvents . map ( assignEnrolledToEventTeam ) ] )
89- return { mageAccount, ingressBindings }
90- }
91-
92- export function CreateAdmitFromIdentityProviderOperation ( idpRepo : IdentityProviderRepository , ingressBindingRepo : UserIngressBindingRepository , userRepo : UserRepository , findEventTeam : FindEventTeam , assignTeamMember : AssignTeamMember , tokenService : JWTService ) : AdmitFromIdentityProviderOperation {
40+ export function CreateAdmitFromIdentityProviderOperation ( idpRepo : IdentityProviderRepository , ingressBindingRepo : UserIngressBindingRepository , userRepo : UserRepository , enrollNewUser : ProcessNewUserEnrollment , tokenService : JWTService ) : AdmitFromIdentityProviderOperation {
9341 return async function admitFromIdentityProvider ( req : AdmitFromIdentityProviderRequest ) : ReturnType < AdmitFromIdentityProviderOperation > {
9442 const idp = await idpRepo . findIdpByName ( req . identityProviderName )
9543 if ( ! idp ) {
@@ -104,7 +52,7 @@ export function CreateAdmitFromIdentityProviderOperation(idpRepo: IdentityProvid
10452 return { mageAccount : existingAccount , ingressBindings }
10553 } )
10654 }
107- return enrollNewUser ( idpAccount , idp , userRepo , ingressBindingRepo , findEventTeam , assignTeamMember )
55+ return enrollNewUser ( idpAccount , idp )
10856 } )
10957 . then ( enrolled => {
11058 const { mageAccount, ingressBindings } = enrolled
0 commit comments