问题描述
我有一个谷歌PNR查询应用程式。这是工作非常精细。但是最近印度Railwys添加CAPTCHA他们PNR调查部分,因为这个我不能够适当的数据传递到服务器,以获得适当的反应。如何添加这个验证码在我的应用程序在ImageView的形式,并要求用户也输入验证码资料,以便我可以把正确的数据,并得到适当的反应。
下面是我的PnrCheck.java我前面使用。请帮助应该在这里完成哪些修改。
进口java.io.BufferedReader中;
进口java.io.ByteArrayInputStream中;
进口java.io.IOException异常;
进口的java.io.InputStream;
进口java.io.InputStreamReader中;
进口的java.net.Socket;
进口的java.net.URL;
进口的java.util.ArrayList;
进口的java.util.List;进口org.apache.http.Header;
进口org.apache.http.HttpHost;
进口org.apache.http.Htt presponse;
进口org.apache.http.HttpVersion;
进口org.apache.http.entity.InputStreamEntity;
进口org.apache.http.impl.DefaultHttpClientConnection;
进口org.apache.http.message.BasicHttpEntityEnclosingRequest;
进口org.apache.http.params.BasicHttpParams;
进口org.apache.http.params.HttpParams;
进口org.apache.http.params.HttpProtocolParams;
进口org.apache.http.protocol.BasicHttpContext;
进口org.apache.http.protocol.BasicHttpProcessor;
进口org.apache.http.protocol.ExecutionContext;
进口org.apache.http.protocol.HttpContext;
进口org.apache.http.protocol.Htt prequestExecutor;
进口org.apache.http.protocol.RequestConnControl;
进口org.apache.http.protocol.RequestContent;
进口org.apache.http.protocol.RequestExpectContinue;
进口org.apache.http.protocol.RequestTargetHost;
进口org.apache.http.protocol.RequestUserAgent;
进口org.apache.http.util.EntityUtils;公共类PNRStatusCheck {
公共静态无效的主要(字符串ARGS []){
尝试{
字符串pnr1 =1154177041;
字符串reqStr =lccp_pnrno1 =+ pnr1 +&放大器; submitpnr =得+状态;
PNRStatusCheck检查=新PNRStatusCheck();
StringBuffer的数据= check.getPNRResponse(reqStrhttp://www.indianrail.gov.in/cgi_bin/inet_pnrstat_cgi.cgi);
如果(数据!= NULL){
@燮pressWarnings(未使用)
PNRStatus PNR = check.parseHtml(数据);
}
}赶上(例外五){
e.printStackTrace();
}
} 公共StringBuffer的getPNRResponse(字符串reqStr,字符串urlAddr)抛出异常{
字符串urlHost = NULL;
INT口;
字符串的方法= NULL;
尝试{
网址URL =新的URL(urlAddr);
urlHost = url.getHost();
端口= url.getPort();
方法= url.getFile(); //验证端口
如果(端口== -1){
端口= url.getDefaultPort();
}
}赶上(例外五){
e.printStackTrace();
抛出新的异常(E);
} 的HttpParams PARAMS =新BasicHttpParams();
HttpProtocolParams.setVersion(参数,可以HttpVersion.HTTP_1_1);
HttpProtocolParams.setContentCharset(参数,可以UTF-8);
HttpProtocolParams.setUserAgent(参数,可以HttpComponents / 1.1);
HttpProtocolParams.setUseExpectContinue(参数,可以真正的); BasicHttpProcessor httpproc =新BasicHttpProcessor();
//所需的协议拦截器
httpproc.addInterceptor(新RequestContent());
httpproc.addInterceptor(新RequestTargetHost());
//推荐协议拦截
httpproc.addInterceptor(新RequestConnControl());
httpproc.addInterceptor(新RequestUserAgent());
httpproc.addInterceptor(新RequestExpectContinue()); HTT prequestExecutor httpexecutor =新HTT prequestExecutor();
HttpContext的背景下=新BasicHttpContext(NULL);
HttpHost主机=新HttpHost(urlHost,口);
DefaultHttpClientConnection康恩=新DefaultHttpClientConnection(); context.setAttribute(ExecutionContext.HTTP_CONNECTION,康涅狄格州);
context.setAttribute(ExecutionContext.HTTP_TARGET_HOST,主机);
@燮pressWarnings(未使用)
字符串resData = NULL;
@燮pressWarnings(未使用)
字符串statusStr = NULL;
StringBuffer的BUFF =新的StringBuffer();
尝试{
字符串REQ_METHOD =方法;
的String [] =目标{REQ_METHOD}; 的for(int i = 0; I< targets.length;我++){
如果(!conn.isOpen()){
Socket套接字=新的Socket(host.getHostName(),host.getPort());
conn.bind(插座,则params);
}
BasicHttpEntityEnclosingRequest REQ =新BasicHttpEntityEnclosingRequest(POST,目标[I]);
req.setEntity(新InputStreamEntity(新ByteArrayInputStream进行(reqStr.toString()的getBytes()),reqStr.length())。);
req.setHeader(内容类型,应用程序/ x-WWW的形式urlen codeD);
req.setHeader(用户代理,Mozilla的/ 5.0(Windows NT的5.1)为AppleWebKit / 535.7(KHTML,像壁虎)的Chrome / Safari浏览器16.0.912.75 / 535.7);
req.setHeader(缓存控制,最大年龄= 0);
req.setHeader(连接,保持活动);
req.setHeader(原点,http://www.indianrail.gov.in);
req.setHeader(接受,text / html的,是application / xhtml + xml的,应用/ XML; Q = 0.9 * / *; Q = 0.8);
req.setHeader(引荐,http://www.indianrail.gov.in/pnr_Enq.html);
//req.setHeader(\"Accept-Encoding,gzip的,放气,SDCH);
req.setHeader(接受语言,EN-US,连接; Q = 0.8);
req.setHeader(接收字符集,ISO-8859-1,utf-8的; Q = 0.7,*; Q = 0.3);
。httpexecutor preProcess(REQ,httpproc,背景); HTT presponse响应= httpexecutor.execute(REQ,康涅狄格州,背景);
response.setParams(PARAMS);
httpexecutor.postProcess(响应,httpproc,背景); 标题[] =头response.getAllHeaders();
对于(INT J = 0; J< headers.length; J ++){
如果(头[J] .getName()。equalsIgnoreCase(ERROR_MSG)){
resData = EntityUtils.toString(response.getEntity());
}
}
。statusStr = response.getStatusLine()的toString();
。InputStream的时间= response.getEntity()的getContent();
读者的BufferedReader = NULL;
如果(在!= NULL){
读者=新的BufferedReader(新的InputStreamReader(中));
} 串线= NULL;
而((行= reader.readLine())!= NULL){
buff.append(行+\\ n);
}
尝试{
附寄();
}赶上(例外五){}
}
}赶上(例外五){
抛出新的异常(E);
} {最后
尝试{
conn.close();
}赶上(IOException异常五){
e.printStackTrace();
}
}
返回的buff;
} 公共PNRStatus parseHtml(StringBuffer的数据)抛出异常{
读者的BufferedReader = NULL;
如果(数据!= NULL){
读者=新的BufferedReader(新的InputStreamReader(新ByteArrayInputStream进行(data.toString()的getBytes())));
}其他{
返回null;
} 串线= NULL;
TrainDetails trainDetails =新TrainDetails();
清单< PassengerDetails> passDetailsList =新的ArrayList< PassengerDetails>();
PassengerDetails passDetails = NULL;
INT I = 0;
而((行= reader.readLine())!= NULL){
如果(line.startsWith(&下; TD)及与放大器; line.contains(table_border_both)){
行= line.replace(&下; B>中,);
行= line.substring(line.indexOf(\\>中)+ 2,line.indexOf(< /))。修剪(); 如果(line.contains(图)){
trainDetails.setChatStatus(线);
打破;
}
如果(ⅰ大于7){//乘客详细
如果(passDetails == NULL){
passDetails =新PassengerDetails();
}
开关(ⅰ){
案例8:
passDetails.setName(线);
打破;
案例9:
passDetails.setBookingStatus(line.replace(,));
打破;
案例10:
passDetails.setCurrentStatus(line.replace(,));
我= 7;
打破;
}
如果(我== 7){
passDetailsList.add(passDetails);
passDetails = NULL;
} }其他{//火车细节
开关(ⅰ){
情况下0:
trainDetails.setNumber(线);
打破;
情况1 :
trainDetails.setName(线);
打破;
案例2:
trainDetails.setBoardingDate(线);
打破;
案例3:
trainDetails.setFrom(线);
打破;
情况4:
trainDetails.setTo(线);
打破;
情况5:
trainDetails.setReservedUpto(线);
打破;
情况6:
trainDetails.setBoardingPoint(线);
打破;
案例7:
trainDetails.setReservedType(线);
打破;
默认情况下:
打破;
}
}
我++;
}
} 如果(trainDetails.getNumber()!= NULL){
PNRStatus pnrStatus =新PNRStatus();
pnrStatus.setTrainDetails(trainDetails);
pnrStatus.setPassengerDetails(passDetailsList);
返回pnrStatus;
}其他{
返回null;
}
}}
我发现一个帖子这样的回答询问相同的:
如果你检查HTML code,其actualy pretty坏的验证码。验证码的背景是:比方说,你下载的HttpClient 4.3.1。在您的项目包括客户端,核心和MIME库(副本libs文件夹,右键单击项目,属性,Java构建路径,库,添加罐 - >添加这些3)。
code例子是:
私有静态最后弦乐FORM_TARGET =http://www.indianrail.gov.in/cgi_bin/inet_pnstat_cgi.cgi;
私有静态最后弦乐INPUT_PNR =lccp_pnrno1;
私有静态最后弦乐INPUT_CAPTCHA =lccp_capinp_val;
私有静态最后弦乐INPUT_CAPTCHA_HIDDEN =lccp_cap_val;私人无效getHtml(字符串userPnr){
MultipartEntityBuilder建设者= MultipartEntityBuilder.create();
builder.addTextBody(INPUT_PNR,userPnr); //用户PNR code
builder.addTextBody(INPUT_CAPTCHA,123456);
builder.addTextBody(提交,获取状态);
builder.addTextBody(INPUT_CAPTCHA_HIDDEN,123456); //值不
//为此事
//只要它们
// 是相同的 HttpEntity实体= builder.build(); HttpPost httpPost =新HttpPost(FORM_TARGET);
httpPost.setEntity(实体); HttpClient的客户端=新DefaultHttpClient(); HTT presponse响应= NULL;
串htmlString =;
尝试{
响应= client.execute(httpPost);
htmlString = convertStreamToString(response.getEntity()的getContent());
//现在你可以解析这个字符串来获得您所需要的数据。
}赶上(例外letsIgnoreItForNow){
}
}私人静态字符串convertStreamToString(InputStream为){
读者的BufferedReader =新的BufferedReader(新的InputStreamReader(是));
StringBuilder的SB =新的StringBuilder(); 串线= NULL;
尝试{
而((行= reader.readLine())!= NULL){
sb.append(线);
}
}赶上(IOException异常ignoredOnceMore){
} {最后
尝试{
is.close();
}赶上(IOException异常manyIgnoredExceptions){
}
} 返回sb.toString();
}
另外,被警告我没有在的AsyncTask
通话包裹,所以你将不得不这样做。
I have a PNR Inquiry app on Google Play. It was working very fine. But recently Indian Railwys added captcha to their PNR Inquiry section and because of this I am not able to pass proper data to the server to get proper response. How to add this captcha in my app in form of an imageview and ask the users to enter captcha details also so that I can send proper data and get proper response.
Indian Railways PNR Inquiry Link
Here is my PnrCheck.java which I was using earlier. Please help what modifications should be done here..
import java.io.BufferedReader;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.Socket;
import java.net.URL;
import java.util.ArrayList;
import java.util.List;
import org.apache.http.Header;
import org.apache.http.HttpHost;
import org.apache.http.HttpResponse;
import org.apache.http.HttpVersion;
import org.apache.http.entity.InputStreamEntity;
import org.apache.http.impl.DefaultHttpClientConnection;
import org.apache.http.message.BasicHttpEntityEnclosingRequest;
import org.apache.http.params.BasicHttpParams;
import org.apache.http.params.HttpParams;
import org.apache.http.params.HttpProtocolParams;
import org.apache.http.protocol.BasicHttpContext;
import org.apache.http.protocol.BasicHttpProcessor;
import org.apache.http.protocol.ExecutionContext;
import org.apache.http.protocol.HttpContext;
import org.apache.http.protocol.HttpRequestExecutor;
import org.apache.http.protocol.RequestConnControl;
import org.apache.http.protocol.RequestContent;
import org.apache.http.protocol.RequestExpectContinue;
import org.apache.http.protocol.RequestTargetHost;
import org.apache.http.protocol.RequestUserAgent;
import org.apache.http.util.EntityUtils;
public class PNRStatusCheck {
public static void main(String args[]) {
try {
String pnr1 = "1154177041";
String reqStr = "lccp_pnrno1=" + pnr1 + "&submitpnr=Get+Status";
PNRStatusCheck check = new PNRStatusCheck();
StringBuffer data = check.getPNRResponse(reqStr, "http://www.indianrail.gov.in/cgi_bin/inet_pnrstat_cgi.cgi");
if(data != null) {
@SuppressWarnings("unused")
PNRStatus pnr = check.parseHtml(data);
}
} catch(Exception e) {
e.printStackTrace();
}
}
public StringBuffer getPNRResponse(String reqStr, String urlAddr) throws Exception {
String urlHost = null;
int port;
String method = null;
try {
URL url = new URL(urlAddr);
urlHost = url.getHost();
port = url.getPort();
method = url.getFile();
// validate port
if(port == -1) {
port = url.getDefaultPort();
}
} catch(Exception e) {
e.printStackTrace();
throw new Exception(e);
}
HttpParams params = new BasicHttpParams();
HttpProtocolParams.setVersion(params, HttpVersion.HTTP_1_1);
HttpProtocolParams.setContentCharset(params, "UTF-8");
HttpProtocolParams.setUserAgent(params, "HttpComponents/1.1");
HttpProtocolParams.setUseExpectContinue(params, true);
BasicHttpProcessor httpproc = new BasicHttpProcessor();
// Required protocol interceptors
httpproc.addInterceptor(new RequestContent());
httpproc.addInterceptor(new RequestTargetHost());
// Recommended protocol interceptors
httpproc.addInterceptor(new RequestConnControl());
httpproc.addInterceptor(new RequestUserAgent());
httpproc.addInterceptor(new RequestExpectContinue());
HttpRequestExecutor httpexecutor = new HttpRequestExecutor();
HttpContext context = new BasicHttpContext(null);
HttpHost host = new HttpHost(urlHost, port);
DefaultHttpClientConnection conn = new DefaultHttpClientConnection();
context.setAttribute(ExecutionContext.HTTP_CONNECTION, conn);
context.setAttribute(ExecutionContext.HTTP_TARGET_HOST, host);
@SuppressWarnings("unused")
String resData = null;
@SuppressWarnings("unused")
String statusStr = null;
StringBuffer buff = new StringBuffer();
try {
String REQ_METHOD = method;
String[] targets = { REQ_METHOD };
for (int i = 0; i < targets.length; i++) {
if (!conn.isOpen()) {
Socket socket = new Socket(host.getHostName(), host.getPort());
conn.bind(socket, params);
}
BasicHttpEntityEnclosingRequest req = new BasicHttpEntityEnclosingRequest("POST", targets[i]);
req.setEntity(new InputStreamEntity(new ByteArrayInputStream(reqStr.toString().getBytes()), reqStr.length()));
req.setHeader("Content-Type", "application/x-www-form-urlencoded");
req.setHeader("User-Agent", "Mozilla/5.0 (Windows NT 5.1) AppleWebKit/535.7 (KHTML, like Gecko) Chrome/16.0.912.75 Safari/535.7");
req.setHeader("Cache-Control", "max-age=0");
req.setHeader("Connection", "keep-alive");
req.setHeader("Origin", "http://www.indianrail.gov.in");
req.setHeader("Accept", "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8");
req.setHeader("Referer", "http://www.indianrail.gov.in/pnr_Enq.html");
//req.setHeader("Accept-Encoding", "gzip,deflate,sdch");
req.setHeader("Accept-Language", "en-US,en;q=0.8");
req.setHeader("Accept-Charset", "ISO-8859-1,utf-8;q=0.7,*;q=0.3");
httpexecutor.preProcess(req, httpproc, context);
HttpResponse response = httpexecutor.execute(req, conn, context);
response.setParams(params);
httpexecutor.postProcess(response, httpproc, context);
Header[] headers = response.getAllHeaders();
for(int j=0; j<headers.length; j++) {
if(headers[j].getName().equalsIgnoreCase("ERROR_MSG")) {
resData = EntityUtils.toString(response.getEntity());
}
}
statusStr = response.getStatusLine().toString();
InputStream in = response.getEntity().getContent();
BufferedReader reader = null;
if(in != null) {
reader = new BufferedReader(new InputStreamReader(in));
}
String line = null;
while((line = reader.readLine()) != null) {
buff.append(line + "\n");
}
try {
in.close();
} catch (Exception e) {}
}
} catch (Exception e) {
throw new Exception(e);
} finally {
try {
conn.close();
} catch (IOException e) {
e.printStackTrace();
}
}
return buff;
}
public PNRStatus parseHtml(StringBuffer data) throws Exception {
BufferedReader reader = null;
if(data != null) {
reader = new BufferedReader(new InputStreamReader(new ByteArrayInputStream(data.toString().getBytes())));
} else {
return null;
}
String line = null;
TrainDetails trainDetails = new TrainDetails();
List<PassengerDetails> passDetailsList = new ArrayList<PassengerDetails>();
PassengerDetails passDetails = null;
int i = 0;
while ((line = reader.readLine()) != null) {
if(line.startsWith("<TD") && line.contains("table_border_both")) {
line = line.replace("<B>", "");
line = line.substring(line.indexOf("\">")+2, line.indexOf("</")).trim();
if(line.contains("CHART")) {
trainDetails.setChatStatus(line);
break;
}
if(i > 7) {//Passenger Details
if(passDetails == null) {
passDetails = new PassengerDetails();
}
switch(i) {
case 8 :
passDetails.setName(line);
break;
case 9 :
passDetails.setBookingStatus(line.replace(" ", ""));
break;
case 10 :
passDetails.setCurrentStatus(line.replace(" ", ""));
i = 7;
break;
}
if(i == 7 ) {
passDetailsList.add(passDetails);
passDetails = null;
}
} else { // Train details
switch(i){
case 0 :
trainDetails.setNumber(line);
break;
case 1 :
trainDetails.setName(line);
break;
case 2 :
trainDetails.setBoardingDate(line);
break;
case 3 :
trainDetails.setFrom(line);
break;
case 4 :
trainDetails.setTo(line);
break;
case 5 :
trainDetails.setReservedUpto(line);
break;
case 6 :
trainDetails.setBoardingPoint(line);
break;
case 7 :
trainDetails.setReservedType(line);
break;
default :
break;
}
}
i++;
}
}
if(trainDetails.getNumber() != null) {
PNRStatus pnrStatus = new PNRStatus();
pnrStatus.setTrainDetails(trainDetails);
pnrStatus.setPassengerDetails(passDetailsList);
return pnrStatus;
} else {
return null;
}
}
}
I found this answer on one post asking same:
If you check the html code, its actualy pretty bad captcha. Background of captcha is: http://www.indianrail.gov.in/1.jpg Those numbers are actualy in input tag:
What they are doing is, via javascript, use numbers from that hidden input tag and put them on that span with "captcha" background.
So basicaly your flow is:
read their html
get "captcha" (lol, funny captcha though) value from input field
when user puts data in your PNR field and presses Get Status
post form field, put PNR in proper value, put captcha in proper value
parse response
Oh yeah, one more thing. You can put any value in hidden input and "captcha" input, as long as they are the same. They aren't checking it via session or anything.
EDIT (code sample for submiting form): To simplify posting form i recommend HttpClient components from Apache: http://hc.apache.org/downloads.cgi Lets say you downloaded HttpClient 4.3.1. Include client, core and mime libraries in your project (copy to libs folder, right click on project, properties, Java Build Path, Libraries, Add Jars -> add those 3.).
Code example would be:
private static final String FORM_TARGET = "http://www.indianrail.gov.in/cgi_bin/inet_pnstat_cgi.cgi";
private static final String INPUT_PNR = "lccp_pnrno1";
private static final String INPUT_CAPTCHA = "lccp_capinp_val";
private static final String INPUT_CAPTCHA_HIDDEN = "lccp_cap_val";
private void getHtml(String userPnr) {
MultipartEntityBuilder builder = MultipartEntityBuilder.create();
builder.addTextBody(INPUT_PNR, userPnr); // users PNR code
builder.addTextBody(INPUT_CAPTCHA, "123456");
builder.addTextBody("submit", "Get Status");
builder.addTextBody(INPUT_CAPTCHA_HIDDEN, "123456"); // values don't
// matter as
// long as they
// are the same
HttpEntity entity = builder.build();
HttpPost httpPost = new HttpPost(FORM_TARGET);
httpPost.setEntity(entity);
HttpClient client = new DefaultHttpClient();
HttpResponse response = null;
String htmlString = "";
try {
response = client.execute(httpPost);
htmlString = convertStreamToString(response.getEntity().getContent());
// now you can parse this string to get data you require.
} catch (Exception letsIgnoreItForNow) {
}
}
private static String convertStreamToString(InputStream is) {
BufferedReader reader = new BufferedReader(new InputStreamReader(is));
StringBuilder sb = new StringBuilder();
String line = null;
try {
while ((line = reader.readLine()) != null) {
sb.append(line);
}
} catch (IOException ignoredOnceMore) {
} finally {
try {
is.close();
} catch (IOException manyIgnoredExceptions) {
}
}
return sb.toString();
}
Also, be warned i didn't wrap this in AsyncTask
call, so you will have to do that.
这篇关于如何更新PNR CAPCHA在印度铁路网站添加的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!