权限类别会阻止Android应用访问DRF?

时间:2019-10-09 02:45:10

标签: android django rest authentication

我在开发要通过Django REST框架进行身份验证以安全访问信息的Android应用程序时遇到了麻烦。我正在成功发放REST令牌,但是IsAuthenticated对于我的所有视图仍然为假。

在Django中,我有一个基于类的视图,如果两个authentication.TokenAuthentication permissions.IsAuthenticated都有效,则会响应:

class TestAuthView(APIView):
    authentication_classes = (authentication.TokenAuthentication,)
    permission_classes = (permissions.IsAuthenticated,)

    def get(self, request, format=None):
        return GetRestData()

在Android中,我将自己的 uname passwd 发布到默认网址/rest-auth/login/,该网址会响应令牌:{"key":"c03c1238ab99d91301d34567bda9d417d2b48c0c"},从而获得令牌

public static String getResponseFromHttpUrl(String... params) throws IOException {

    ArrayList<AbstractMap.SimpleEntry<String,String>> paramssss = new ArrayList<>();

    paramssss.add(new AbstractMap.SimpleEntry<>("username", "root"));
    paramssss.add(new AbstractMap.SimpleEntry<>("password", "mypass"));

    URL url = new URL(params[0]);

    HttpURLConnection urlConnection = (HttpURLConnection) url.openConnection();
    urlConnection.setReadTimeout(3000);
    urlConnection.setConnectTimeout(3000);

    urlConnection.setRequestMethod("POST");
    urlConnection.setDoInput(true);
    urlConnection.setDoOutput(true);

    OutputStream os = urlConnection.getOutputStream();
    BufferedWriter writer = new BufferedWriter(
            new OutputStreamWriter(os, "UTF-8"));
    writer.write(getQuery(paramssss));
    writer.flush();
    writer.close();
    os.close();

    urlConnection.connect();

    try {
        InputStream in = urlConnection.getInputStream();

        Scanner scanner = new Scanner(in);
        scanner.useDelimiter("\\A");

        boolean hasInput = scanner.hasNext();
        if (hasInput) {
            return scanner.next(); //eg. {"key":"c03c1238ab99d91301d34567bda9d417d2b48c0c"}
        } else {
            return null;
        }

    } finally {
        urlConnection.disconnect();
    }
}

然后我存储令牌,然后使用它来请求一些数据:

@Override
protected String doInBackground(String... sUrl) {
    try {
        URL url = new URL(sUrl[0]);

        URLConnection urlConnection = url.openConnection();
        String authToken = "c03c1238ab99d91301d34567bda9d417d2b48c0c"; //just use a constant string for now..
        urlConnection.addRequestProperty("Authorization", "Token " + authToken);
        urlConnection.addRequestProperty("Content-Type", "application/x-www-form-urlencoded; charset=UTF-8");

        urlConnection.connect();

        ...
        process the response
        ...

查看Django日志,我看到登录成功,但是GET请求失败,并显示HTTP_401_UNAUTHORIZED

  

[08 / Oct / 2019 22:18:53]“ POST / rest-auth / login / HTTP / 1.1” 200 50

     

[08 / Oct / 2019 22:18:53]“ GET / update / HTTP / 1.1” 401 58

当我将Permissions_classes更改为AllowAny时:

class TestAuthView(APIView):
    authentication_classes = (authentication.TokenAuthentication,)
    permission_classes = (permissions.AllowAny,) //Changed this!!!

    def get(self, request, format=None):
        return GetRestData()

响应包含预期的REST数据,并且一切成功:

  

[08 / Oct / 2019 22:24:57]“ POST / rest-auth / login / HTTP / 1.1” 200 50

     

[08 / Oct / 2019 22:25:02]“ GET / update / HTTP / 1.1” 200 19451876

我不知道如何正确验证我的Android应用程序,以使IsAuthenticated不会始终为False?

目前,我向/rest-auth/login/提交了用户名和密码,并获得了休息令牌。但是我也必须在其他地方登录以获得CSRF令牌并也使用它吗?

我对permissions.IsAuthenticated的需求并不熟悉,它是否甚至适用于Android应用程序?我的意思是我是否将非浏览器Android应用的权限保留为AllowAny?我觉得这是个坏主意。

我已经为此花了几天时间,非常感谢您的帮助!

0 个答案:

没有答案