Использование JSoup для входа по URL (Java) - PullRequest
0 голосов
/ 03 марта 2019

Я пытаюсь войти на веб-страницу обычным способом, чтобы перебирать / извлекать данные.С входом в систему все работает нормально, но в ответ я получаю HTML-страницу с надписью «Вход в систему, пожалуйста, подождите».

Требуемая страница возврата является последней в последовательности'.

Есть ли способ пропустить это?Что-то, что я пропустил?

Извините, если это дубликат, я перечитал StackOverflow, не найдя ничего подобного.

Код выглядит так:

public static void main(String[] args) throws IOException, ParseException{
    final String USER_AGENT = "\"Mozilla/5.0 (Windows NT\" +\n" +
    "          \" 6.1; WOW64) AppleWebKit/535.2 (KHTML, like Gecko) Chrome/15.0.874.120 Safari/535.2\"";
    String username = "xxx";
    String password = "xxx";
    HashMap<String, String> cookies = new HashMap<>();
    HashMap<String, String> formData = new HashMap<>();
    String loginFormUrl = "https://id.ice.no/oauth2/account/login?returnUrl=%2Foauth2%2Fconnect%2Fauthorize%2Fcallback%3Fclient_id%3DSelfService%26redirect_uri%3Dhttps%253A%252F%252Fminside.ice.no%252Fsignin-callback.html%26response_type%3Did_token%2520token%26scope%3Dopenid%2520profile%2520roles%2520SelfService%26state%3D7f6047df0ddd4949b2992761ed98dd3b%26nonce%3Dbfc111c39548438c9a39b327c745947f%26acr_values%3DreturnUrl%2520Lw%253D%253D";
    String loginActionUrl= "https://id.ice.no/oauth2/account/login?returnUrl=%2Foauth2%2Fconnect%2Fauthorize%2Fcallback%3Fclient_id%3DSelfService%26redirect_uri%3Dhttps%253A%252F%252Fminside.ice.no%252Fsignin-callback.html%26response_type%3Did_token%2520token%26scope%3Dopenid%2520profile%2520roles%2520SelfService%26state%3D6ef2cad2efd24b3db7d61343aacc29f5%26nonce%3Db8b29eea53ae4952b8ffec5c43a9882a%26acr_values%3DreturnUrl%2520L2Fib25uZW1lbnQvMTYxODYwNjIvc2VuZHNtcw%253D%253D";
    Connection.Response loginForm = Jsoup.connect(loginFormUrl).method(Connection.Method.GET).userAgent(USER_AGENT).execute();
    Document loginDoc = loginForm.parse(); // this is the document that contains response html
    cookies.putAll(loginForm.cookies()); // save the cookies, this will be passed on to next request

    formData.put("username", username);
    formData.put("Password", password);
    String authToken = loginDoc.select("#form > input[type=hidden]:nth-child(8)")
      .first()
      .attr("value");
    formData.put("__RequestVerificationToken", authToken);

    Connection.Response homePage = Jsoup.connect(loginActionUrl)
   .cookies(cookies)
   .data(formData)
   .method(Connection.Method.POST)
   .userAgent(USER_AGENT)
   .execute();


   System.out.println(homePage.parse().html());

1 Ответ

0 голосов
/ 03 марта 2019

Трудно сказать без реального логина и пароля, чтобы проверить, что там происходит, поэтому мне придется угадывать.Несколько замечаний:

  1. Ввод с именем пользователя имеет имя Username, но вы устанавливаете formData с помощью username.Это может вызвать проблемы.

  2. Форма входа имеет несколько входов, но вы только вводите имя пользователя, пароль и токен.Это может вызвать проблемы.Вы должны всегда включать все поля, поэтому вам не хватает:

String returnUrl = loginDoc.select("input[name=ReturnUrl]").first().attr("value");
formData.put("ReturnUrl", returnUrl);
formData.put("RememberLogin", "false");
formData.put("button", "login");

Для отладчика пользовательского браузера всегда полезно посмотреть, какие данные действительно отправляются: enter image description here

Если это работает, это не проблема, но мне не нравится, как вы получаете токен.Вместо:
String authToken = loginDoc.select("#form > input[type=hidden]:nth-child(8)").first().attr("value");

Вы можете просто использовать:

String authToken = loginDoc.select("input[name=__RequestVerificationToken]").first().attr("value");
Это может быть самым важным.Я ожидаю, что есть страница, которая перенаправляет ваш браузер на URL, определенный в ReturnUrl.Jsoup не может обрабатывать перенаправления JavaScript, поэтому вы должны запросить эту страницу вручную.На самом деле это то, что ваш браузер будет делать в любом случае - сделать еще один запрос с последними куки.Вы на правильном пути, поэтому в конце вашего кода вы должны дополнительно получить нужную страницу с полученными файлами cookie:
 cookies.putAll(homePage.cookies());// get the cookies after successful login
 Connection.Response finalPage = Jsoup.connect(returnUrl) //this should be the URL of the page you want to visit in the first place
   .cookies(cookies)
   .userAgent(USER_AGENT)
   .execute();

РЕДАКТИРОВАТЬ: О, это действительно правильные учетные данные.Но я вижу, что на вкладке Сеть отладчика Chrome происходит больше перенаправлений.Это сложно, так как части нового URL генерируются Javascript.Чтобы преодолеть ограничения Jsoup, попробуйте использовать Selenium Webdriver.

...