/**
   * Takes the extracted base URI and parameters from the {@link RequestConfig} consolidated
   * parameter type and creates a {@link HttpRequestBase} of the designated method type.
   *
   * @param uri the {@link URI} whose parameters should be populated
   * @param annotatedParams the list of {@link Param}s and the parameter objects which were
   *     annotated with them; <b>Complex objects should supply a formatted version of their String
   *     representation via {@link Object#toString()}</b>
   * @param staticParams the list of {@link Request.Param}s and the parameter objects which were
   *     annotated with them <br>
   *     <br>
   * @return the created {@link HttpRequestBase} which is an instance of {@link HttpPost} <br>
   *     <br>
   * @throws Exception when the {@link HttpRequestBase} could not be created due to an exception
   *     <br>
   *     <br>
   * @since 1.1.3
   */
  private static HttpRequestBase populatePutParameters(
      URI uri, Map<Object, Param> annotatedParams, List<Request.Param> staticParams)
      throws Exception {

    List<NameValuePair> nameValuePairs = new ArrayList<NameValuePair>();

    for (Request.Param param : staticParams)
      nameValuePairs.add(new BasicNameValuePair(param.name(), param.value()));

    Set<Entry<Object, Param>> methodParams = annotatedParams.entrySet();

    for (Entry<Object, Param> entry : methodParams)
      nameValuePairs.add(
          new BasicNameValuePair(entry.getValue().value(), entry.getKey().toString()));

    UrlEncodedFormEntity urlEncodedFormEntity = new UrlEncodedFormEntity(nameValuePairs);
    urlEncodedFormEntity.setContentType(ContentType.APPLICATION_FORM_URLENCODED.getMimeType());

    HttpPut httpPut = new HttpPut(uri);

    httpPut.setHeader(
        HttpHeaders.CONTENT_TYPE.getHeaderName(),
        ContentType.APPLICATION_FORM_URLENCODED.getMimeType());

    httpPut.setEntity(new UrlEncodedFormEntity(nameValuePairs));

    return httpPut;
  }
  /**
   * Takes the extracted base URI and parameters from the {@link RequestConfig} consolidated
   * parameter type and creates a {@link HttpRequestBase} of the designated method type.
   *
   * @param uri the {@link URI} whose parameters should be populated
   * @param annotatedParams the list of {@link Param}s and the parameter objects which were
   *     annotated with them
   * @param staticParams the list of {@link Request.Param}s and the parameter objects which were
   *     annotated with them <br>
   *     <br>
   * @return the created {@link HttpRequestBase} which is an instance of {@link HttpGet} <br>
   *     <br>
   * @throws Exception when the {@link HttpRequestBase} could not be created due to an exception
   *     <br>
   *     <br>
   * @since 1.1.2
   */
  private static HttpRequestBase populateGetParameters(
      URI uri, Map<Object, Param> annotatedParams, List<Request.Param> staticParams)
      throws Exception {

    Uri.Builder uriBuilder = Uri.parse(uri.toASCIIString()).buildUpon();

    for (Request.Param param : staticParams)
      uriBuilder.appendQueryParameter(param.name(), param.value());

    Set<Entry<Object, Param>> methodParams = annotatedParams.entrySet();

    for (Entry<Object, Param> entry : methodParams) {

      if (!(entry.getKey() instanceof String)) {

        StringBuilder message = new StringBuilder();

        message.append("Parameters for GET requests can only be of type ");
        message.append(String.class.getName());
        message.append(
            "\nIf it is a complex type, consider overriding toString() "
                + "and providing a meaningful String representation");

        throw new IllegalArgumentException(message.toString());
      }

      uriBuilder.appendQueryParameter(entry.getValue().value(), (String) entry.getKey());
    }

    return new HttpGet(uriBuilder.build().toString());
  }
  /**
   * Takes the extracted base URI and parameters from the {@link RequestConfig} consolidated
   * parameter type and creates a {@link HttpRequestBase} of the designated method type.
   *
   * @param uri the {@link URI} whose parameters should be populated
   * @param annotatedParams the list of {@link Param}s and the parameter objects which were
   *     annotated with them; <b>Complex objects should supply a formatted version of their String
   *     representation via {@link Object#toString()}</b>
   * @param staticParams the list of {@link Request.Param}s and the parameter objects which were
   *     annotated with them <br>
   *     <br>
   * @return the created {@link HttpRequestBase} which is an instance of {@link HttpPost} <br>
   *     <br>
   * @throws Exception when the {@link HttpRequestBase} could not be created due to an exception
   *     <br>
   *     <br>
   * @since 1.1.3
   */
  private static HttpRequestBase populateDeleteParameters(
      URI uri, Map<Object, Param> annotatedParams, List<Request.Param> staticParams)
      throws Exception {

    HttpParams httpParams = new BasicHttpParams();

    for (Request.Param param : staticParams) httpParams.setParameter(param.name(), param.value());

    Set<Entry<Object, Param>> methodParams = annotatedParams.entrySet();

    for (Entry<Object, Param> entry : methodParams)
      httpParams.setParameter(entry.getValue().value(), entry.getKey().toString());

    HttpDelete httpDelete = new HttpDelete(uri);
    httpDelete.setParams(httpParams);

    return httpDelete;
  }