Рубрики
Без рубрики

RestTemplate с дайджест-аутентификацией

Как настроить дайджест-аутентификацию для Spring RestTemplate с помощью HttpClient 4.

Автор оригинала: Eugen Paraschiv.

1. Обзор

В этой статье будет показано, как настроить Spring RestTemplate для использования службы, защищенной дайджест-аутентификацией .

Аналогично базовой аутентификации, как только в шаблоне будет задан дайджест-аутентификация, клиент сможет выполнить необходимые шаги безопасности и получить информацию, необходимую для заголовка Authorization :

Authorization: Digest 
    username="user1",
    realm="Custom Realm Name",
    nonce="MTM3NTYwOTA5NjU3OTo5YmIyMjgwNTFlMjdhMTA1MWM3OTMyMWYyNDY2MGFlZA==",
    uri="/spring-security-rest-digest-auth/api/foos/1", 
    ....

С помощью этих данных сервер может правильно аутентифицировать запрос и вернуть ответ 200 OK.

2. Настройте табличку RestTemplate

RestTemplate должен быть объявлен как bean в контексте Spring – это достаточно просто либо в XML, либо в обычной Java, используя аннотацию @Bean :

import org.apache.http.HttpHost;
import com.baeldung.client.HttpComponentsClientHttpRequestFactoryDigestAuth;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.client.RestTemplate;

@Configuration
public class ClientConfig {

    @Bean
    public RestTemplate restTemplate() {
        HttpHost host = new HttpHost("localhost", 8080, "http");
        CloseableHttpClient client = HttpClientBuilder.create().
          setDefaultCredentialsProvider(provider()).useSystemProperties().build();
        HttpComponentsClientHttpRequestFactory requestFactory = 
          new HttpComponentsClientHttpRequestFactoryDigestAuth(host, client);

        return new RestTemplate(requestFactory);;
    }
    
    private CredentialsProvider provider() {
        CredentialsProvider provider = new BasicCredentialsProvider();
        UsernamePasswordCredentials credentials = 
          new UsernamePasswordCredentials("user1", "user1Pass");
        provider.setCredentials(AuthScope.ANY, credentials);
        return provider;
    }
}

Большая часть настройки механизма дайджест – доступа выполняется в пользовательской реализации фабрики http-запросов клиента, введенной в шаблон – HttpComponentsClientHttpRequestFactoryDigestAuth .

Обратите внимание, что сейчас мы предварительно настраиваем шаблон с учетными данными, имеющими доступ к защищенному API.

3. Настройте Дайджест-Аутентификацию

Мы собираемся использовать поддержку, введенную весной 3.1 для текущего HttpClient 4.x, а именно HttpComponentsClientHttpRequestFactory , путем расширения и настройки его.

В основном мы собираемся настроить HttpContext и подключить нашу пользовательскую логику для дайджест-аутентификации:

import java.net.URI;
import org.apache.http.HttpHost;
import org.apache.http.client.AuthCache;
import org.apache.http.client.protocol.ClientContext;
import org.apache.http.impl.auth.DigestScheme;
import org.apache.http.impl.client.BasicAuthCache;
import org.apache.http.protocol.BasicHttpContext;
import org.apache.http.protocol.HttpContext;
import org.springframework.http.HttpMethod;
import org.springframework.http.client.HttpComponentsClientHttpRequestFactory;

public class HttpComponentsClientHttpRequestFactoryDigestAuth 
  extends HttpComponentsClientHttpRequestFactory {

    HttpHost host;

    public HttpComponentsClientHttpRequestFactoryDigestAuth(HttpHost host) {
        super(httpClient);
        this.host = host;
    }

    @Override
    protected HttpContext createHttpContext(HttpMethod httpMethod, URI uri) {
        return createHttpContext();
    }

    private HttpContext createHttpContext() {
        // Create AuthCache instance
        AuthCache authCache = new BasicAuthCache();
        // Generate DIGEST scheme object, initialize it and add it to the local auth cache
        DigestScheme digestAuth = new DigestScheme();
        // If we already know the realm name
        digestAuth.overrideParamter("realm", "Custom Realm Name");
        authCache.put(host, digestAuth);

        // Add AuthCache to the execution context
        BasicHttpContext localcontext = new BasicHttpContext();
        localcontext.setAttribute(ClientContext.AUTH_CACHE, authCache);
        return localcontext;
    }
}

Теперь RestTemplate можно просто ввести и использовать в тесте:

@Test
public void whenSecuredRestApiIsConsumed_then200OK() {
    String uri = "http://localhost:8080/spring-security-rest-digest-auth/api/foos/1";
    ResponseEntity entity = restTemplate.exchange(uri, HttpMethod.GET, null, Foo.class);
    System.out.println(entity.getStatusCode());
}

Чтобы проиллюстрировать полный процесс настройки, этот тест также устанавливает учетные данные пользователя – user1 и user1Pass . Эта часть, конечно, должна быть выполнена только один раз и вне самого теста .

4. Зависимости Maven

Необходимые зависимости Maven для RestTemplate и библиотеки HttpClient:


   org.springframework
   spring-webmvc
   5.2.8.RELEASE



   org.apache.httpcomponents
   httpclient
   4.3.5

5. Заключение

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

Реализацию можно найти в примере проекта GitHub – это проект на основе Maven, поэтому его должно быть легко импортировать и запускать как есть.