排球岗位请求无效

时间:2016-03-22 15:01:50

标签: android android-volley okhttp

我是Volley和OkHttp的新手,我正在尝试使用 OkHttp作为Volley 的传输层登录网站。 登录需要通过SSL完成,并实现了几个重定向

OkHttp被迫自动跟踪重定向,因为我需要手动为此站点执行此操作(我认为),但我在发布请求时失败(我不确定)。

帖子请求需要一些这样的参数:

source=AEM&target=IAM&URL=selfcare&login-form-type=pwd&username=user&userId=user&password=pass&rememberUsername=yes&button=

所以如果我没有弄错的话应该是StringRequest,而且我需要覆盖所有请求的标题,如下所示:

@Override
public Map<String, String> getHeaders() throws AuthFailureError {
Map<String, String>  params = new HashMap<String, String>();
params.put("Connection", "keep-alive");
params.put("User-Agent", "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/47.0.2526.106 Safari/537.36");
params.put("Content-Type", "application/x-www-form-urlencoded; charset=utf-8");
return params;
}

如果有人可以忽略我的代码,看看我哪里出错了,我将不胜感激。再一次,我是排球和okhttp的新手,所以downvoters应该温柔。

修改

对于遇到同样问题的人。

我终于在PersistentCookieStore(https://gist.github.com/franmontiel/ed12a2295566b7076161)的帮助下成功登录了。

此外,我需要制作一个同步的RequestQueue ,以便能够手动关注所有重定向。 (这可以通过使用 FutureRequest 来改进,但它可以工作,随时根据您的需要更改以下工作代码。

Singleton类:

public class TestController extends Application {
    public static final String TAG = "VolleyPatterns";
    private RequestQueue mRequestQueue;
    private static TestController sInstance;

    @Override
    public void onCreate() {
        super.onCreate();
        sInstance = this;
    }
    public static synchronized TestController getInstance() {
        return sInstance;
    }
    public RequestQueue getRequestQueue() {
        if (mRequestQueue == null) {
            mRequestQueue = Volley.newRequestQueue(getApplicationContext(), new OkHttpStack());
        }
        return mRequestQueue;
    }
    public <T> void addToRequestQueue(Request<T> req, String tag) {
        req.setTag(TextUtils.isEmpty(tag) ? TAG : tag);
        VolleyLog.e("Adding request to queue: %s", req.getUrl());
        getRequestQueue().add(req);
    }
    public <T> void addToRequestQueue(Request<T> req) {
        req.setTag(TAG);

        getRequestQueue().add(req);
    }
    public void cancelPendingRequests(Object tag) {
        if (mRequestQueue != null) {
            mRequestQueue.cancelAll(tag);
        }
    }
}

OkHttpStack类(SSL允许所有证书用于测试目的):

public class OkHttpStack extends HurlStack {
    private final OkUrlFactory okUrlFactory;

    public OkHttpStack() {
        this(new OkUrlFactory(getOkHttpClient()));
    }

    public OkHttpStack(OkUrlFactory okUrlFactory) {
        if (okUrlFactory == null) {
            throw new NullPointerException("Client must not be null.");
        }
        this.okUrlFactory = okUrlFactory;
    }

    private static OkHttpClient getOkHttpClient() {
        if (BuildConfig.DEBUG) {
            return getUnsafeOkHttpClient();
        } else {
            return new OkHttpClient();
        }
    }

    private static OkHttpClient getUnsafeOkHttpClient() {
        try {
            // Create a trust manager that does not validate certificate chains
            final TrustManager[] trustAllCerts = new TrustManager[]{
                    new X509TrustManager() {
                        @Override
                        public void checkClientTrusted(java.security.cert.X509Certificate[] chain, String authType) throws CertificateException {
                        }

                        @Override
                        public void checkServerTrusted(java.security.cert.X509Certificate[] chain, String authType) throws CertificateException {
                        }

                        @Override
                        public java.security.cert.X509Certificate[] getAcceptedIssuers() {
                            return null;
                        }
                    }
            };
            // Install the all-trusting trust manager
            final SSLContext sslContext = SSLContext.getInstance("SSL");
            sslContext.init(null, trustAllCerts, new java.security.SecureRandom());
            // Create an ssl socket factory with our all-trusting manager
            final SSLSocketFactory sslSocketFactory = sslContext.getSocketFactory();
            OkHttpClient okHttpClient = new OkHttpClient();
            okHttpClient.setFollowRedirects(false);
            okHttpClient.setSslSocketFactory(sslSocketFactory);
            okHttpClient.setHostnameVerifier(new HostnameVerifier() {
                @Override
                public boolean verify(String hostname, SSLSession session) {
                    return true;
                }
            });
            return okHttpClient;
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }

    @Override
    protected HttpURLConnection createConnection(URL url) throws IOException {

        return okUrlFactory.open(url);
    }
}

MainActivity:

public class MainActivity extends AppCompatActivity {

private String LOGINURL = "https://www.test.com/testhandler/iam/authenticateuser/";
private static String redirectURL;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    CookieManager cmrCookieMan = new CookieManager(new PersistentCookieStore(this), CookiePolicy.ACCEPT_ALL);
    CookieHandler.setDefault(cmrCookieMan);

    Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
    setSupportActionBar(toolbar);

    final StringRequest postRequest = new StringRequest(Request.Method.POST, LOGINURL,
            new Response.Listener<String>() {
                @Override
                public void onResponse(String response) {
                    Log.d("Response", response);
                }
            },
            new Response.ErrorListener() {
                @Override
                public void onErrorResponse(VolleyError error) {
                    redirectURL = null;
                    final int status = error.networkResponse.statusCode;
                    if (HttpURLConnection.HTTP_MOVED_PERM == status || status == HttpURLConnection.HTTP_MOVED_TEMP || status == HttpURLConnection.HTTP_SEE_OTHER) {
                        redirectURL = error.networkResponse.headers.get("Location");
                        Log.e("Redirected to ", redirectURL);
                        Log.d("ERROR", "error => " + error.toString());
                        LoadFirst();
                        Log.w("1st ", "Link");
                    }
                }
            }
    ) {
        @Override
        public String getBodyContentType() {
            return "application/x-www-form-urlencoded; charset=utf-8";
        }

        // this is the relevant method
        @Override
        public byte[] getBody() throws AuthFailureError {
            String httpPostBody ="username=yser&password=pass";
            try {
                httpPostBody = httpPostBody + URLEncoder.encode("", "UTF-8");
            } catch (UnsupportedEncodingException exception) {
                Log.e("ERROR", "exception", exception);
                return null;
            }
            return httpPostBody.getBytes();
        }
    };
    TestController.getInstance().addToRequestQueue(postRequest);
}

private void LoadFirst() {

    StringRequest stringRequest = new StringRequest(Request.Method.GET, redirectURL,
            new Response.Listener<String>() {
                @Override
                public void onResponse(String response) {
                    Log.e("Response:", response);
                }

            }, new Response.ErrorListener() {
        @Override
        public void onErrorResponse(VolleyError error) {
            redirectURL = null;
            final int status = error.networkResponse.statusCode;
            if (HttpURLConnection.HTTP_MOVED_PERM == status || status == HttpURLConnection.HTTP_MOVED_TEMP || status == HttpURLConnection.HTTP_SEE_OTHER) {
                redirectURL = error.networkResponse.headers.get("Location");
                Log.e("2nd Redirect to ", redirectURL);
                LoadSecond();
                Log.w("2nd ", "Link");
            }
        }

    });
    TestController.getInstance().addToRequestQueue(stringRequest);
}

private void LoadSecond() {

    StringRequest stringRequest = new StringRequest(Request.Method.GET, redirectURL,
            new Response.Listener<String>() {

                @Override
                public void onResponse(String s) {
                //Search the secretUserID in the response, which is only provided after successfull login
                    for (String line : s.split("\n")) {
                        if (line.contains("secretUserID")) {
                            String[] out = line.split("'");
                            String CustID = out[1].toString();
                            Log.w("secretUserID", CustID);
                        }
                    }
                    Log.w("3rd FINAL ", "Successfully logged in!");
                }
            }, new Response.ErrorListener() {

        @Override
        public void onErrorResponse(VolleyError error) {
            Log.e("Fatal error: ", error.toString());
            if (error instanceof TimeoutError) {
                // note : may cause recursive invoke if always timeout.
                Log.e("Timed out ", "retrying..");
                LoadSecond();
            }
        }

    });
    stringRequest.setRetryPolicy(new DefaultRetryPolicy(DefaultRetryPolicy.DEFAULT_TIMEOUT_MS * 2,
            DefaultRetryPolicy.DEFAULT_MAX_RETRIES, DefaultRetryPolicy.DEFAULT_BACKOFF_MULT));
    TestController.getInstance().addToRequestQueue(stringRequest);
}

}

logcat的:

03-23 16:19:46.791 5847-5878/test.com.example.buddy.myapplication D/OpenGLRenderer: Use EGL_SWAP_BEHAVIOR_PRESERVED: true
03-23 16:19:46.846 5847-5878/test.com.example.buddy.myapplication I/OpenGLRenderer: Initialized EGL, version 1.4
03-23 16:19:47.534 5847-5877/test.com.example.buddy.myapplication E/Volley: [1644] BasicNetwork.performRequest: Request at https://www.test.com/testhandler/iam/authenticateuser/ has been redirected to https://www.test.com/login.login/?url=%2Ftesthandler%2Fiam%2Fauthenticateuser%2F
03-23 16:19:47.538 5847-5847/test.com.example.buddy.myapplication E/Redirected to: https://www.test.com/login.login/?url=%2Fztesthandler%2Fiam%2Fauthenticateuser%2F
03-23 16:19:47.538 5847-5847/test.com.example.buddy.myapplication D/ERROR: error => com.android.volley.RedirectError
03-23 16:19:47.540 5847-5847/test.com.example.buddy.myapplication W/1st: Link
03-23 16:19:47.611 5847-5874/test.com.example.buddy.myapplication E/Volley: [1641] BasicNetwork.performRequest: Request at https://www.test.com/login.login/?url=%2Ftesthandler%2Fiam%2Fauthenticateuser%2F has been redirected to https://www.test.com/test/?selfcare
03-23 16:19:47.612 5847-5847/test.com.example.buddy.myapplication E/2nd Redirect to: https://www.test.com/test/?selfcare
03-23 16:19:47.612 5847-5847/test.com.example.buddy.myapplication W/2nd: Link
03-23 16:19:51.533 5847-5875/test.com.example.buddy.myapplication D/Volley: [1642] BasicNetwork.logSlowRequests: HTTP response for request=<[ ] https://www.test.com/test/?selfcare 0xe5b1fae3 NORMAL 3> [lifetime=3920], [size=34928], [rc=200], [retryCount=0]
03-23 16:19:51.544 5847-5847/test.com.example.buddy.myapplication W/encryptedCustID: someUserID
03-23 16:19:51.545 5847-5847/test.com.example.buddy.myapplication W/3rd FINAL: Successfully logged in!

0 个答案:

没有答案