2012-04-27 3 views
34

私はRESTful APIを持っています。AndroidとRestTemplateで接続しようとしています。 APIへのすべての要求は、HttpEntityのヘッダーを設定し、RestTemplateのexchange()メソッドを使用して、HTTP認証で認証されます。AndroidでSpring RestTemplateを使用して認証されたPOSTリクエストを作成する

すべてのGETリクエストはこのようにうまく機能しますが、認証されたPOSTリクエストをどのように達成するかはわかりません。 postForObjectpostForEntityはPOSTを処理しますが、認証ヘッダーを設定する簡単な方法はありません。

のでGETをするために、これは素晴らしい作品:それはカスタマイズされたヘッダを送信したことがないと私はexchange()を使用してリクエストボディを設定する方法を見ないよう

HttpAuthentication httpAuthentication = new HttpBasicAuthentication("username", "password"); 
HttpHeaders requestHeaders = new HttpHeaders(); 
requestHeaders.setAuthorization(httpAuthentication); 

HttpEntity<?> httpEntity = new HttpEntity<Object>(requestHeaders); 

MyModel[] models = restTemplate.exchange("/api/url", HttpMethod.GET, httpEntity, MyModel[].class); 

しかし、ポストは明らかにexchange()では動作しません。

RestTemplateから認証されたPOSTリクエストを作成する最も簡単な方法は何ですか?

+1

requestHeaders.setAuthorization(httpAuthentication)...などsetAuthorizationとしてのundefined..no方法が – DEADEND

答えて

75

回答が見つかりました。 exchange()が最適です。奇妙なことに、HttpEntityクラスにはsetBody()メソッド(getBody())がありませんが、依然としてコンストラクタを介して要求本体を設定することはできます。

// Create the request body as a MultiValueMap 
MultiValueMap<String, String> body = new LinkedMultiValueMap<String, String>();  

body.add("field", "value"); 

// Note the body object as first parameter! 
HttpEntity<?> httpEntity = new HttpEntity<Object>(body, requestHeaders); 

MyModel model = restTemplate.exchange("/api/url", HttpMethod.POST, httpEntity, MyModel.class); 
+2

...それはTypeMismatchエラー をスローします 型の不一致:私はそれが ResponseEntity モデル= restTemplate.exchange( "/ API/URL"、HttpMethod.POST、httpEntity、MyModel.class)であるべきと思います。..に、mymodelにResponseEntity から を変換することはできません。 – Sid

+0

'MyModel myModel = restTemplate.exchange(completeServiceUrl、HttpMethod.GET、request、MyModel.class).getBody()'は、 – Isank

+0

THANKSという問題を解決するのに役立ちます。これは私があなたのポストをつまずくまで2時間かけていました。 – guenhter

7

非常に便利な私は、要求XMLがPOSTのボディとないのparam自体たわずかに異なるシナリオを持っていました。そのためには、次のコードを使用することができます。似たような問題を抱えている誰かが利益を得る場合に備えて、回答として投稿する。

final HttpHeaders headers = new HttpHeaders(); 
    headers.add("header1", "9998"); 
    headers.add("username", "xxxxx"); 
    headers.add("password", "xxxxx"); 
    headers.add("header2", "yyyyyy"); 
    headers.add("header3", "zzzzz"); 
    headers.setContentType(MediaType.APPLICATION_XML); 
    headers.setAccept(Arrays.asList(MediaType.APPLICATION_XML)); 
    final HttpEntity<MyXmlbeansRequestDocument> httpEntity = new HttpEntity<MyXmlbeansRequestDocument>(
      MyXmlbeansRequestDocument.Factory.parse(request), headers); 
    final ResponseEntity<MyXmlbeansResponseDocument> responseEntity = restTemplate.exchange(url, HttpMethod.POST, httpEntity,MyXmlbeansResponseDocument.class); 
    log.info(responseEntity.getBody()); 
14

少し異なるアプローチ:

MultiValueMap<String, String> headers = new LinkedMultiValueMap<String, String>(); 
headers.add("HeaderName", "value"); 
headers.add("Content-Type", "application/json"); 

RestTemplate restTemplate = new RestTemplate(); 
restTemplate.getMessageConverters().add(new MappingJackson2HttpMessageConverter()); 

HttpEntity<ObjectToPass> request = new HttpEntity<ObjectToPass>(objectToPass, headers); 

restTemplate.postForObject(url, request, ClassWhateverYourControllerReturns.class); 
+2

ObjectToPassは –

+0

@Ismail Iqbalのどこにありますか?それは渡す必要がある情報を持つオブジェクトです(例:private Person john = Person( "John"、24);)。それはjsonペイロードに変換され、リクエスト本体を介してサーバーに送信されます – Andrey

7

私は最近、JavaからREST呼び出しをしながら、私は過去の認証を取得しようとしていた問題に対処する、としながら、このスレッドで回答(と他のスレッド)が助けてくれましたが、それを動作させるにはまだまだ試行錯誤がありました。

私にとっては、資格情報をBase64にエンコードし、それを基本認証ヘッダーとして追加することが効果的でした。その後、HttpEntityrestTemplate.postForEntityに追加しました。これは私に必要な応答を与えました。

ここで私は(RestTemplateを拡張)、フルで、このために書いたクラスです:

public class AuthorizedRestTemplate extends RestTemplate{ 

    private String username; 
    private String password; 

    public AuthorizedRestTemplate(String username, String password){ 
     this.username = username; 
     this.password = password; 
    } 

    public String getForObject(String url, Object... urlVariables){ 
     return authorizedRestCall(this, url, urlVariables); 
    } 

    private String authorizedRestCall(RestTemplate restTemplate, 
      String url, Object... urlVariables){ 
     HttpEntity<String> request = getRequest(); 
     ResponseEntity<String> entity = restTemplate.postForEntity(url, 
       request, String.class, urlVariables); 
     return entity.getBody(); 
    } 

    private HttpEntity<String> getRequest(){ 
     HttpHeaders headers = new HttpHeaders(); 
     headers.add("Authorization", "Basic " + getBase64Credentials()); 
     return new HttpEntity<String>(headers); 
    } 

    private String getBase64Credentials(){ 
     String plainCreds = username + ":" + password; 
     byte[] plainCredsBytes = plainCreds.getBytes(); 
     byte[] base64CredsBytes = Base64.encodeBase64(plainCredsBytes); 
     return new String(base64CredsBytes); 
    } 
} 
関連する問題