Возникли проблемы при реализации формы Stormpath для входа в систему / аутентификации вместе с аутентификацией REST oAuth в том же приложении

Мы используем Stormpath с Java, а также пытаемся объединить форму Login с аутентификацией REST API в том же приложении.

Я настроил плагин сервлета Stormpath, как описано здесь https://docs.stormpath.com/java/servlet-plugin/quickstart.html... Это работает очень хорошо.

Теперь в том же приложении у нас есть API, в которых я реализовал аутентификацию oAuth с помощью stormpath, см. Здесь http://docs.stormpath.com/guides/api-key-management/

Первый запрос на токен доступа работает нормально, отправив Basic Base64(keyId:keySecret) в заголовке запроса и grant_type = client_credentials в теле. Жетоны доступа возвращаются красиво. Однако пытается аутентифицировать последующие запросы с заголовком Bearer <the-obtained-access-token> даже не попал в приложение, прежде чем вернуть следующее сообщение об ошибке json...

{
    "error": "invalid_client",
    "error_description": "access_token is invalid."
}

Это сбивает с толку, потому что я установил точки останова по всему приложению, и я почти уверен, что запрос API не попадает нигде в приложении, пока не начнется stormpath и вернет эту ошибку. И даже если stormpath каким-то образом перехватывает запрос перед тем, как попасть в интерфейс REST, это сообщение не имеет для меня никакого смысла, потому что я, безусловно, выполняю последующие вызовы API с действительным токеном доступа, полученным из первого вызова для получения доступа. маркер.

У меня закончились идеи, почему это может происходить, но я подозреваю, что это может иметь какое-то отношение к конфигурации Stormpath, особенно с комбинацией формы Login/Authentication для веб-представлений и oAuth Athentication для конечных точек REST. С учетом вышесказанного, вот как выглядит мой stormpath.properties. Надеюсь, это поможет мне понять, что я могу делать неправильно.

stormpath.application.href=https://api.stormpath.com/v1/applications/[app-id]
stormpath.web.filters.authr=com.app.security.AuthorizationFilter
stormpath.web.request.event.listener = com.app.security.AuthenticationListener

stormpath.web.uris./resources/**=anon
stormpath.web.uris./assets/**=anon
stormpath.web.uris./v1.0/**=anon
stormpath.web.uris./** = authc,authr
stormpath.web.uris./**/**=authc,authr

Помощь с этим будет высоко ценится.

2 ответа

Проблема может быть связана с неправильным запросом.

Можно ли попробовать этот код в своем приложении?:

 private boolean verify(String accessToken) throws OauthAuthenticationException {
     HttpRequest request = createRequestForOauth2AuthenticatedOperation(accessToken);
     AccessTokenResult result = Applications.oauthRequestAuthenticator(application)
        .authenticate(request);
     System.out.println(result.getAccount().getEmail() + " was successfully verified, you can allow your protect operation to continue");
     return true;
 }

 private HttpRequest createRequestForOauth2AuthenticatedOperation(String token) {
     try {
         Map<String, String[]> headers = new LinkedHashMap<String, String[]>();
         headers.put("Accept", new String[]{"application/json"});
         headers.put("Authorization", new String[]{"Bearer " + token});
         HttpRequest request = HttpRequests.method(HttpMethod.GET)
             .headers(headers)
             .build();
         return request;
     } catch (Exception e) {
         e.printStackTrace();
         return null;
     }
 }

Я подготовил пример, который демонстрирует создание oauth-токена, а также авторизованный доступ к защищенным страницам с использованием токенов доступа.

Он построен на примере сервлета в Stormpath SDK. Репо можно найти здесь: https://github.com/stormpath/stormpath-java-oauth-servlet-sample

Он демонстрирует запуск приложения сервлета и наличие внеполосной программы для получения и использования маркеров oauth для доступа к защищенным ресурсам.

Ядро oauth части находится в TokenAuthTest.java:

public class TokenAuthTest {
    public static void main(String[] args) throws Exception {

        String command = System.getProperty("command");

        if (command == null || !("getToken".equals(command) || "getPage".equals(command))) {
            System.err.println("Must supply a command:");
            System.err.println("\t-Dcommand=getToken OR");
            System.err.println("\t-Dcommand=getPage OR");
            System.exit(1);
        }

        if ("getToken".equals(command)) {
            getToken();
        } else {
            getPage();
        }
    }

    private static final String APP_URL = "http://localhost:8080";
    private static final String OAUTH_URI = "/oauth/token";
    private static final String PROTECTED_URI = "/dashboard";

    private static void getToken() throws Exception {
        String username = System.getProperty("username");
        String password = System.getProperty("password");

        if (username == null || password == null) {
            System.err.println("Must supply -Dusername=<username> -Dpassword=<password> on the command line");
            System.exit(1);
        }

        PostMethod method = new PostMethod(APP_URL + OAUTH_URI);

        method.setRequestHeader("Origin", APP_URL);
        method.setRequestHeader("Content-type", "application/x-www-form-urlencoded");

        method.addParameter("grant_type", "password");
        method.addParameter("username", username);
        method.addParameter("password", password);

        HttpClient client = new HttpClient();
        client.executeMethod(method);

        BufferedReader br = new BufferedReader(new InputStreamReader(method.getResponseBodyAsStream()));
        String readLine;
        while(((readLine = br.readLine()) != null)) {
            System.out.println(readLine);
        }
    }

    private static void getPage() throws Exception {
        String token = System.getProperty("token");

        if (token == null) {
            System.err.println("Must supply -Dtoken=<access token> on the command line");
            System.exit(1);
        }

        GetMethod method = new GetMethod(APP_URL + PROTECTED_URI);
        HttpClient client = new HttpClient();

        System.out.println("Attempting to retrieve " + PROTECTED_URI + " without token...");

        int returnCode = client.executeMethod(method);
        System.out.println("return code: " + returnCode);

        System.out.println();

        System.out.println("Attempting to retrieve " + PROTECTED_URI + " with token...");

        method.addRequestHeader("Authorization", "Bearer " + token);
        returnCode = client.executeMethod(method);
        System.out.println("return code: " + returnCode);
    }
}
Другие вопросы по тегам