Download a file from a page (cookies needed) using post request - java

I have tested the first step (the login page) and it works. I put all parameters (user, pass, etc) and I can print the result (page with my data). The problem is when I try to download a file from that web. I need the cookies from the first step. In the file that I download I have the message: "Expired session". This is my code:
URL login = new URL("...");
URL download_page = new URL("...");
URL document_link new URL("...");
//String for request
String data_post = "username=name&password=1234&other_data=...";
//Login page
HttpURLConnection conn = (HttpURLConnection)login.openConnection();
conn.setDoOutput(true);
OutputStreamWriter wr = new OutputStreamWriter(conn.getOutputStream());
wr.write(data_post);
wr.close();
conn.connect();
//Download page
HttpURLConnection connDownload = (HttpURLConnection)download_page.openConnection();
connDownload.connect();
//Link to the file
HttpURLConnection connFile = (HttpURLConnection)document_link.openConnection();
connFile.connect();
BufferedInputStream in = new BufferedInputStream(connFile.getInputStream());
File saveFile = new File("myfile.txt");
OutputStream out = new BufferedOutputStream(new FileOutputStream(saveFile));
byte[] buf = new byte[256];
int n = 0;
while ((n=in.read(buf))>=0) {
out.write(buf, 0, n);
}
out.flush();
out.close();
Thanks in advance.

Have you tried to check the headers for a cookie on the first page before closing the connection? I'd try something like:
String cookies = conn.getHeaderField("Set-Cookie");
Then set the cookie subsequently in the following connections, before executing connect(), using:
connDownload.setRequestProperty("Cookie", cookies);
... See if that works ...

Related

File download from url using HttpURLConnection |HTTP 400 if file name contain space

I'm trying to download the files from url(soap request) using http connection, and below is my code, while executing i'm getting http = 400, because of file Name contain space (ac abc.pdf)
String downloadFileName = "ac abc.pdf";
String saveDir = "D:/download";
String baseUrl = "abc.com/AttachmentDownload?Filename=";
URL url = new URL(baseUrl + downloadFileName);
HttpURLConnection connection = (HttpURLConnection) url
.openConnection();
connection.setReadTimeout(60 * 1000);
connection.setConnectTimeout(60 * 1000);
connection.setRequestMethod("POST");
connection.setRequestProperty("Content-Type", "application/octet-stream");
connection.setRequestProperty("SOAPAction", url.toString());
String userCredentials = "user:pass";
connection.setRequestProperty("Authorization", userCredentials);
connection.setDoInput(true);
connection.setDoOutput(true);
int responseCode = connection.getResponseCode();
if (responseCode == HttpURLConnection.HTTP_OK) {
try (InputStream inputStream = connection.getInputStream()) {
String saveFilePath = saveDir + downloadFileName;
try (FileOutputStream outputStream = new FileOutputStream(saveFilePath)) {
int bytesRead = -1;
byte[] buffer = new byte[BUFFER_SIZE];
while ((bytesRead = inputStream.read(buffer)) != -1) {
outputStream.write(buffer, 0, bytesRead);
}
}
}
while executing the above code getting the below output
responsecode400
response messageBad Request
No file to download. Server replied HTTP code: 400
let me know how can we format the url with the above situation
Spaces and some other symbols are not well tollerated in URL. You need to escape or encode them change your code
URL url = new URL(baseUrl + downloadFileName);
To:
URL url = new URL(baseUrl + URLEncoder.encode(downloadFileName, StandardCharsets.UTF_8.name());
That should resolve your problem. Besides there are Open Source libraries that resolve your issue for you. See Apache commons which is a popular solution. Another solution is MgntUtils library (version 1.5.0.2). It contains class HttpClient that allows you to do things very simple:
httpClient.sendHttpRequestForBinaryResponse(baseUrl + URLEncoder.encode(downloadFileName, StandardCharsets.UTF_8.name()", HttpClient.HttpMethod.POST);
This will return ByteBuffer that contains the response as raw bytes. The same class has method sendHttpRequest to get Textual response. Both methods throw IOException in case of failure. Here is the link to an article that explains where to get MgntUtils library as well as what utilities it has. In the article the HttpClient class is not mentioned (It is a new feature), but the library comes with well written javadoc. So look for javadoc for HttpClient class in that library.

Timeout exception while reading data from HttpURLConnection in Google App Engine

I am running an application on Google App Engine which calls a Http URL of my
web application(running on Glassfish) to read data using inputstream. Here is
my code snippet.
OutputStream os = response.getOutputStream();
URL url = new URL(Http URL);
conn = (HttpURLConnection)url.openConnection();
conn.setConnectTimeout(0);
conn.setReadTimeout(0);
conn.setRequestMethod("GET");
System.out.println("response code=" + conn.getResponseCode());
byte b[] = new byte[2048];
InputStream is = url.openStream();
int len;
while ((len=is.read(b))!=-1){
os.write(b, 0, len);
System.out.println("len=" + len);
}
But I am getting "Timeout while fetching URL:" exception.
I have tried URLFetchService too, but exception remains same
URLFetchService urlFetchService = URLFetchServiceFactory.getURLFetchService();
URL url = new URL(Http URL);
Future future = urlFetchService.fetchAsync(url);
HTTPResponse response1 = (HTTPResponse)future.get();
byte[] content = response1.getContent();
int responseCode = response1.getResponseCode();
List<HTTPHeader> headers = response1.getHeaders();
System.out.println("responseCode=" + responseCode);
Please advise how to proceed. Thanks in advance for your help.
Resolved this exception. Http URL of my web application(running on Glassfish) was an internal IP address. On attempting to read data from Google, it should be a publicly accessible IP address.

HttpURLConnection: resulting json-code suggests page doesnt exist (404), even when url is correct

I am trying to get data from an MySQL database using a php-file. My java code is as follows:
HttpURLConnection conn = null;
URL url = null;
try {
url = new URL(getURL);
System.out.println(getURL);
conn = (HttpURLConnection)url.openConnection();
//conn.setReadTimeout(READ_TIMEOUT);
//conn.setConnectTimeout(CONNECTION_TIMEOUT);
conn.setRequestMethod("POST");
// setDoInput and setDoOutput method depict handling of both send and receive
conn.setDoInput(true);
conn.setDoOutput(true);
// Append parameters to URL
Uri.Builder builder = new Uri.Builder();
builder.appendQueryParameter("user", USER);
builder.appendQueryParameter("pass", PASS);
builder.appendQueryParameter("server", SERVER);
builder.appendQueryParameter("db", DB);
String query = builder.build().getEncodedQuery();
// Open connection for sending data
OutputStream os = conn.getOutputStream();
BufferedWriter writer = new BufferedWriter(new OutputStreamWriter(os, "UTF-8"));
writer.write(query);
writer.flush();
writer.close();
os.close();
conn.connect();
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e1) {
e1.printStackTrace();
}
try {
int response_code = conn.getResponseCode();
// Check if successful connection made
if (response_code == HttpURLConnection.HTTP_OK) {
// Read data sent from server
InputStream input = conn.getInputStream();
BufferedReader reader = new BufferedReader(new InputStreamReader(input));
result = reader.readLine();
return(result);
}else{
return("unsuccessful");
}
When I go to my url (hidden in the variable getURL) using a browser, I see string of json on my screen, just as it should. However, when I output the contents of the reader (above code only takes the first line, but by adapting the code I can, of course, output more) it shows the html-code for a website displaying a 404 - Page does not exist message.
Anyone has any idea what goes wrong? Yes, I did check for typo's.
Okay, I have no clue what happened, as I didn't change anything. But all of the sudden it started working?!?
Must have been something server-side I guess...
Thanks for the input and sharing your thoughts!

Hit a URL in JAVA without redirecting

I want to hit a URL in php from java servlet.I just want to send a information to that url.I didn't need to go to that url.i want to stay in my page.Anyway to do that.?
You could simply make a post on that url like in the http components doc
PostMethod post = new PostMethod("http://jakarata.apache.org/");
NameValuePair[] data = {
new NameValuePair("user", "joe"),
new NameValuePair("password", "bloggs")
};
post.setRequestBody(data);
// execute method and handle any error responses.
...
InputStream in = post.getResponseBodyAsStream();
// handle response.
Try following code
URL url = new URL("your url");
URLConnection connection = url.openConnection();
connection.setConnectTimeout(5000); // time out
connection.setDoOutput(true);
PrintWriter out = new PrintWriter(new OutputStreamWriter(connection.getOutputStream()));
String postData = "your post data";
out.print(postData);
out.close();
String response connection.getInputStream();
or you can use
Request.Post("your url").bodyForm(
Form.form().add("parameter name", "value")
.add("parameter name1", "value").build()).execute();

How to manage loop of request-response dialog with server

I'm writing a simple client-server system and the question is: how to structure my client code in order to get POST request-response working in a loop?
At the moment it looks something like this (and it's is NOT a loop right now):
open HttpURLConnection
set properties
setDoOutput(true)
writing to output stream
closing output stream
new DataInputStream
reading response
exiting method
I'm not sure which objects do I have to save for the next iterations and which ones I should close.
you need to save the connection object and you should make use of setDoInput(true) for reading data but if you just want to read responseCode and responseMessage you dont need InputStream. check the code below.
HttpURLConnection connection =(HttpURLConnection)new URL("url").openConnection();
connection.setDoOutput(true);
connection.setRequestProperty("Content-type", "text/xml"); // depend on you
connection.setRequestProperty("Accept", "text/xml, application/xml"); // depend on you
connection.setRequestMethod("POST");
OutputStreamWriter writer = new OutputStreamWriter(connection.getOutputStream());
writer.write(yaml);
writer.close();
int statusCode = connection.getResponseCode();
String message = connection.getResponseMessage();
for InputStreamReader
connection.setDoInput(true);
InputStreamReader reader = new InputStreamReader(connection.getInputStream());
char[] cbuf = new char[100];
reader.read(cbuf);
// there are 3 read method you can choose as per your convenience
//and put a check for end of line in while loop for reading whole content.
reader.close();
After managing my own 'research' on this subject (thanks to Google and Nokia Developer forums) I've come to the final view of my code. It's a file upload loop:
path = Paths.get(requestString);
in = Files.newInputStream(path);
int i = 0;
while ((bytesRead = in.read(buf)) != -1) {
URL u = new URL(defaultURL);
huc =
(HttpURLConnection) u.openConnection();
huc.setRequestMethod("POST");
huc.setDoOutput(true);
huc.setDoInput(true);
os = huc.getOutputStream();
os.write(buf, 0, bytesRead);
os.flush();
os = null;
// thanks to dku.rajkumar for the following block of code !
InputStreamReader reader =
new InputStreamReader(huc.getInputStream());
char[] cbuf = new char[400];
reader.read(cbuf);
reader.close();
String s = new String(cbuf);
messagebuffer.append(s + "\n\n");
huc.disconnect();
Thread.sleep(16);
}

Categories

Resources