/* * Copyright (C) 2014 Sasha Vasko <sasha at aftercode dot net> * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.wifiafterconnect.http; import java.io.BufferedInputStream; import java.io.BufferedReader; import java.io.DataOutputStream; import java.io.FileNotFoundException; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.net.HttpURLConnection; import java.net.ProtocolException; import java.net.URL; import java.util.HashMap; import java.util.List; import java.util.Map; import com.wifiafterconnect.BuildConfig; import com.wifiafterconnect.Constants; import com.wifiafterconnect.util.Worker; /** * @author Sasha Vasko * */ public class HttpURLConnectionWrapper extends HttpConnectionWrapper{ // Yes, we are dirty liars public static final String HTTP_USER_AGENT = "Mozilla/5.0 (Android; Mobile; rv:24.0) Gecko/20100101 Firefox/24.0"; public static final String HTTP_ACCEPT = "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8"; @Override public boolean post(Worker context, String postDataString, String cookies, String referer) { URL url = getUrl(); context.debug("POST to url [" + url + "]"); context.debug("data to post ["+postDataString+"]"); if (postDataString == null || postDataString.isEmpty()){ context.error("Failed to compile data for authentication POST"); return false; } else if (url == null) { context.error("Missing URL to POST the form"); return false; } HttpURLConnection conn = null; try { URL postURL = url; context.debug("Post URL = [" + postURL + "]"); conn = (HttpURLConnection) postURL.openConnection(); conn.setInstanceFollowRedirects(false); conn.setConnectTimeout(Constants.SOCKET_CONNECT_TIMEOUT_MS); conn.setReadTimeout(Constants.SOCKET_READ_TIMEOUT_MS); conn.setDoInput(true); conn.setDoOutput(true); conn.setUseCaches(false); // we need the next two to avoid 404 code on non-standard ports : conn.setRequestProperty("User-Agent",HTTP_USER_AGENT); conn.setRequestProperty("Accept", HTTP_ACCEPT); conn.setRequestProperty("Content-Type","application/x-www-form-urlencoded"); //conn.setRequestProperty("charset", "utf-8"); conn.setRequestProperty("Content-Length", Integer.toString(postDataString.getBytes().length)); conn.setRequestProperty("Origin", url.getProtocol() + "://" + url.getHost() + ":" + url.getPort()); conn.setRequestProperty("Connection", "close"); if (referer != null) { conn.setRequestProperty("Referer",referer); } if (cookies != null) conn.setRequestProperty("Cookie", cookies); showRequestProperties (context, conn); conn.setRequestMethod("POST"); DataOutputStream output = new DataOutputStream (conn.getOutputStream()); output.writeBytes(postDataString); output.flush(); output.close(); context.debug("Data posted, checking result ..."); return receive(context, conn); }catch ( ProtocolException e) { context.exception (e); }catch (FileNotFoundException e) { context.debug("Can't read result - FileNotFound exception."); } catch (IOException e) { context.exception (e); }finally { if (conn != null) conn.disconnect(); } return false; } @Override public boolean get(Worker context, String referer) { context.debug("Getting [" + getUrl() + "]"); HttpURLConnection conn = null; if (getUrl() != null){ try { conn = (HttpURLConnection) getUrl().openConnection(); conn.setConnectTimeout(Constants.SOCKET_CONNECT_TIMEOUT_MS); conn.setReadTimeout(Constants.SOCKET_READ_TIMEOUT_MS); conn.setUseCaches(false); conn.setRequestProperty("User-Agent",HTTP_USER_AGENT); conn.setRequestProperty("Accept","*/*"); conn.setRequestProperty("Connection", "close"); if (referer != null) conn.setRequestProperty("Referer",referer); showRequestProperties (context, conn); return receive (context, conn); } catch (IOException e) { context.exception(e); }finally { if (conn != null) conn.disconnect(); } } return false; } private boolean receive (Worker context, HttpURLConnection conn) { try { InputStream in = null; try { in = new BufferedInputStream(conn.getInputStream()); } catch (FileNotFoundException e) { in = new BufferedInputStream(conn.getErrorStream()); } Map<String,String> headers = new HashMap<String,String>(); String field = null; for (int pos = 0 ; (field = conn.getHeaderField(pos)) != null ; ++pos ) headers.put (conn.getHeaderFieldKey(pos), field); if (BuildConfig.DEBUG) showReceived (context); context.debug("Response code = " + conn.getResponseCode()); BufferedReader r = new BufferedReader(new InputStreamReader(in)); StringBuilder total = new StringBuilder(); char []buffer = new char[4096]; int bytesIn; while ((bytesIn = r.read(buffer, 0, 4096)) >= 0) { if (bytesIn > 0) { total.append(buffer, 0, bytesIn); } } data = total.toString(); if (BuildConfig.DEBUG) showReceived (context); return true; }catch (IOException e) { context.error ("Failed to receive from " + conn.toString()); context.exception (e); } catch (Throwable e) { context.exception (e); } return false; } private void showRequestProperties (Worker context, HttpURLConnection conn) { Map<String,List<String>> reqProps = conn.getRequestProperties(); context.debug("RequestProperties for [" + conn.getURL() + "]"); for (String key : reqProps.keySet()) { String propStr = "RequestPropery[" + key + "] = {"; for (String val : reqProps.get(key)) { propStr += "[" + val + "]"; } context.debug(propStr + "}"); } } }