Reputation: 11947
I am using the following code to try to connect to the associates program through Amazon:
public static Session login(final Account account) throws IOException{
final HashMap<String, String> info = new HashMap<String, String>();
final URL url = new URL("https://affiliate-program.amazon.com/");
final HttpURLConnection connection = (HttpURLConnection)(account.isProxySet() ? url.openConnection(account.getProxy()) : url.openConnection());
connection.setUseCaches(false);
connection.setDoOutput(true);
connection.setDoInput(true);
connection.setReadTimeout(timeout);
connection.setConnectTimeout(timeout);
connection.setRequestMethod("POST");
connection.addRequestProperty("User-Agent", account.getUserAgent());
connection.addRequestProperty("User-Content", "text/plain");
connection.setAllowUserInteraction(true);
final BufferedWriter writer = new BufferedWriter(new OutputStreamWriter(connection.getOutputStream()));
final Scanner reader = new Scanner(connection.getInputStream());
while(reader.hasNextLine()){
final String line = reader.nextLine().trim();
if(line.contains("<input type=\"hidden\"")){
final String[] split = line.split("\"");
info.put(split[3], split[5]);
}
}
String writable = "";
final Iterator<String> iterator = info.keySet().iterator();
while(iterator.hasNext()){
final String key = iterator.next();
writable += String.format("%s=%s", URLEncoder.encode(key, "UTF-8"), URLEncoder.encode(info.get(key), "UTF-8"));
if(iterator.hasNext()) writable += "&";
}
final String data = String.format("%s&email=%s&password=%s&submit=Sign In", writable, URLEncoder.encode(account.getEmail(), "UTF-8"), URLEncoder.encode(account.getPass(), "UTF-8"));
System.out.println(data);
writer.write(data);
writer.flush();
writer.close();
connection.getInputStream().read();
System.out.println(connection.getURL().toString());
return new Session(account);
}
The classes Session and Account are both mine, but it is not relevant to my problem. So basically I am trying to connect to the amazon site and I am having a problem. Whenever it prints out the data that it is actually writing, it seems to look exactly how it looks inside the source of the webpage (writing the proper names with their associated values). But, when it prints out the new URL, it is the same as the old one.
I think I do know the reason why; it appears that you can't read before you write (that's why I initialised the BufferedWriter before I initialised the Scanner because if I didn't, it would tell me that I can't write after reading and throw an IOException) basically if you look at the page source for the site, you'll see an id called 'sessionId' and it changes each time you open a new connection.
So I could only conclude that the only solution is to find out someway to read before writing so the session id doesn't change. I conclude this because each time I create a new connection and print out the data that I'm writing (before it's encoded), the session id is different. Does anyone have any ideas on how to do this? Any ideas would be greatly appreciated. Thanks.
Edit: Modified the code according to ruakh's answer.
Upvotes: 2
Views: 247
Reputation: 183544
One problem is that this:
writer.write(URLEncoder.encode(data, "UTF-8"));
will replace all the ampersands and equals-signs with URL-escapes, so instead of posting something like this:
a=b&c=d&e=f
you're posting something like this:
a%3Db%26c%3Dd%26e%3Df
which is effectively garbage.
You need to perform the URL-encoding on the individual components separately, and then assemble the result with =
and &
.
Upvotes: 1