Самый простой способ перейти на страницу и отправить форму в Java

Что мне нужно сделать, так это перейти на веб-страницу, войти в систему, а затем перейти на другую веб-страницу на этом сайте, которая требует, чтобы вы вошли в систему, поэтому она должна сохранять файлы cookie. После этого мне нужно щелкнуть элемент на этой странице, в котором я бы заполнил форму и получил сообщение о том, что веб-страница возвращает мне. Причина, по которой мне нужно на самом деле перейти на страницу и нажать кнопку, как если бы я просто перешел непосредственно к ссылке, заключается в том, что вам назначается идентификатор сеанса каждый раз, когда вы входите в систему и нажимаете ссылку, и он всегда отличается. Кнопка выглядит так, это не обычная ссылка href:

<span id=":tv" idlink="" class="sA" tabindex="0" role="link">Next</span>

В любом случае, как проще всего это сделать? Спасибо.

Обновление: после того, как вы попробовали HTMLunit и другие безголовые библиотеки браузера, не похоже, что это происходит с использованием чего-либо «безголового». Еще одна вещь, которую я недавно узнал об этой странице, заключается в том, что весь HTML-код имеет какой-то странный формат... Все это находится внутри тега script. Вот образец.

"?ui\x3d2\x26view\x3dss\x26mset\x3dmain\x26ver\x3d-68igm85d1771\x26am\x3d!Zsl-0RZ-XLv0BO3aNKsL0sgMg3nH10t5WrPgJSU8CYS-KNWlyrLmiW3HvC5ykER_n_5dDw\x26fri"],"http://example.com/?ctx\x3d%67mail\x26hl\x3den",,0,"Gmail","Gmail",[["us","c130f0854ca2c2bb",[["n"],["m","New features!"],["u"],["k","0"],["p","1000:500000,10,200000,5,100000,3,75000,2,0,1"],["h","https://survey.googleratings.com/wix/p1679258.aspx?l\x3d1033"],["at","query,5,contacts,5,adv,5,cf,5,default,20"],["v","https://www.youtube.com/embed/Ra8HG6MkOXY?showinfo\x3d0"],

Когда я проверяю элемент на кнопке, HTML-код, который я разместил выше для кнопки, появляется, но не при просмотре исходного кода. По сути, мне нужно будет использовать какой-то графический интерфейс, чтобы пользователь перешел по ссылке, а затем программа заполнила информацию. Кто-нибудь знает, как я могу это сделать? Спасибо.


person user1947236    schedule 06.02.2013    source источник
comment
Попробуйте Selenium и Selenium IDE. В Интернете можно найти множество статей и руководств, которые помогут вам приступить к работе за несколько часов.   -  person bakoyaro    schedule 13.02.2013


Ответы (6)


Это должно быть возможно в Selenium, как отмечали другие.

Я использовал Selenium для входа в систему, затем просматривал сайт и обнаруживал каждую перестановку значений для каждой формы на сайте (более 30 форм). Эти значения позже используются для заполнения и отправки формы с определенным перебором значений. Этот сайт был очень тяжелым для JS/jQuery, и для этого я использовал встроенную в Selenium поддержку исполнителя javascript, селекторов css и XPath.

Я реализовал HtmlUnit и HttpUnit как более быстрые альтернативы, но обнаружил, что они не так надежны, как Selenium, учитывая семантику JS сайта, который я сканировал.

Трудно дать вам код о том, как это сделать, потому что ваша реализация Selenium будет довольно специфичной для страницы, и я не могу посмотреть на страницу, для которой вы кодируете, чтобы понять, что происходит с этим мусором скрипта кнопки. Тем не менее, я включил некоторые, возможно, соответствующие фрагменты кода селена (Java):

Element element = driver.findElements(By.id(value)); //find element on page
List<Element> buttons = parent.findElements(By.xpath("./tr/td/button")); //find child element
button.click();
element.submit() //submit enclosing form
element.sendKeys(text); //enter text in an input
String elementText = (String) ((JavascriptExecutor) driver).executeScript("return arguments[0].innerText || arguments[0].textContent", element); //interact with a selenium element via JS

Если вы программируете похожие функции на разных страницах, вам могут помочь PageObjects за интерфейсами.

Ссылка, опубликованная Anew, является хорошей отправной точкой, и в старом добром StackOverflow есть ответы практически на любую проблему Selenium.

person Marquee    schedule 16.02.2013

Ознакомьтесь с 5-минутным руководством по началу работы с Selenium: http://code.google.com/p/selenium/wiki/GettingStarted

person Anew    schedule 09.02.2013
comment
Еще один бесценный инструмент в этом стеке — подключаемый модуль SeleniumIDE для Firefox. Это позволяет вам записывать ваши действия на странице, а затем экспортировать взаимодействие в код Java. - person bakoyaro; 13.02.2013

На странице входа просмотрите HTML-код формы, чтобы увидеть URL-адрес, на который она отправляется, и параметры URL-адреса. Затем запросите этот URL-адрес с теми же параметрами, заполненными правильной информацией, и обязательно сохраните все заголовки файлов cookie для отправки на вторую страницу. Затем используйте парсер html, чтобы найти вашу ссылку. На sourceforge доступно несколько парсеров html, и вы даже можете попробовать встроенные в Java парсеры xml, хотя, если на сайте есть хотя бы крошечная ошибка html, они будут глючить.

EDIT не заметил того факта, что это не обычная ссылка. В этом случае вам нужно будет посмотреть на javascript сайта, чтобы увидеть, куда ведет ссылка. Если ссылка требует запуска javascript, все становится сложнее. Java не может выполнять javascript браузера, но я нашел библиотеку под названием DJ native swing, которая включает класс веб-браузера, который вы можете добавить в jframes. Он использует ваш собственный браузер для рендеринга и запуска javascript.

person DankMemes    schedule 06.02.2013
comment
Возможно ли, чтобы пользователь вручную переходил на страницу с помощью библиотеки браузера с графическим интерфейсом, а библиотека заполняла формы для пользователя из кода? Это использование DJ Native. - person user1947236; 07.02.2013
comment
Да, конечно. Это хорошее решение. Посмотрите свинговую библиотеку DJ Native. Добавить веб-браузер в вашу рамку так же просто, как JWebBrowser b=new JWebBrowser(); frame.add(b); - person DankMemes; 08.02.2013
comment
Пожалуйста, смотрите редактирование поста. Есть ли способ включить такую ​​​​библиотеку графического интерфейса, но затем программно заполнить форму на странице? Я бы попросил пользователя перейти на страницу, а затем программа заполнила бы формы/нажала кнопки и т.д. - person user1947236; 08.02.2013

Вместо того, чтобы пытаться просматривать программно, попробуйте выполнить запрос на вход и сохранить файлы cookie, а затем установить их в следующем запросе в сообщение формы.

person scott    schedule 09.02.2013

HTMLUnit довольно плохо справляется с обработкой JavaScript, библиотека Rhino JS часто выдает ошибки (фактически отсутствие ошибок является большим исключением). Я бы посоветовал использовать Selenium, который в основном представляет собой фреймворк для управления безголовыми браузерами (на основе Chrome, Firefox).

Для вашего вопроса следующий код выполнит работу

selenium.open(myurl);
selenium.click("id=:tv");

Затем вам нужно дождаться загрузки страницы

selenium.waitForPageToLoad(someTime);
person Julien    schedule 15.02.2013

Я бы порекомендовал htmlunit в любой день. Это отличная библиотека.

Сначала посетите их веб-страницу (http://htmlunit.sourceforge.net/), чтобы получить htmlunit и Бег. Убедитесь, что вы используете последний снимок (2.12 при написании этого)

Попробуйте эти настройки, чтобы игнорировать практически любое препятствие:

WebClient webClient = new WebClient(BrowserVersion.FIREFOX_17);
webClient.getOptions().setRedirectEnabled(true);
webClient.getOptions().setCssEnabled(false);
webClient.getOptions().setThrowExceptionOnScriptError(false);
webClient.getOptions().setThrowExceptionOnFailingStatusCode(false);
webClient.getOptions().setUseInsecureSSL(true);
webClient.getOptions().setJavaScriptEnabled(true);
webClient.getCookieManager().setCookiesEnabled(true);

Затем, загружая свою страницу, убедитесь, что вы ждете фонового Javascript, прежде чем что-либо делать со страницей, например, размещать форму входа:

//Get Page
HtmlPage page1 = webClient.getPage("https://login-url/");

//Wait for background Javascript
webClient.waitForBackgroundJavaScript(10000);

//Get first form on page
HtmlForm form = page1.getForms().get(0);

//Get login input fields using input field name
HtmlTextInput userName = form.getInputByName("UserName");
HtmlPasswordInput password = form.getInputByName("Password");

//Set input values
userName.setValueAttribute("MyUserName"); 
password.setValueAttribute("MyPassword"); 

//Find the first button in form using name, id or xpath
HtmlElement button = (HtmlElement) form.getFirstByXPath("//button");

//Post by clicking the button and cast the result, login arrival url, to a new page and repeat what you did with page1 or something else :) 
HtmlPage page2 = (HtmlPage) button.click(); 

//Profit
System.out.println(page2.asXml());    

Я надеюсь, что этот базовый пример поможет вам!

person OakNinja    schedule 15.02.2013