Untitled

 avatar
unknown
plain_text
9 months ago
5.1 kB
13
Indexable
private void handleAccountChooserIfPresent() {
  final String original = driver.getWindowHandle();

  // 0) PROBE: czy chooser już jest otwarty? (np. otworzył się w trakcie poprzedniej metody)
  if (switchToChooserWindowIfOpen(Duration.ofSeconds(1))) {
    tryClickFirstOrPreferredAccount();
    driver.switchTo().window(original);
    return;
  }

  // 1) Jeśli nie ma – czekaj albo na przyrost okien, albo na pojawienie się okna z accounts.google.com
  final int initialCount = driver.getWindowHandles().size();
  try {
    new WebDriverWait(driver, Duration.ofSeconds(15)).until(drv -> {
      // warunek 1: przybyło okno
      if (drv.getWindowHandles().size() > initialCount) return true;
      // warunek 2: istnieje już chooser (czasem otwiera się bez zmiany count, ale zwykle i tak rośnie)
      return chooserHandle(drv).isPresent();
    });
  } catch (TimeoutException te) {
    logger.atInfo().log("Account chooser window not detected; continue.");
    return;
  }

  // 2) przełącz na chooser (teraz powinien już istnieć)
  if (!switchToChooserWindowIfOpen(Duration.ofSeconds(5))) {
    logger.atInfo().log("Account chooser handle still not found after wait; continue.");
    return;
  }

  try {
    tryClickFirstOrPreferredAccount();
  } finally {
    driver.switchTo().window(original);
  }
}

/** Znajdź i przełącz na okno z account chooserem (po URL/tytule). */
private boolean switchToChooserWindowIfOpen(Duration scanTimeout) {
  long end = System.nanoTime() + scanTimeout.toNanos();
  while (System.nanoTime() < end) {
    Optional<String> chooser = chooserHandle(driver);
    if (chooser.isPresent()) {
      driver.switchTo().window(chooser.get());
      return true;
    }
    try { Thread.sleep(100); } catch (InterruptedException ignored) {}
  }
  return false;
}

/** Zwraca handle okna, którego URL/tytuł wygląda na Google Account Chooser. */
private Optional<String> chooserHandle(WebDriver drv) {
  for (String h : drv.getWindowHandles()) {
    try {
      drv.switchTo().window(h);
      String url = "";
      String title = "";
      try { url = drv.getCurrentUrl(); } catch (Exception ignored) {}
      try { title = drv.getTitle(); }   catch (Exception ignored) {}
      if ((url != null && url.contains("accounts.google.com"))
          || (title != null && title.toLowerCase().contains("choose an account"))) {
        return Optional.of(h);
      }
    } catch (NoSuchWindowException ignored) {
      // handle mógł już zniknąć – pomiń
    }
  }
  return Optional.empty();
}

private static final By accountCard = By.cssSelector("[data-identifier],[data-email]");
private static final By accountClickable = By.cssSelector("[role='link'],[jsname][tabindex]");
// jeśli chcesz – wpisz email; gdy null -> bierze pierwsze
private static final String PREFERRED_EMAIL = null;

/** Kliknij preferowane konto albo pierwsze z listy (z fallbackami na Actions/JS). */
private void tryClickFirstOrPreferredAccount() {
  WebDriverWait wait = new WebDriverWait(driver, Duration.ofSeconds(20));

  // lekkie potwierdzenie, że to chooser
  try {
    wait.until(ExpectedConditions.or(
        ExpectedConditions.urlContains("accounts.google.com"),
        ExpectedConditions.titleContains("Choose an account")));
  } catch (TimeoutException ignored) { /* miękko */ }

  WebElement card;
  if (PREFERRED_EMAIL != null) {
    card = wait.until(d -> d.findElements(accountCard).stream()
        .filter(e -> {
          String id = Optional.ofNullable(e.getAttribute("data-identifier"))
                              .orElse(e.getAttribute("data-email"));
          return PREFERRED_EMAIL.equalsIgnoreCase(id);
        })
        .findFirst().orElse(null));
    if (card == null) {
      logger.atInfo().log("Preferred email '%s' not found; using first account.", PREFERRED_EMAIL);
      card = wait.until(ExpectedConditions.presenceOfElementLocated(accountCard));
    }
  } else {
    card = wait.until(ExpectedConditions.presenceOfElementLocated(accountCard));
  }

  WebElement clickable;
  try {
    clickable = card.findElement(By.xpath("ancestor-or-self::*[@role='link'][1]"));
  } catch (NoSuchElementException e) {
    clickable = card.findElement(accountClickable);
  }

  ((JavascriptExecutor) driver).executeScript("arguments[0].scrollIntoView({block:'center'})", clickable);

  try {
    wait.until(ExpectedConditions.elementToBeClickable(clickable));
    clickable.click();
    logger.atInfo().log("Clicked account (native).");
  } catch (Exception e1) {
    try {
      new Actions(driver).moveToElement(clickable).pause(Duration.ofMillis(80)).click().perform();
      logger.atInfo().log("Clicked account (Actions).");
    } catch (Exception e2) {
      ((JavascriptExecutor) driver).executeScript(
          "const el=arguments[0].closest('[role=\"link\"]')||arguments[0]; el.click();", clickable);
      logger.atInfo().log("Clicked account (JS).");
    }
  }
}
Editor is loading...
Leave a Comment