如何在使用 java 设置用于屏幕抓取的表单值后调用 post 方法



背景:我有一个网页(.aspx(,其中下拉列表很少。列表值正在根据上一个下拉列表的选择使用 Ajax 调用进行填充。选择所有下拉列表的值后,我们可以单击下载按钮,数据将根据我们需要执行其他一些操作的下载数据进行下载。

我已经做了什么:我能够通过正确调用 ajax 来设置下拉数据,但发送 post 请求是一个问题。这是代码片段/伪代码。

随意使用任何工具以及java

public static void main(String[] args) throws FailingHttpStatusCodeException, IOException {
        final WebClient webClient = new WebClient(BrowserVersion.FIREFOX_17);

        WebRequest request = new WebRequest(new URL(DataDownloader.MY_URL),HttpMethod.POST);
        webClient.getOptions().setThrowExceptionOnScriptError(false);
        webClient.setJavaScriptTimeout(10000);
        webClient.getOptions().setJavaScriptEnabled(true);
        webClient.setAjaxController(new NicelyResynchronizingAjaxController());
        webClient.getOptions().setTimeout(10000);
        HtmlPage page = webClient.getPage(request);     
        HtmlSelect firstDd = (HtmlSelect) page.getElementById("dd1_id");
        List<HtmlOption> firstOption = firstDd.getOptions();
        firstDd.setSelectedAttribute(firstOption.get(2), true);
        webClient.waitForBackgroundJavaScript(3000);
        HtmlPage pgAfterFirstDd = (HtmlPage) webClient.getCurrentWindow().getEnclosedPage();
        HtmlSelect secondDd = (HtmlSelect) pgAfterFirstDd.getElementById("dd2_id");
        List<HtmlOption> secondOption = secondDd.getOptions();
        secondDd.setSelectedAttribute(secondOption.get(2), true);
        webClient.waitForBackgroundJavaScript(10000);
        //set the value for all other dropdowns

        HtmlPage finalpage = (HtmlPage) webClient.getCurrentWindow().getEnclosedPage();         
        HtmlForm form = finalpage.getHtmlElementById("aspnetForm");
        webClient.waitForBackgroundJavaScript(10000);

        request.setRequestBody("REQUESTBODY");
        Page redirectPage = webClient.getPage(request);
//       HtmlSubmitInput submitInput=form.getInputByName("btnSubmit");
//      submitInput.click();
        /*HtmlButton submitButton = (HtmlButton) pageAfterWard.createElement("btnSubmit");
        submitButton.setAttribute("type", "submit");
        form.appendChild(submitButton);
        HtmlPage nextPage = (HtmlPage) submitButton.click();*/
    }

为什么要隐藏错误详细信息?有什么秘密吗?如果你喜欢有用的答案,你必须提供尽可能多的信息。所以我做了一个疯狂的猜测...

submitInput.click();

将返回一个 PDF。在这种情况下,您必须执行以下操作

Page pdfPage = submitInput.click();
WebResponse resp = pdfPage.getWebResponse();
if("application/pdf".equals(resp.getContentType())) {
    .... process the bytes
    .... resp.getContentAsStream()
}

HtmlUnit有四种页面HtmlPage/XmlPage/TextPage和UnexpectedPage。二进制内容(如 PDF 或办公文档(作为意外页面处理。处理此内容由您决定。

正如您在RBRi的答案下的评论中提到的,您遇到了类型转换错误。

  • 您得到的确切错误是什么
  • 您期望的文件/响应类型。

因为代码对我来说看起来不错,而且应该可以完美运行。

final WebClient webClient = new WebClient(BrowserVersion.FIREFOX_17);

看起来您使用的是旧版本,请使用最新版本。

WebRequest request = new WebRequest(new URL(DataDownloader.MY_URL),HttpMethod.POST);

使用HtmlUnit,您通常不会处理请求。这个想法是工作更像"浏览器"。使用类似getPage(final URL url(的东西。

List<HtmlOption> firstOption = firstDd.getOptions();
firstDd.setSelectedAttribute(firstOption.get(2), true);

让你的工作更像"浏览器">

firstOption.get(2)setSelected(true);

这将为您完成所有后台工作,例如取消选择其他选项和事件处理。

关于提交您的想法的表格

 HtmlSubmitInput submitInput=form.getInputByName("btnSubmit");
 HtmlPage nextPage = submitInput.click();

看起来是正确的。也许你也必须在那之后等待。如果您仍然遇到问题,则必须提供您正在使用的 URL,以便我们重现/调试您的案例。

最新更新