@@ -10,7 +10,7 @@ use aide::{NoApi, OperationIo, transform::TransformOperation};
10
10
use axum:: { Json , extract:: State , response:: IntoResponse } ;
11
11
use hyper:: StatusCode ;
12
12
use mas_axum_utils:: record_error;
13
- use mas_matrix:: HomeserverConnection ;
13
+ use mas_matrix:: { HomeserverConnection , ProvisionRequest } ;
14
14
use mas_storage:: {
15
15
BoxRng ,
16
16
queue:: { ProvisionUserJob , QueueJobRepositoryExt as _} ,
@@ -106,6 +106,10 @@ pub struct Request {
106
106
/// tokens (like with admin access) for them
107
107
#[ serde( default ) ]
108
108
skip_homeserver_check : bool ,
109
+
110
+ /// Delay the response until the user has been created on the homeserver.
111
+ #[ serde( default ) ]
112
+ add_synchronously : bool ,
109
113
}
110
114
111
115
pub fn doc ( operation : TransformOperation ) -> TransformOperation {
@@ -168,9 +172,19 @@ pub async fn handler(
168
172
169
173
let user = repo. user ( ) . add ( & mut rng, & clock, params. username ) . await ?;
170
174
171
- repo. queue_job ( )
172
- . schedule_job ( & mut rng, & clock, ProvisionUserJob :: new ( & user) )
173
- . await ?;
175
+ if params. add_synchronously {
176
+ homeserver
177
+ . provision_user ( & ProvisionRequest :: new (
178
+ homeserver. mxid ( & user. username ) ,
179
+ & user. sub ,
180
+ ) )
181
+ . await
182
+ . map_err ( RouteError :: Homeserver ) ?;
183
+ } else {
184
+ repo. queue_job ( )
185
+ . schedule_job ( & mut rng, & clock, ProvisionUserJob :: new ( & user) )
186
+ . await ?;
187
+ }
174
188
175
189
repo. save ( ) . await ?;
176
190
@@ -183,6 +197,7 @@ pub async fn handler(
183
197
#[ cfg( test) ]
184
198
mod tests {
185
199
use hyper:: { Request , StatusCode } ;
200
+ use mas_matrix:: HomeserverConnection ;
186
201
use mas_storage:: { RepositoryAccess , user:: UserRepository } ;
187
202
use sqlx:: PgPool ;
188
203
@@ -220,6 +235,28 @@ mod tests {
220
235
assert_eq ! ( user. username, "alice" ) ;
221
236
}
222
237
238
+ #[ sqlx:: test( migrator = "mas_storage_pg::MIGRATOR" ) ]
239
+ async fn test_add_user_synchronously ( pool : PgPool ) {
240
+ setup ( ) ;
241
+ let mut state = TestState :: from_pool ( pool) . await . unwrap ( ) ;
242
+ let token = state. token_with_scope ( "urn:mas:admin" ) . await ;
243
+
244
+ let request = Request :: post ( "/api/admin/v1/users" )
245
+ . bearer ( & token)
246
+ . json ( serde_json:: json!( {
247
+ "username" : "alice" ,
248
+ "add_synchronously" : true ,
249
+ } ) ) ;
250
+
251
+ let response = state. request ( request) . await ;
252
+ response. assert_status ( StatusCode :: CREATED ) ;
253
+
254
+ // Check that the user was created on the homeserver
255
+ let mxid = state. homeserver_connection . mxid ( "alice" ) ;
256
+ let result = state. homeserver_connection . query_user ( & mxid) . await ;
257
+ assert ! ( result. is_ok( ) ) ;
258
+ }
259
+
223
260
#[ sqlx:: test( migrator = "mas_storage_pg::MIGRATOR" ) ]
224
261
async fn test_add_user_invalid_username ( pool : PgPool ) {
225
262
setup ( ) ;
0 commit comments