/** * Licensed to the Apache Software Foundation (ASF) under one * or more contributor license agreements. See the NOTICE file * distributed with this work for additional information * regarding copyright ownership. The ASF licenses this file * to you under the Apache License, Version 2.0 (the * "License"); you may not use this file except in compliance * with the License. You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package org.apache.hadoop.fs.azure; import com.google.common.annotations.VisibleForTesting; import org.apache.http.Header; import org.apache.http.HttpResponse; import org.apache.http.HttpStatus; import org.apache.http.StatusLine; import org.apache.http.client.ClientProtocolException; import org.apache.http.client.HttpClient; import org.apache.http.client.methods.HttpGet; import org.apache.http.impl.client.HttpClientBuilder; import java.io.BufferedReader; import java.io.IOException; import java.io.InputStreamReader; import java.nio.charset.StandardCharsets; /** * Helper class the has constants and helper methods * used in WASB when integrating with a remote http cred * service. Currently, remote service will be used to generate * SAS keys. */ class WasbRemoteCallHelper { /** * Return code when the remote call is successful. {@value} */ public static final int REMOTE_CALL_SUCCESS_CODE = 0; /** * Client instance to be used for making the remote call. */ private HttpClient client = null; @VisibleForTesting public void updateHttpClient(HttpClient client) { this.client = client; } public WasbRemoteCallHelper() { this.client = HttpClientBuilder.create().build(); } /** * Helper method to make remote HTTP Get request. * @param getRequest - HttpGet request object constructed by caller. * @return Http Response body returned as a string. The caller * is expected to semantically understand the response. * @throws WasbRemoteCallException * @throws IOException */ public String makeRemoteGetRequest(HttpGet getRequest) throws WasbRemoteCallException, IOException { try { final String APPLICATION_JSON = "application/json"; final int MAX_CONTENT_LENGTH = 1024; getRequest.setHeader("Accept", APPLICATION_JSON); HttpResponse response = client.execute(getRequest); StatusLine statusLine = response.getStatusLine(); if (statusLine == null || statusLine.getStatusCode() != HttpStatus.SC_OK) { throw new WasbRemoteCallException(getRequest.getURI().toString() + ":" + ((statusLine!=null) ? statusLine.toString() : "NULL") ); } Header contentTypeHeader = response.getFirstHeader("Content-Type"); if (contentTypeHeader == null || !APPLICATION_JSON.equals(contentTypeHeader.getValue())) { throw new WasbRemoteCallException(getRequest.getURI().toString() + ":" + "Content-Type mismatch: expected: " + APPLICATION_JSON + ", got " + ((contentTypeHeader!=null) ? contentTypeHeader.getValue() : "NULL") ); } BufferedReader rd = new BufferedReader( new InputStreamReader(response.getEntity().getContent(), StandardCharsets.UTF_8)); StringBuilder responseBody = new StringBuilder(); String responseLine = ""; while ((responseLine = rd.readLine()) != null) { responseBody.append(responseLine); } rd.close(); return responseBody.toString(); } catch (ClientProtocolException clientProtocolEx) { throw new WasbRemoteCallException(getRequest.getURI().toString() + ":" + "Encountered ClientProtocolException while making remote call", clientProtocolEx); } catch (IOException ioEx) { throw new WasbRemoteCallException(getRequest.getURI().toString() + ":" + "Encountered IOException while making remote call", ioEx); } } }