【问题标题】:Why do I get an error 500 when I send POST data to an ASP.NET MVC site through Android?当我通过 Android 向 ASP.NET MVC 站点发送 POST 数据时,为什么会收到错误 500?
【发布时间】:2011-05-21 15:45:55
【问题描述】:

我正在尝试创建一个 Android 应用来检查我在工程学校的考试成绩。为了下载包含分数的 Word,我需要登录门户。

我认为发送 POST 请求会很简单。

由于此页面上的代码绕过了自签名证书(或其他)的问题:Self-signed SSL acceptance on Android

我在尝试向登录页面发送任何 POST 请求时仍然收到 500 错误,登录页面如下:https://e-campus.hei.fr/ERP-prod/pc_mv_login.aspx

我尝试了网络上的各种代码来发送 POST 数据(尤其是 How to do a HTTP Post in Android? 这个)。即使在纯 Java 应用程序上,我也能得到 500。

当我将 URL 指向另一个测试页面时,我设法让它工作,但不是在 https://e-campus.hei.fr/ERP-prod/pc_mv_login.aspx

谁能向我解释为什么它不起作用或帮助我摆脱这个错误?

编辑: 这是通过我的浏览器发送的内容(根据 chrome 开发者工具)

__EVENTTARGET:
__EVENTARGUMENT:
__VIEWSTATE:dDwxNDU4ODc4MDI5O3Q8O2w8aTwwPjs+O2w8dDw7bDxpPDE+O2k8Nz47aTwxMz47aTwxNT47aTwxNz47aTwxOT47PjtsPHQ8cDxwPGw8VGV4dDs+O2w8SWRlbnRpZmlhbnQgOjs+Pjs+Ozs+O3Q8cDxwPGw8VGV4dDs+O2w8TW90IGRlIHBhc3NlIDo7Pj47Pjs7Pjt0PHA8cDxsPFRleHQ7PjtsPExhbmd1ZSA6Oz4+Oz47Oz47dDx0PDt0PGk8Mj47QDxBbmdsYWlzO0ZyYW7Dp2Fpczs+O0A8ZW47ZnI7Pj47bDxpPDE+Oz4+Ozs+O3Q8cDxwPGw8VGV4dDs+O2w8Vm91cyBuJ8OqdGVzIHBhcyBhdXRvcmlzw6kgIMOgIHZvdXMgY29ubmVjdGVyLjs+Pjs+Ozs+O3Q8cDxwPGw8VGV4dDs+O2w8Q29ubmVjdGVyIDo7Pj47Pjs7Pjs+Pjs+Pjs+inmhCwE9zfymuEXDXGORShkB1GI=
Username:******
Password:******
Langues:fr
Button1:Connecter :

这是我发送的字符串:

String parameters = "__EVENTTARGET=&__EVENTARGUMENT=&__VIEWSTATE="
            + URLEncoder
                    .encode("dDwxNDU4ODc4MDI5O3Q8O2w8aTwwPjs+O2w8dDw7bDxpPDE+O2k8Nz47aTwxMz47aTwxNT47aTwxNz47aTwxOT47PjtsPHQ8cDxwPGw8VGV4dDs+O2w8SWRlbnRpZmlhbnQgOjs+Pjs+Ozs+O3Q8cDxwPGw8VGV4dDs+O2w8TW90IGRlIHBhc3NlIDo7Pj47Pjs7Pjt0PHA8cDxsPFRleHQ7PjtsPExhbmd1ZSA6Oz4+Oz47Oz47dDx0PDt0PGk8Mj47QDxBbmdsYWlzO0ZyYW7Dp2Fpczs+O0A8ZW47ZnI7Pj47bDxpPDE+Oz4+Ozs+O3Q8cDxwPGw8VGV4dDs+O2w8Vm91cyBuJ8OqdGVzIHBhcyBhdXRvcmlzw6kgIMOgIHZvdXMgY29ubmVjdGVyLjs+Pjs+Ozs+O3Q8cDxwPGw8VGV4dDs+O2w8Q29ubmVjdGVyIDo7Pj47Pjs7Pjs+Pjs+Pjs+inmhCwE9zfymuEXDXGORShkB1GI=",
                            "UTF-8") + "&Username="
            + URLEncoder.encode(mUsername, "UTF-8") + "&Password="
            + URLEncoder.encode(mPassword, "UTF-8")
            + "&Langues=fr&Button1="
            + URLEncoder.encode("Connecter :", "UTF-8");

【问题讨论】:

  • 你能发布发送的标题吗?
  • 我正在浏览页面源。在表单字段中,除了用户名和密码之外,还有 3 个字段:__EVENTTARGET、__EVENTARGUMENT 和 __VIEWSTATE。在您的代码中,您是否也在 POST 请求中发送这些值?

标签: java android asp.net


【解决方案1】:

HTTP 错误 500 仅表示服务器端代码失败。它有一个错误,例如NullPointerException 被扔到那里。如果响应正文不包含任何有意义的内容(例如堆栈跟踪),以便您可以了解它是如何引起的并相应地更改请求,那么您最好的办法是联系服务器管理员并在服务器代码中报告此错误并询问如何正确执行程序化登录。

如果由于某种原因这不是一个选项,那么您应该仔细检查您是否忘记发送特定的 cookie、标头和/或参数。可能是服务器端代码在期待它,但它是null,并且代码有问题,因此它完全打破了 500。我建议使用Firebug 来跟踪整个 HTTP 流量并将其与标头进行比较/您设置的参数。可能您需要发回特定的cookie?或者您需要发送提交按钮的名称=值对?等等。


更新:您发送了错误的 __VIEWSTATE 值。该网站在 ASP.NET MVC 上运行,这是一个基于组件的 MVC 框架(如 Java EE 中的 JSF)。它将组件树存储为“视图状态”。您不应将随机/不存在/无效的视图状态作为参数发送回,而应发送一个有效。您需要重写 HTTP 客户端,使其首先在带有表单的页面上触发 GET 请求,然后使用 HTML 解析器 (Jsoup?) 提取隐藏的 __VIEWSTATE 输入字段的值,最后触发 POST使用该值的请求(并且请求标头中的 cookie 完全相同!)。

就像在 JSF 中一样,视图状态是 CSRF 攻击预防的一部分。如果不先在同一会话中从网站本身请求表单,您就无法提交表单。


【讨论】:

  • 我完全明白如何提取 __VIEWSTATE,但我该如何传递相同的 cookie?
  • 在第一个请求时,服务器应该在响应中添加一个Set-Cookie 标头,指示会话ID。您需要在后续请求的 Cookie 标头中准确发送该 cookie name=value,以便维护会话。有关一些示例,另请参阅 stackoverflow.com/questions/2793150/…
  • 第二个 HTTPS 请求有这个问题吗?在发送第一个请求之前尝试设置以下系统属性:System.setProperty("http.keepAlive", "false");
  • 但是你说你有一个 HTTP 500?情况有变化吗?
  • 当我只尝试从我的笔记本电脑或 Android 发出 POST 请求时,我总是有一个 HTTP500。根据您的建议,我删除了所有内容并从头开始,当我简单地尝试 GET 时,我从笔记本电脑获得了 HTTP500,无论是“无受信任的服务器证书”还是 Android 的文件未找到异常。我不明白发生了什么事。我想我可能会放弃......
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2020-09-05
  • 2021-08-15
  • 1970-01-01
  • 2012-03-05
  • 2020-01-08
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多