@@ -22,7 +22,12 @@ import {
2222 changeEmail ,
2323 getLatestURLWithToken ,
2424} from "../helpers" ;
25- import { tryWebauthnSignUp } from "./webauthn.helpers" ;
25+ import {
26+ openRecoveryAccountPage ,
27+ tryWebauthnSignUp ,
28+ getTokenFromEmail ,
29+ openRecoveryWithToken ,
30+ } from "./webauthn.helpers" ;
2631import assert from "assert" ;
2732
2833/*
@@ -139,7 +144,7 @@ describe("SuperTokens WebAuthn Account Linking", function () {
139144 ) ;
140145 } ) ;
141146
142- it ( "should handle email updates correctly for user that signed up with webauthn" , async ( ) => {
147+ it . only ( "should handle email updates correctly for user that signed up with webauthn" , async ( ) => {
143148 await page . evaluate ( ( ) => window . localStorage . setItem ( "mode" , "REQUIRED" ) ) ;
144149 await setAccountLinkingConfig ( false , false ) ;
145150 const email = await getTestEmail ( ) ;
@@ -178,4 +183,64 @@ describe("SuperTokens WebAuthn Account Linking", function () {
178183
179184 await page . waitForTimeout ( 4000 ) ;
180185 } ) ;
186+
187+ it ( "should allow same emails to be linked but requiring verification" , async ( ) => {
188+ await setAccountLinkingConfig ( true , true , true ) ;
189+ await page . evaluate ( ( ) => window . localStorage . setItem ( "mode" , "REQUIRED" ) ) ;
190+ const email = await getTestEmail ( ) ;
191+
192+ await Promise . all ( [
193+ page . goto ( `${ TEST_CLIENT_BASE_URL } /auth?authRecipe=passwordless` ) ,
194+ page . waitForNavigation ( { waitUntil : "networkidle0" } ) ,
195+ ] ) ;
196+
197+ // Signup using the email
198+ await setInputValues ( page , [ { name : "email" , value : email } ] ) ;
199+ await submitForm ( page ) ;
200+
201+ await waitForSTElement ( page , "[data-supertokens~=input][name=userInputCode]" ) ;
202+
203+ const loginAttemptInfo = JSON . parse (
204+ await page . evaluate ( ( ) => localStorage . getItem ( "supertokens-passwordless-loginAttemptInfo" ) )
205+ ) ;
206+ const device = await getPasswordlessDevice ( loginAttemptInfo ) ;
207+ await setInputValues ( page , [ { name : "userInputCode" , value : device . codes [ 0 ] . userInputCode } ] ) ;
208+ await submitForm ( page ) ;
209+ await page . waitForTimeout ( 2000 ) ;
210+
211+ // Find the div with classname logoutButton and click it using normal
212+ // puppeteer selector
213+ const logoutButton = await page . waitForSelector ( "div.logoutButton" ) ;
214+ await logoutButton . click ( ) ;
215+ await new Promise ( ( res ) => setTimeout ( res , 1000 ) ) ;
216+
217+ // Try to signup with the same email through webauthn now
218+ // await tryWebauthnSignUp(page, email);
219+
220+ // // We should be in the confirmation page now.
221+ // await submitForm(page);
222+
223+ // Try to recover the webauthn account using the same email
224+ await openRecoveryAccountPage ( page , email , true ) ;
225+ await page . waitForTimeout ( 1000 ) ;
226+
227+ // Get the token from the email
228+ const token = await getTokenFromEmail ( email ) ;
229+ console . log ( token ) ;
230+ assert . ok ( token ) ;
231+
232+ // Use the token to recover the account
233+ await openRecoveryWithToken ( page , token ) ;
234+
235+ // We should be in the recovery page now, click the continue button
236+ await submitFormUnsafe ( page ) ;
237+
238+ await new Promise ( ( res ) => setTimeout ( res , 2000 ) ) ;
239+
240+ const successContainer = await waitForSTElement ( page , "[data-supertokens~='headerText']" ) ;
241+ const headerText = await successContainer . evaluate ( ( el ) => el . textContent ) ;
242+
243+ // Assert the text contains "Account recovered successfully!"
244+ assert . deepStrictEqual ( headerText , "Account recovered successfully!" ) ;
245+ } ) ;
181246} ) ;
0 commit comments