Apart from the obvious fields we need to send back (username, password...), you can see by the highlighted sections there are 2 hidden fields. Thankfully the first one (iov1) is not necessary for a login - this field is rather complexly generated by javascript and does not render except in a browser. This means we are only interested in the "multiform" hidden field which we need to send back in our request.
That sorts out the fields we need to populate: username, password, submit and multiform. What about cookies? Yes there are cookies but that is easily captured in the header request message (set-cookie) and we can simply attach the same cookie back into our response header unmodified.
I have since setup a cron job on Google App Engine that runs my code once every month. This should help alleviate the headache of logging in manually every month. Here is the code if anyone wants to use it:
URL url = new URL("https://account.dyn.com/entrance/"); HttpURLConnection con = (HttpURLConnection) url.openConnection(); con.setRequestMethod("GET"); //Spoof as if from a web browser con.setRequestProperty("User-Agent", "Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.31 (KHTML, like Gecko) Chrome/26.0.1410.64 Safari/537.31"); con.setDoOutput(true); con.connect(); // give it 15 seconds to respond con.setReadTimeout(15 * 1000); //Get cookie id String headerName = null; String cookie = null; for(int i = 1; (headerName = con.getHeaderFieldKey(i)) != null; i++) { if (headerName.equalsIgnoreCase("Set-Cookie")) { cookie = con.getHeaderField(i); break; } } //Read the website into a string so we can parse with Jsoup BufferedReader reader = new BufferedReader(new InputStreamReader(con.getInputStream())); String temp = ""; String line = null; while((line = reader.readLine()) != null) { temp += line + "\r\n"; } reader.close(); Document doc = Jsoup.parse(temp); Elements els = doc.getElementsByTag("input"); String multiform = null; for(Element e : els) { String name = e.attr("name"); String value = e.attr("value"); //Get the hidden field required for login if(name.equalsIgnoreCase("multiform")) { multiform = value; break; } } //Open the connection again with the correct headers con = (HttpURLConnection) url.openConnection(); con.setRequestProperty("Cookie", cookie); con.setRequestProperty("Host", "account.dyn.com"); con.setRequestProperty("Origin", "https://account.dyn.com"); con.setRequestProperty("Referer", "https://account.dyn.com/entrance/"); con.setRequestProperty("User-Agent", "Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.31 (KHTML, like Gecko) Chrome/26.0.1410.64 Safari/537.31"); con.setRequestMethod("POST"); con.setDoOutput(true); String username = "your_username_here"; String password = "your_password_here"; //Set the login fields OutputStreamWriter out = new OutputStreamWriter(con.getOutputStream()); String data = URLEncoder.encode("username", "UTF-8") + "=" + URLEncoder.encode(username, "UTF-8"); data += "&" + URLEncoder.encode("password", "UTF-8") + "=" + URLEncoder.encode(password, "UTF-8"); data += "&" + URLEncoder.encode("submit", "UTF-8") + "=" + URLEncoder.encode("Log in", "UTF-8"); data += "&" + URLEncoder.encode("multiform", "UTF-8") + "=" + URLEncoder.encode(multiform, "UTF-8"); out.write(data); out.flush(); out.close(); //Read the response message reader = new BufferedReader(new InputStreamReader(con.getInputStream())); boolean success = false; while((line = reader.readLine()) != null) { //If the title says we are logged in everything worked if(line.contains("My Dyn Account ")) { success = true; break; } } if(success) { System.out.println("Succesfully logged in!"); } else { System.out.println("Login failed!"); } reader.close();