URL формы HttpClient, содержащий параметр без значения

#java #web-services #httpclient

#java #веб-сервисы #httpclient

Вопрос:

Необходимо передать get параметр без значения и без символа «=», чтобы использовать внешний API. URL-адрес является

http://example.com/Service/v1/service.ashx?methodNameamp;name=valamp;blablabla

Как вы могли видеть, первый параметр — это имя метода (methodName), который будет вызван на сервере, и у него нет ни значения, ни «=». Я хочу сформировать параметры «правильным» способом, но на данный момент формирую их, как показано ниже:

     List<NameValuePair> params = new LinkedList<NameValuePair>();
    params.add(new BasicNameValuePair("name", "val"));
    params.add(new BasicNameValuePair("name1", "val1"));

    String paramString = URLEncodedUtils.format(params, "utf-8");

    HttpClient client = new DefaultHttpClient();
    HttpGet httpGet = new HttpGet(getEndpointUrl()   "?methodNameamp;"   paramString);
  

Проблема в последней строке, где используется конкатенация (вместо обычного преобразования параметров). Добавление «methodName» в качестве имени к параметрам и null в качестве значения дает «methodName=» в результирующем URL. Сервер не понимает такую запись.

Ответ №1:

Я думаю, вам было бы лучше сформировать URL вручную. Мы широко используем методы HttpGet, и когда мы создаем строки URL, мы делаем это вручную, чтобы гарантировать «правильность» параметра. Затем мы используем URIUtil из проекта HttpClient для кодирования строки запроса:

 // Start with your base method name, if necessary/known
String paramString = "methodName";
for (NameValuePair p : params ) {
    String n = p.getName();
    String v = p.getValue();
    if ( v == null ) {
        paramString  = "amp;"   n;
    } else {
        paramString  = "amp;"   n   "="   v;
    }
}

String url = "http://example.com/Service/v1/service.ashx?"   URIUtil.encodeQuery(paramString);
HttpGet get = new HttpGet(url);
  

Комментарии:

1. Похоже, мне нужно будет это сделать или объединить это решение с ответом Игоря.

2. Если проблема возникает только при использовании BasicNameValuePair, то это хорошее решение. В любом случае, я бы инкапсулировал этот код в какой-нибудь HttpServiceRequest и использовал бы его следующим образом: new HttpServiceRequest(ServiceName, параметры);

Ответ №2:

Лучше всего просматривать исходные файлы HttpClient. На первый взгляд кажется, что вам нужно создать подкласс HttpGet и переопределить метод getRequestLine, чтобы вернуть вашу реализацию интерфейса RequestLine, который соответствующим образом отформатирует URL.

Ответ №3:

Вы могли бы ввести фиктивное значение и не проверять его на сервере.

 params.add(new BasicNameValuePair("methodName", "unused"));
  

Комментарии:

1. API является внешним , поэтому не контролируется нашей стороной.