@faable/auth-sdk 2.6.15 → 2.6.17

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/spec/openapi.json CHANGED
@@ -3,7 +3,7 @@
3
3
  "info": {
4
4
  "title": "@faablecloud/auth",
5
5
  "description": "Auth Platform made by Faable. Manage Users and Roles",
6
- "version": "2.16.0",
6
+ "version": "2.18.0",
7
7
  "license": {
8
8
  "name": "private",
9
9
  "url": "https://faable.com/docs/platform/privacy-policy"
@@ -482,6 +482,13 @@
482
482
  "additionalProperties": false,
483
483
  "description": "Password-recovery delivery channels. Set on the Account as the tenant default; the same object on a Client overrides it field by field, like `login_methods` and `mfa_policy`."
484
484
  },
485
+ "default_country_iso": {
486
+ "type": "string",
487
+ "minLength": 2,
488
+ "maxLength": 2,
489
+ "description": "ISO 3166-1 alpha-2 country assumed for phone numbers written without an international prefix (`636647460` → `+34…` with `ES`). Needed before SMS can reach anyone: most people type their number without a prefix.",
490
+ "nullable": true
491
+ },
485
492
  "webauthn_rp_id": {
486
493
  "type": "string",
487
494
  "description": "WebAuthn Relying Party ID for this tenant's passkeys. Defaults to the account domain. Set it to a registrable suffix you own (e.g. `acme.com`) when the login screen is served from more than one host — the RP ID is frozen into every credential at registration, so changing it afterwards invalidates every passkey already enrolled.",
@@ -2237,6 +2244,12 @@
2237
2244
  "federated"
2238
2245
  ]
2239
2246
  },
2247
+ {
2248
+ "type": "string",
2249
+ "enum": [
2250
+ "sms_otp"
2251
+ ]
2252
+ },
2240
2253
  {
2241
2254
  "type": "null"
2242
2255
  }
@@ -2324,11 +2337,17 @@
2324
2337
  "federated"
2325
2338
  ]
2326
2339
  },
2340
+ {
2341
+ "type": "string",
2342
+ "enum": [
2343
+ "sms_otp"
2344
+ ]
2345
+ },
2327
2346
  {
2328
2347
  "type": "null"
2329
2348
  }
2330
2349
  ],
2331
- "description": "How `phone_verified` was last set. Same enum as `email_verified_method`."
2350
+ "description": "How `phone_verified` was last set. Same enum as `email_verified_method`, plus `sms_otp` — the user typed a code sent by SMS (`POST /user/:id/verify-phone/start`)."
2332
2351
  },
2333
2352
  "phone_verified_at": {
2334
2353
  "type": "string",
@@ -6465,6 +6484,18 @@
6465
6484
  }
6466
6485
  ]
6467
6486
  },
6487
+ "default_country_iso": {
6488
+ "anyOf": [
6489
+ {
6490
+ "type": "string",
6491
+ "minLength": 2,
6492
+ "maxLength": 2
6493
+ },
6494
+ {
6495
+ "type": "null"
6496
+ }
6497
+ ]
6498
+ },
6468
6499
  "webauthn_rp_id": {
6469
6500
  "type": "string",
6470
6501
  "nullable": true
@@ -7262,6 +7293,13 @@
7262
7293
  "additionalProperties": false,
7263
7294
  "description": "Password-recovery delivery channels. Set on the Account as the tenant default; the same object on a Client overrides it field by field, like `login_methods` and `mfa_policy`."
7264
7295
  },
7296
+ "default_country_iso": {
7297
+ "type": "string",
7298
+ "minLength": 2,
7299
+ "maxLength": 2,
7300
+ "description": "ISO 3166-1 alpha-2 country assumed for phone numbers written without an international prefix (`636647460` → `+34…` with `ES`). Needed before SMS can reach anyone: most people type their number without a prefix.",
7301
+ "nullable": true
7302
+ },
7265
7303
  "webauthn_rp_id": {
7266
7304
  "type": "string",
7267
7305
  "description": "WebAuthn Relying Party ID for this tenant's passkeys. Defaults to the account domain. Set it to a registrable suffix you own (e.g. `acme.com`) when the login screen is served from more than one host — the RP ID is frozen into every credential at registration, so changing it afterwards invalidates every passkey already enrolled.",
@@ -7804,6 +7842,13 @@
7804
7842
  "additionalProperties": false,
7805
7843
  "description": "Password-recovery delivery channels. Set on the Account as the tenant default; the same object on a Client overrides it field by field, like `login_methods` and `mfa_policy`."
7806
7844
  },
7845
+ "default_country_iso": {
7846
+ "type": "string",
7847
+ "minLength": 2,
7848
+ "maxLength": 2,
7849
+ "description": "ISO 3166-1 alpha-2 country assumed for phone numbers written without an international prefix (`636647460` → `+34…` with `ES`). Needed before SMS can reach anyone: most people type their number without a prefix.",
7850
+ "nullable": true
7851
+ },
7807
7852
  "webauthn_rp_id": {
7808
7853
  "type": "string",
7809
7854
  "description": "WebAuthn Relying Party ID for this tenant's passkeys. Defaults to the account domain. Set it to a registrable suffix you own (e.g. `acme.com`) when the login screen is served from more than one host — the RP ID is frozen into every credential at registration, so changing it afterwards invalidates every passkey already enrolled.",
@@ -8400,6 +8445,13 @@
8400
8445
  "additionalProperties": false,
8401
8446
  "description": "Password-recovery delivery channels. Set on the Account as the tenant default; the same object on a Client overrides it field by field, like `login_methods` and `mfa_policy`."
8402
8447
  },
8448
+ "default_country_iso": {
8449
+ "type": "string",
8450
+ "minLength": 2,
8451
+ "maxLength": 2,
8452
+ "description": "ISO 3166-1 alpha-2 country assumed for phone numbers written without an international prefix (`636647460` → `+34…` with `ES`). Needed before SMS can reach anyone: most people type their number without a prefix.",
8453
+ "nullable": true
8454
+ },
8403
8455
  "webauthn_rp_id": {
8404
8456
  "type": "string",
8405
8457
  "description": "WebAuthn Relying Party ID for this tenant's passkeys. Defaults to the account domain. Set it to a registrable suffix you own (e.g. `acme.com`) when the login screen is served from more than one host — the RP ID is frozen into every credential at registration, so changing it afterwards invalidates every passkey already enrolled.",
@@ -8815,6 +8867,18 @@
8815
8867
  }
8816
8868
  ]
8817
8869
  },
8870
+ "default_country_iso": {
8871
+ "anyOf": [
8872
+ {
8873
+ "type": "string",
8874
+ "minLength": 2,
8875
+ "maxLength": 2
8876
+ },
8877
+ {
8878
+ "type": "null"
8879
+ }
8880
+ ]
8881
+ },
8818
8882
  "webauthn_rp_id": {
8819
8883
  "type": "string",
8820
8884
  "nullable": true
@@ -9297,6 +9361,13 @@
9297
9361
  "additionalProperties": false,
9298
9362
  "description": "Password-recovery delivery channels. Set on the Account as the tenant default; the same object on a Client overrides it field by field, like `login_methods` and `mfa_policy`."
9299
9363
  },
9364
+ "default_country_iso": {
9365
+ "type": "string",
9366
+ "minLength": 2,
9367
+ "maxLength": 2,
9368
+ "description": "ISO 3166-1 alpha-2 country assumed for phone numbers written without an international prefix (`636647460` → `+34…` with `ES`). Needed before SMS can reach anyone: most people type their number without a prefix.",
9369
+ "nullable": true
9370
+ },
9300
9371
  "webauthn_rp_id": {
9301
9372
  "type": "string",
9302
9373
  "description": "WebAuthn Relying Party ID for this tenant's passkeys. Defaults to the account domain. Set it to a registrable suffix you own (e.g. `acme.com`) when the login screen is served from more than one host — the RP ID is frozen into every credential at registration, so changing it afterwards invalidates every passkey already enrolled.",
@@ -9812,6 +9883,13 @@
9812
9883
  "additionalProperties": false,
9813
9884
  "description": "Password-recovery delivery channels. Set on the Account as the tenant default; the same object on a Client overrides it field by field, like `login_methods` and `mfa_policy`."
9814
9885
  },
9886
+ "default_country_iso": {
9887
+ "type": "string",
9888
+ "minLength": 2,
9889
+ "maxLength": 2,
9890
+ "description": "ISO 3166-1 alpha-2 country assumed for phone numbers written without an international prefix (`636647460` → `+34…` with `ES`). Needed before SMS can reach anyone: most people type their number without a prefix.",
9891
+ "nullable": true
9892
+ },
9815
9893
  "webauthn_rp_id": {
9816
9894
  "type": "string",
9817
9895
  "description": "WebAuthn Relying Party ID for this tenant's passkeys. Defaults to the account domain. Set it to a registrable suffix you own (e.g. `acme.com`) when the login screen is served from more than one host — the RP ID is frozen into every credential at registration, so changing it afterwards invalidates every passkey already enrolled.",
@@ -14895,6 +14973,12 @@
14895
14973
  "federated"
14896
14974
  ]
14897
14975
  },
14976
+ {
14977
+ "type": "string",
14978
+ "enum": [
14979
+ "sms_otp"
14980
+ ]
14981
+ },
14898
14982
  {
14899
14983
  "type": "null"
14900
14984
  }
@@ -14982,11 +15066,17 @@
14982
15066
  "federated"
14983
15067
  ]
14984
15068
  },
15069
+ {
15070
+ "type": "string",
15071
+ "enum": [
15072
+ "sms_otp"
15073
+ ]
15074
+ },
14985
15075
  {
14986
15076
  "type": "null"
14987
15077
  }
14988
15078
  ],
14989
- "description": "How `phone_verified` was last set. Same enum as `email_verified_method`."
15079
+ "description": "How `phone_verified` was last set. Same enum as `email_verified_method`, plus `sms_otp` — the user typed a code sent by SMS (`POST /user/:id/verify-phone/start`)."
14990
15080
  },
14991
15081
  "phone_verified_at": {
14992
15082
  "type": "string",
@@ -15267,6 +15357,12 @@
15267
15357
  "federated"
15268
15358
  ]
15269
15359
  },
15360
+ {
15361
+ "type": "string",
15362
+ "enum": [
15363
+ "sms_otp"
15364
+ ]
15365
+ },
15270
15366
  {
15271
15367
  "type": "null"
15272
15368
  }
@@ -15354,11 +15450,17 @@
15354
15450
  "federated"
15355
15451
  ]
15356
15452
  },
15453
+ {
15454
+ "type": "string",
15455
+ "enum": [
15456
+ "sms_otp"
15457
+ ]
15458
+ },
15357
15459
  {
15358
15460
  "type": "null"
15359
15461
  }
15360
15462
  ],
15361
- "description": "How `phone_verified` was last set. Same enum as `email_verified_method`."
15463
+ "description": "How `phone_verified` was last set. Same enum as `email_verified_method`, plus `sms_otp` — the user typed a code sent by SMS (`POST /user/:id/verify-phone/start`)."
15362
15464
  },
15363
15465
  "phone_verified_at": {
15364
15466
  "type": "string",
@@ -15718,6 +15820,12 @@
15718
15820
  "federated"
15719
15821
  ]
15720
15822
  },
15823
+ {
15824
+ "type": "string",
15825
+ "enum": [
15826
+ "sms_otp"
15827
+ ]
15828
+ },
15721
15829
  {
15722
15830
  "type": "null"
15723
15831
  }
@@ -15805,11 +15913,17 @@
15805
15913
  "federated"
15806
15914
  ]
15807
15915
  },
15916
+ {
15917
+ "type": "string",
15918
+ "enum": [
15919
+ "sms_otp"
15920
+ ]
15921
+ },
15808
15922
  {
15809
15923
  "type": "null"
15810
15924
  }
15811
15925
  ],
15812
- "description": "How `phone_verified` was last set. Same enum as `email_verified_method`."
15926
+ "description": "How `phone_verified` was last set. Same enum as `email_verified_method`, plus `sms_otp` — the user typed a code sent by SMS (`POST /user/:id/verify-phone/start`)."
15813
15927
  },
15814
15928
  "phone_verified_at": {
15815
15929
  "type": "string",
@@ -16088,6 +16202,12 @@
16088
16202
  "federated"
16089
16203
  ]
16090
16204
  },
16205
+ {
16206
+ "type": "string",
16207
+ "enum": [
16208
+ "sms_otp"
16209
+ ]
16210
+ },
16091
16211
  {
16092
16212
  "type": "null"
16093
16213
  }
@@ -16175,11 +16295,17 @@
16175
16295
  "federated"
16176
16296
  ]
16177
16297
  },
16298
+ {
16299
+ "type": "string",
16300
+ "enum": [
16301
+ "sms_otp"
16302
+ ]
16303
+ },
16178
16304
  {
16179
16305
  "type": "null"
16180
16306
  }
16181
16307
  ],
16182
- "description": "How `phone_verified` was last set. Same enum as `email_verified_method`."
16308
+ "description": "How `phone_verified` was last set. Same enum as `email_verified_method`, plus `sms_otp` — the user typed a code sent by SMS (`POST /user/:id/verify-phone/start`)."
16183
16309
  },
16184
16310
  "phone_verified_at": {
16185
16311
  "type": "string",
@@ -16587,6 +16713,39 @@
16587
16713
  "connection": {
16588
16714
  "type": "string",
16589
16715
  "description": "Optional connection_name to disambiguate when the tenant has more than one database connection. Defaults to the tenant database connection."
16716
+ },
16717
+ "channel": {
16718
+ "anyOf": [
16719
+ {
16720
+ "anyOf": [
16721
+ {
16722
+ "type": "string",
16723
+ "enum": [
16724
+ "email"
16725
+ ]
16726
+ },
16727
+ {
16728
+ "type": "string",
16729
+ "enum": [
16730
+ "sms"
16731
+ ]
16732
+ },
16733
+ {
16734
+ "type": "string",
16735
+ "enum": [
16736
+ "whatsapp"
16737
+ ]
16738
+ },
16739
+ {
16740
+ "type": "string",
16741
+ "enum": [
16742
+ "factor"
16743
+ ]
16744
+ }
16745
+ ]
16746
+ }
16747
+ ],
16748
+ "description": "How to deliver it: `email` (the link) or `sms` / `whatsapp` (a 6-digit code to the verified phone on file). Falls back to the tenant default when not available for this user; the response says which channel was used."
16590
16749
  }
16591
16750
  },
16592
16751
  "additionalProperties": false
@@ -16619,7 +16778,8 @@
16619
16778
  "required": [
16620
16779
  "status",
16621
16780
  "credential_id",
16622
- "ticket_id"
16781
+ "ticket_id",
16782
+ "channel"
16623
16783
  ],
16624
16784
  "properties": {
16625
16785
  "status": {
@@ -16633,6 +16793,34 @@
16633
16793
  },
16634
16794
  "ticket_id": {
16635
16795
  "type": "string"
16796
+ },
16797
+ "channel": {
16798
+ "anyOf": [
16799
+ {
16800
+ "type": "string",
16801
+ "enum": [
16802
+ "email"
16803
+ ]
16804
+ },
16805
+ {
16806
+ "type": "string",
16807
+ "enum": [
16808
+ "sms"
16809
+ ]
16810
+ },
16811
+ {
16812
+ "type": "string",
16813
+ "enum": [
16814
+ "whatsapp"
16815
+ ]
16816
+ },
16817
+ {
16818
+ "type": "string",
16819
+ "enum": [
16820
+ "factor"
16821
+ ]
16822
+ }
16823
+ ]
16636
16824
  }
16637
16825
  }
16638
16826
  }
@@ -16687,7 +16875,8 @@
16687
16875
  "email",
16688
16876
  "createdAt",
16689
16877
  "expires_at",
16690
- "ttl"
16878
+ "ttl",
16879
+ "channel"
16691
16880
  ],
16692
16881
  "properties": {
16693
16882
  "id": {
@@ -16730,6 +16919,10 @@
16730
16919
  "ttl": {
16731
16920
  "type": "number"
16732
16921
  },
16922
+ "channel": {
16923
+ "type": "string",
16924
+ "description": "How this ticket reaches the person: `email` (the link), `sms` / `whatsapp` (a code), `factor`. Older tickets are `email`."
16925
+ },
16733
16926
  "link": {
16734
16927
  "type": "string",
16735
16928
  "description": "The link from the ticket email. Present only while the ticket is usable — a dead link is noise, not a recovery path."
@@ -16815,6 +17008,141 @@
16815
17008
  }
16816
17009
  }
16817
17010
  },
17011
+ "/user/{user_id}/verify-phone/start": {
17012
+ "post": {
17013
+ "operationId": "user/verifyPhoneStart",
17014
+ "summary": "Send a verification code to the user's phone",
17015
+ "tags": [
17016
+ "user"
17017
+ ],
17018
+ "description": "Sends a 6-digit code by SMS to the user's phone (optionally setting a new phone first) and returns an opaque `state` to confirm it with. Same authorization as `verify-email/start`: the user themself (session or bearer), an admin of another tenant, or a machine token. Counts against the tenant's monthly SMS allowance. Fails with 409 `sms_unavailable` when no SMS can go out (no provider, plan does not allow it, allowance exhausted).",
17019
+ "requestBody": {
17020
+ "required": true,
17021
+ "content": {
17022
+ "application/json": {
17023
+ "schema": {
17024
+ "type": "object",
17025
+ "properties": {
17026
+ "phone": {
17027
+ "type": "string",
17028
+ "description": "Phone to verify. When given, it replaces the user's phone (normalised to E.164 with the account's `default_country_iso` as fallback) before the code is sent. When omitted, the code goes to the phone already on the user."
17029
+ }
17030
+ },
17031
+ "additionalProperties": false
17032
+ }
17033
+ }
17034
+ }
17035
+ },
17036
+ "parameters": [
17037
+ {
17038
+ "schema": {
17039
+ "type": "string"
17040
+ },
17041
+ "in": "path",
17042
+ "name": "user_id",
17043
+ "required": true
17044
+ }
17045
+ ],
17046
+ "responses": {
17047
+ "200": {
17048
+ "description": "Default Response",
17049
+ "content": {
17050
+ "application/json": {
17051
+ "schema": {
17052
+ "type": "object",
17053
+ "required": [
17054
+ "status",
17055
+ "destination_masked",
17056
+ "state",
17057
+ "expires_in"
17058
+ ],
17059
+ "properties": {
17060
+ "status": {
17061
+ "type": "string",
17062
+ "enum": [
17063
+ "sent"
17064
+ ]
17065
+ },
17066
+ "destination_masked": {
17067
+ "type": "string"
17068
+ },
17069
+ "state": {
17070
+ "type": "string",
17071
+ "description": "Opaque handle to confirm with. It is what lets a tenant backend start the verification (M2M) and send the person to `/flow/verify-phone?state=…` without a session."
17072
+ },
17073
+ "expires_in": {
17074
+ "type": "integer"
17075
+ }
17076
+ }
17077
+ }
17078
+ }
17079
+ }
17080
+ }
17081
+ }
17082
+ }
17083
+ },
17084
+ "/verify-phone/confirm": {
17085
+ "post": {
17086
+ "operationId": "user/verifyPhoneConfirm",
17087
+ "summary": "Confirm a phone verification code",
17088
+ "tags": [
17089
+ "user"
17090
+ ],
17091
+ "description": "Marks the phone verified (`phone_verified_method: sms_otp`) when the code matches the pending verification identified by `state`. Five wrong codes burn the `state`; start again. No session needed: the `state` plus the code are the proof.",
17092
+ "requestBody": {
17093
+ "required": true,
17094
+ "content": {
17095
+ "application/json": {
17096
+ "schema": {
17097
+ "type": "object",
17098
+ "required": [
17099
+ "state",
17100
+ "code"
17101
+ ],
17102
+ "properties": {
17103
+ "state": {
17104
+ "type": "string"
17105
+ },
17106
+ "code": {
17107
+ "type": "string",
17108
+ "minLength": 4,
17109
+ "maxLength": 12
17110
+ }
17111
+ },
17112
+ "additionalProperties": false
17113
+ }
17114
+ }
17115
+ }
17116
+ },
17117
+ "responses": {
17118
+ "200": {
17119
+ "description": "Default Response",
17120
+ "content": {
17121
+ "application/json": {
17122
+ "schema": {
17123
+ "type": "object",
17124
+ "required": [
17125
+ "status",
17126
+ "user_id"
17127
+ ],
17128
+ "properties": {
17129
+ "status": {
17130
+ "type": "string",
17131
+ "enum": [
17132
+ "verified"
17133
+ ]
17134
+ },
17135
+ "user_id": {
17136
+ "type": "string"
17137
+ }
17138
+ }
17139
+ }
17140
+ }
17141
+ }
17142
+ }
17143
+ }
17144
+ }
17145
+ },
16818
17146
  "/user/{user_id}/factors": {
16819
17147
  "get": {
16820
17148
  "operationId": "user/factors",
@@ -31526,6 +31854,12 @@
31526
31854
  "federated"
31527
31855
  ]
31528
31856
  },
31857
+ {
31858
+ "type": "string",
31859
+ "enum": [
31860
+ "sms_otp"
31861
+ ]
31862
+ },
31529
31863
  {
31530
31864
  "type": "null"
31531
31865
  }
@@ -31613,11 +31947,17 @@
31613
31947
  "federated"
31614
31948
  ]
31615
31949
  },
31950
+ {
31951
+ "type": "string",
31952
+ "enum": [
31953
+ "sms_otp"
31954
+ ]
31955
+ },
31616
31956
  {
31617
31957
  "type": "null"
31618
31958
  }
31619
31959
  ],
31620
- "description": "How `phone_verified` was last set. Same enum as `email_verified_method`."
31960
+ "description": "How `phone_verified` was last set. Same enum as `email_verified_method`, plus `sms_otp` — the user typed a code sent by SMS (`POST /user/:id/verify-phone/start`)."
31621
31961
  },
31622
31962
  "phone_verified_at": {
31623
31963
  "type": "string",
@@ -33567,6 +33907,39 @@
33567
33907
  "properties": {
33568
33908
  "email": {
33569
33909
  "type": "string"
33910
+ },
33911
+ "channel": {
33912
+ "anyOf": [
33913
+ {
33914
+ "anyOf": [
33915
+ {
33916
+ "type": "string",
33917
+ "enum": [
33918
+ "email"
33919
+ ]
33920
+ },
33921
+ {
33922
+ "type": "string",
33923
+ "enum": [
33924
+ "sms"
33925
+ ]
33926
+ },
33927
+ {
33928
+ "type": "string",
33929
+ "enum": [
33930
+ "whatsapp"
33931
+ ]
33932
+ },
33933
+ {
33934
+ "type": "string",
33935
+ "enum": [
33936
+ "factor"
33937
+ ]
33938
+ }
33939
+ ]
33940
+ }
33941
+ ],
33942
+ "description": "How to deliver the reset: `email` (link), `sms` / `whatsapp` (a 6-digit code to the verified phone on file). Silently falls back to the tenant default when the channel is not available for this user — the response never says which channels an account has."
33570
33943
  }
33571
33944
  }
33572
33945
  }
@@ -33661,6 +34034,183 @@
33661
34034
  }
33662
34035
  }
33663
34036
  },
34037
+ "/reset-code/verify": {
34038
+ "post": {
34039
+ "operationId": "reset_code_verify",
34040
+ "summary": "Redeem a password-reset code sent by SMS/WhatsApp",
34041
+ "tags": [
34042
+ "dbconnection"
34043
+ ],
34044
+ "description": "Second entry point to the new-password screen, for a reset delivered as a 6-digit code instead of a link. Answers the same `redirect_url` that the emailed link would land on. Five wrong codes consume the ticket; the error is always `invalid_code` and reveals nothing about the account.",
34045
+ "requestBody": {
34046
+ "required": true,
34047
+ "content": {
34048
+ "application/json": {
34049
+ "schema": {
34050
+ "type": "object",
34051
+ "required": [
34052
+ "email",
34053
+ "code"
34054
+ ],
34055
+ "properties": {
34056
+ "email": {
34057
+ "type": "string"
34058
+ },
34059
+ "code": {
34060
+ "type": "string",
34061
+ "minLength": 4,
34062
+ "maxLength": 12
34063
+ }
34064
+ },
34065
+ "additionalProperties": false
34066
+ }
34067
+ }
34068
+ }
34069
+ },
34070
+ "responses": {
34071
+ "200": {
34072
+ "description": "Default Response",
34073
+ "content": {
34074
+ "application/json": {
34075
+ "schema": {
34076
+ "type": "object",
34077
+ "required": [
34078
+ "redirect_url"
34079
+ ],
34080
+ "properties": {
34081
+ "redirect_url": {
34082
+ "type": "string"
34083
+ }
34084
+ }
34085
+ }
34086
+ }
34087
+ }
34088
+ }
34089
+ }
34090
+ }
34091
+ },
34092
+ "/dbconnections/recovery_options": {
34093
+ "post": {
34094
+ "operationId": "recovery_options",
34095
+ "summary": "Recovery channels to offer for an identifier",
34096
+ "tags": [
34097
+ "dbconnection"
34098
+ ],
34099
+ "description": "For the forgot-password screen. With the tenant's `visible` list empty (the default) it answers from configuration alone and never looks the account up. Otherwise it returns the channels the user can pick, with masked destinations.",
34100
+ "requestBody": {
34101
+ "required": true,
34102
+ "content": {
34103
+ "application/json": {
34104
+ "schema": {
34105
+ "type": "object",
34106
+ "required": [
34107
+ "email"
34108
+ ],
34109
+ "properties": {
34110
+ "email": {
34111
+ "type": "string"
34112
+ }
34113
+ },
34114
+ "additionalProperties": false
34115
+ }
34116
+ }
34117
+ }
34118
+ },
34119
+ "responses": {
34120
+ "200": {
34121
+ "description": "Default Response",
34122
+ "content": {
34123
+ "application/json": {
34124
+ "schema": {
34125
+ "type": "object",
34126
+ "required": [
34127
+ "picker",
34128
+ "default",
34129
+ "channels"
34130
+ ],
34131
+ "properties": {
34132
+ "picker": {
34133
+ "type": "boolean",
34134
+ "description": "Whether the screen should offer a choice. False when the tenant keeps `visible` empty — then nothing here depends on the account existing."
34135
+ },
34136
+ "default": {
34137
+ "anyOf": [
34138
+ {
34139
+ "type": "string",
34140
+ "enum": [
34141
+ "email"
34142
+ ]
34143
+ },
34144
+ {
34145
+ "type": "string",
34146
+ "enum": [
34147
+ "sms"
34148
+ ]
34149
+ },
34150
+ {
34151
+ "type": "string",
34152
+ "enum": [
34153
+ "whatsapp"
34154
+ ]
34155
+ },
34156
+ {
34157
+ "type": "string",
34158
+ "enum": [
34159
+ "factor"
34160
+ ]
34161
+ }
34162
+ ]
34163
+ },
34164
+ "channels": {
34165
+ "type": "array",
34166
+ "items": {
34167
+ "type": "object",
34168
+ "required": [
34169
+ "channel"
34170
+ ],
34171
+ "properties": {
34172
+ "channel": {
34173
+ "anyOf": [
34174
+ {
34175
+ "type": "string",
34176
+ "enum": [
34177
+ "email"
34178
+ ]
34179
+ },
34180
+ {
34181
+ "type": "string",
34182
+ "enum": [
34183
+ "sms"
34184
+ ]
34185
+ },
34186
+ {
34187
+ "type": "string",
34188
+ "enum": [
34189
+ "whatsapp"
34190
+ ]
34191
+ },
34192
+ {
34193
+ "type": "string",
34194
+ "enum": [
34195
+ "factor"
34196
+ ]
34197
+ }
34198
+ ]
34199
+ },
34200
+ "destination_masked": {
34201
+ "type": "string"
34202
+ }
34203
+ }
34204
+ }
34205
+ }
34206
+ }
34207
+ }
34208
+ }
34209
+ }
34210
+ }
34211
+ }
34212
+ }
34213
+ },
33664
34214
  "/dbconnections/signup": {
33665
34215
  "post": {
33666
34216
  "operationId": "signup",