2929import org .openqa .selenium .TimeoutException ;
3030import org .openqa .selenium .WebDriver ;
3131import org .openqa .selenium .WebElement ;
32+ import org .openqa .selenium .support .ui .ExpectedCondition ;
3233import org .openqa .selenium .support .ui .ExpectedConditions ;
3334import org .openqa .selenium .support .ui .WebDriverWait ;
3435import org .parosproxy .paros .Constant ;
@@ -51,6 +52,7 @@ public final class MsLoginAuthenticator implements Authenticator {
5152 private static final By PASSWORD_FIELD = By .id ("i0118" );
5253 private static final By SUBMIT_BUTTON = By .id ("idSIButton9" );
5354 private static final By KMSI_FIELD = By .id ("KmsiCheckboxField" );
55+ private static final By PROOF_REDIRECT_FIELD = By .id ("idSubmit_ProofUp_Redirect" );
5456
5557 private enum State {
5658 START ,
@@ -61,6 +63,9 @@ private enum State {
6163
6264 POST_PASSWORD ,
6365 STAY_SIGNED_IN ,
66+
67+ PROOF_REDIRECT ,
68+ PROOF ,
6469 }
6570
6671 @ Override
@@ -177,7 +182,13 @@ private Result authenticateImpl(
177182 Constant .messages .getString (
178183 "authhelper.auth.method.diags.steps.ms.stepchoice" ));
179184
180- // XXX There might be a proof step too…
185+ try {
186+ waitForElement (wd , PROOF_REDIRECT_FIELD );
187+ states .add (State .PROOF_REDIRECT );
188+ break ;
189+ } catch (TimeoutException e ) {
190+ // Ignore, there's still the next step to check.
191+ }
181192
182193 try {
183194 waitForElement (wd , KMSI_FIELD );
@@ -206,15 +217,55 @@ private Result authenticateImpl(
206217 states .add (State .SUBMIT );
207218 states .add (State .POST_PASSWORD );
208219 break ;
220+
221+ case PROOF_REDIRECT :
222+ WebElement proofElement = wd .findElement (PROOF_REDIRECT_FIELD );
223+ proofElement .click ();
224+ diags .recordStep (
225+ wd ,
226+ Constant .messages .getString (
227+ "authhelper.auth.method.diags.steps.ms.clickproofredirect" ),
228+ proofElement );
229+
230+ states .add (State .PROOF );
231+ break ;
232+
233+ case PROOF :
234+ try {
235+ WebElement skipElement =
236+ waitForElement (
237+ wd ,
238+ new ElementWithText (By .tagName ("button" ), "Skip setup" ));
239+ skipElement .click ();
240+ diags .recordStep (
241+ wd ,
242+ Constant .messages .getString (
243+ "authhelper.auth.method.diags.steps.ms.clickproofskip" ),
244+ skipElement );
245+
246+ states .add (State .POST_PASSWORD );
247+ break ;
248+ } catch (TimeoutException e ) {
249+ diags .recordStep (
250+ wd ,
251+ Constant .messages .getString (
252+ "authhelper.auth.method.diags.steps.ms.stepproofunknown" ));
253+ LOGGER .debug (
254+ "Still in proof but no skip setup button found, assuming unsuccessful login." );
255+ break ;
256+ }
209257 }
210258 } while (!states .isEmpty ());
211259
212260 return new Result (true , successful , userField , pwdField );
213261 }
214262
215263 private WebElement waitForElement (WebDriver wd , By by ) {
216- return new WebDriverWait (wd , DEFAULT_WAIT_UNTIL )
217- .until (ExpectedConditions .elementToBeClickable (by ));
264+ return waitForElement (wd , ExpectedConditions .elementToBeClickable (by ));
265+ }
266+
267+ private WebElement waitForElement (WebDriver wd , ExpectedCondition <WebElement > condition ) {
268+ return new WebDriverWait (wd , DEFAULT_WAIT_UNTIL ).until (condition );
218269 }
219270
220271 private static boolean isMsLoginFlow (WebDriver wd ) {
@@ -230,4 +281,28 @@ private static boolean isMsLoginFlow(WebDriver wd, Duration duration) {
230281 return false ;
231282 }
232283 }
284+
285+ private static class ElementWithText implements ExpectedCondition <WebElement > {
286+
287+ private final By locator ;
288+ private final String text ;
289+
290+ ElementWithText (By locator , String text ) {
291+ this .locator = locator ;
292+ this .text = text ;
293+ }
294+
295+ @ Override
296+ public WebElement apply (WebDriver driver ) {
297+ return driver .findElements (locator ).stream ()
298+ .filter (e -> text .equalsIgnoreCase (e .getText ()))
299+ .findFirst ()
300+ .orElse (null );
301+ }
302+
303+ @ Override
304+ public String toString () {
305+ return String .format ("element '%s' with text '%s' is not present" , locator , text );
306+ }
307+ }
233308}
0 commit comments