Can';t处理CakePHP和android之间的csrf令牌

Can';t处理CakePHP和android之间的csrf令牌,android,cakephp,cookies,csrf,httpurlconnection,Android,Cakephp,Cookies,Csrf,Httpurlconnection,我已经阅读了十几篇关于这个主题的文章,其中大多数都依赖于不推荐的Android API,我最终尝试使用,但没有成功: 所以我得到的csrftoken是这样的: URL url = new URL(urlString); HttpURLConnection urlConnection = (HttpURLConnection) url.openConnection(); urlConnection.setUseCaches(false); urlConnection.setRequestMeth

我已经阅读了十几篇关于这个主题的文章,其中大多数都依赖于不推荐的Android API,我最终尝试使用,但没有成功:

所以我得到的csrftoken是这样的:

URL url = new URL(urlString);

HttpURLConnection urlConnection = (HttpURLConnection) url.openConnection();
urlConnection.setUseCaches(false);
urlConnection.setRequestMethod("GET");

if (urlConnection.getResponseCode() == HttpURLConnection.HTTP_OK) {
    String COOKIES_HEADER = "Set-Cookie";
    site.setCookieManager(new java.net.CookieManager());

    Map<String, List<String>> headerFields = urlConnection.getHeaderFields();
    List<String> cookiesHeader = headerFields.get(COOKIES_HEADER);

    if(cookiesHeader != null)
    {
        for (String cookie : cookiesHeader)
        {
            if (cookie.startsWith("csrfToken")) {
                site.getCookieManager().getCookieStore().add(null, HttpCookie.parse(cookie).get(0));
            }
        }
    }

    urlConnection.disconnect();
} else {
    urlConnection.disconnect();
    return null;
}
urlConnection = (HttpURLConnection) url.openConnection();

if(site.getCookieManager().getCookieStore().getCookies().size() > 0)
{
    urlConnection.setRequestProperty("Cookie",
            TextUtils.join(";", site.getCookieManager().getCookieStore().getCookies()));
}

if ((params != null) && !params.isEmpty()) {
    urlConnection.setDoOutput(true);
    urlConnection.setChunkedStreamingMode(0);
    urlConnection.setRequestProperty("Accept-Charset", "UTF-8");
    urlConnection.setRequestProperty("Content-Type", "application/x-www-form-urlencoded;charset=" + "UTF-8");

    OutputStream output = urlConnection.getOutputStream();
    output.write(params.getBytes("UTF-8"));
    output.close();
}

is = urlConnection.getInputStream();
因此,如果我查看urlconnection数据,我可以看到:

requestHeaders
    nameAndValues
        0 = "Cookie"
        1 = "csrkToken=5f62......973"
        2 = "Accept-Charset"
        3 = "UTF-8"
        4 = "Content-Type"
        5 = "application/x-www-form-urlencoded;charset=UTF-8"
但是当我执行
urlConnection.getInputStream()
时,我得到以下异常:

java.io.FileNotFoundException: http://my.example.com/mywebservice
    at com.android.okhttp.internal.huc.HttpURLConnectionImpl.getInputStream(HttpURLConnectionImpl.java:238)
    at com.ndguide.ndguide.JSONParser.getJSONFromUrl(JSONParser.java:93)
    at com.ndguide.ndguide.MainActivity.sendRegistrationIdToBackend(MainActivity.java:1562)
    at com.ndguide.ndguide.MainActivity.access$600(MainActivity.java:82)
    at com.ndguide.ndguide.MainActivity$2.doInBackground(MainActivity.java:1160)
    at com.ndguide.ndguide.MainActivity$2.doInBackground(MainActivity.java:1122)
    at android.os.AsyncTask$2.call(AsyncTask.java:295)
    at java.util.concurrent.FutureTask.run(FutureTask.java:237)
    at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:234)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1113)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:588)
    at java.lang.Thread.run(Thread.java:818)
CookieManager cookieManager = new CookieManager();
CookieHandler.setDefault(cookieManager);
请允许我明确指出,如果我不在服务器端加载Csrf组件,一切都会正常进行

当我在这里阅读时,我还尝试在我的应用程序的开头添加以下行,但它会导致相同的异常:

java.io.FileNotFoundException: http://my.example.com/mywebservice
    at com.android.okhttp.internal.huc.HttpURLConnectionImpl.getInputStream(HttpURLConnectionImpl.java:238)
    at com.ndguide.ndguide.JSONParser.getJSONFromUrl(JSONParser.java:93)
    at com.ndguide.ndguide.MainActivity.sendRegistrationIdToBackend(MainActivity.java:1562)
    at com.ndguide.ndguide.MainActivity.access$600(MainActivity.java:82)
    at com.ndguide.ndguide.MainActivity$2.doInBackground(MainActivity.java:1160)
    at com.ndguide.ndguide.MainActivity$2.doInBackground(MainActivity.java:1122)
    at android.os.AsyncTask$2.call(AsyncTask.java:295)
    at java.util.concurrent.FutureTask.run(FutureTask.java:237)
    at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:234)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1113)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:588)
    at java.lang.Thread.run(Thread.java:818)
CookieManager cookieManager = new CookieManager();
CookieHandler.setDefault(cookieManager);

那么我的标题有什么问题呢?

所以,多亏了ndm的建议,我探索了Csrf组件的期望,在这里我解释了应该做些什么来完全满足它,因为到目前为止我只找到了部分解释,至少对于像我这样的noob来说是这样的

首先,我们必须执行
GET
请求以获取csrf令牌:

URL url = new URL(urlString);

HttpURLConnection urlConnection = (HttpURLConnection) url.openConnection();
urlConnection.setUseCaches(false); // Don't use a Cached Copy
urlConnection.setRequestMethod("GET");

if (urlConnection.getResponseCode() == HttpURLConnection.HTTP_OK) {
    String COOKIES_HEADER = "Set-Cookie";
    site.setCookieManager(new java.net.CookieManager());

    Map<String, List<String>> headerFields = urlConnection.getHeaderFields();
    List<String> cookiesHeader = headerFields.get(COOKIES_HEADER);

    if(cookiesHeader != null)
    {
        for (String cookie : cookiesHeader)
        {
            if (cookie.startsWith("csrfToken")) {
                site.getCookieManager().getCookieStore().add(null, HttpCookie.parse(cookie).get(0));
            }
        }
    }
}
urlConnection.disconnect();

希望这有帮助。

csrkToken
?另外,请始终提及您使用的确切CakePHP版本,您说的是CSRF组件,因此表示Cake 3.x,但没有人能够真正确定(默认情况下,Cake 3.x使用长寿令牌,而Cake 2.x使用一次性令牌)。@ndm抱歉,
csrfToken
在CakePHP 3.1中。事实上,我有这个问题,因为csrf组件中的错误是在测试版AFAIR中解决的。我想我的问题出在Android方面,因为我与其他web服务没有任何问题。但当我发现一些关于这个主题的文章没有成功时,我经常试图解决它。我可以在CakePHP csrf组件中检查一些内容以获得更多信息吗?因此,在本例中,
csrkToken=5f62……973
中的
k
只是一个输入错误?如果是这样,那么我建议您从调试CakePHP端接收的内容开始,即记录请求数据/cookie转储。。。你能帮我吗explain@amity很酷,站点只是一个全局数据结构。在我的应用程序中。与所需库无关,或者我不知道还有什么。您自己创建了站点类吗?