it-roy-ru.com

Как вызвать RESTful веб-сервис с Android?

Я написал веб-сервис REST в Netbean IDE, используя Jersey Framework и Java. 

Для каждого запроса пользователь должен предоставить имя пользователя и пароль, я знаю, что эта аутентификация не является наилучшей практикой (используя команду curl, такую ​​как: curl -u username:password -X PUT http://localhsot:8080/user).

Теперь я хочу вызвать веб-сервис REST из класса Android. 

Как я должен это делать? 

У меня есть класс Android, который использует DefaultHttpClient и CredentialUsernameAndPassword, но когда я запускаю его в Eclipse, иногда я получаю исключение времени выполнения или SDK.

47
sudo

Это пример класса restclient

public class RestClient
{
    public enum RequestMethod
    {
        GET,
        POST
    }
    public int responseCode=0;
    public String message;
    public String response;
    public void Execute(RequestMethod method,String url,ArrayList<NameValuePair> headers,ArrayList<NameValuePair> params) throws Exception
    {
        switch (method)
        {
            case GET:
            {
                // add parameters
                String combinedParams = "";
                if (params!=null)
                {
                    combinedParams += "?";
                    for (NameValuePair p : params)
                    {
                        String paramString = p.getName() + "=" + URLEncoder.encode(p.getValue(),"UTF-8");
                        if (combinedParams.length() > 1)
                            combinedParams += "&" + paramString;
                        else
                            combinedParams += paramString;
                    }
                }
                HttpGet request = new HttpGet(url + combinedParams);
                // add headers
                if (headers!=null)
                {
                    headers=addCommonHeaderField(headers);
                    for (NameValuePair h : headers)
                        request.addHeader(h.getName(), h.getValue());
                }
                executeRequest(request, url);
                break;
            }
            case POST:
            {
                HttpPost request = new HttpPost(url);
                // add headers
                if (headers!=null)
                {
                    headers=addCommonHeaderField(headers);
                    for (NameValuePair h : headers)
                        request.addHeader(h.getName(), h.getValue());
                }
                if (params!=null)
                    request.setEntity(new UrlEncodedFormEntity(params, HTTP.UTF_8));
                executeRequest(request, url);
                break;
            }
        }
    }
    private ArrayList<NameValuePair> addCommonHeaderField(ArrayList<NameValuePair> _header)
    {
        _header.add(new BasicNameValuePair("Content-Type","application/x-www-form-urlencoded"));
        return _header;
    }
    private void executeRequest(HttpUriRequest request, String url)
    {
        HttpClient client = new DefaultHttpClient();
        HttpResponse httpResponse;
        try
        {
            httpResponse = client.execute(request);
            responseCode = httpResponse.getStatusLine().getStatusCode();
            message = httpResponse.getStatusLine().getReasonPhrase();
            HttpEntity entity = httpResponse.getEntity();

            if (entity != null)
            {
                InputStream instream = entity.getContent();
                response = convertStreamToString(instream);
                instream.close();
            }
        }
        catch (Exception e)
        { }
    }

    private static String convertStreamToString(InputStream is)
    {
        BufferedReader reader = new BufferedReader(new InputStreamReader(is));
        StringBuilder sb = new StringBuilder();
        String line = null;
        try
        {
            while ((line = reader.readLine()) != null)
            {
                sb.append(line + "\n");
            }
            is.close();
        }
        catch (IOException e)
        { }
        return sb.toString();
    }
}
19
Varghese John

Недавно обнаружил, что сторонняя библиотека - Square Retrofit может выполнять эту работу очень хорошо.


Определение конечной точки REST

public interface GitHubService {
   @GET("/users/{user}/repos")
   List<Repo> listRepos(@Path("user") String user,Callback<List<User>> cb);
}

Получение конкретной услуги

RestAdapter restAdapter = new RestAdapter.Builder()
    .setEndpoint("https://api.github.com")
    .build();
GitHubService service = restAdapter.create(GitHubService.class);

Вызов конечной точки REST

List<Repo> repos = service.listRepos("octocat",new Callback<List<User>>() { 
    @Override
    public void failure(final RetrofitError error) {
        Android.util.Log.i("example", "Error, body: " + error.getBody().toString());
    }
    @Override
    public void success(List<User> users, Response response) {
        // Do something with the List of Users object returned
        // you may populate your adapter here
    }
});

Библиотека обрабатывает сериализацию и десериализацию JSON для вас. Вы также можете настроить сериализацию и десериализацию.

Gson gson = new GsonBuilder()
    .setFieldNamingPolicy(FieldNamingPolicy.LOWER_CASE_WITH_UNDERSCORES)
    .registerTypeAdapter(Date.class, new DateTypeAdapter())
    .create();

RestAdapter restAdapter = new RestAdapter.Builder()
    .setEndpoint("https://api.github.com")
    .setConverter(new GsonConverter(gson))
    .build();
14
Tianhai

Прекратите делать то, что вы делали! :) 

Реализуйте клиент RESTful как SERVICE и делегируйте интенсивный сетевой компонент независимому компоненту активности: SERVICE. 

Посмотрите это проницательное видео http://www.youtube.com/watch?v=xHXn3Kg2IQE где Вирджил Добжански объясняет свой подход (ы) к этой проблеме ...

6
luigi7up

Я использую этот REST клиент для моего Android. Это выглядит действительно круто. Хорошая работа Люка.

http://lukencode.com/2010/04/27/calling-web-services-in-Android-using-httpclient/

6
Naveen Vijay

Я использовал OkHttpClient для вызова успокоительного веб-сервиса. Это очень просто.

OkHttpClient httpClient = new OkHttpClient();
Request request = new Request.Builder()
                .url(url)
                .build();

Response response = httpClient.newCall(request).execute();
String body = response.body().string()
1
taynguyen

Использование Spring для Android с RestTemplate https://spring.io/guides/gs/consuming-rest-Android/

// The connection URL 
String url = "https://ajax.googleapis.com/ajax/" + 
    "services/search/web?v=1.0&q={query}";

// Create a new RestTemplate instance
RestTemplate restTemplate = new RestTemplate();

// Add the String message converter
restTemplate.getMessageConverters().add(new StringHttpMessageConverter());

// Make the HTTP GET request, marshaling the response to a String
String result = restTemplate.getForObject(url, String.class, "Android");
1
Igor Vuković

Выполните следующие шаги, чтобы использовать RestFul в Android.

Шаг 1

Создайте пустой проект Android.

Шаг 2

Нужно разрешение доступа в интернет. напишите приведенный ниже код в файле AndroidManifest.xml.

 <uses-permission Android:name="Android.permission.INTERNET">
</uses-permission>

Шаг 3

Нужен URL RestFul, который работает на другом сервере или той же машине.

Step4

Сделайте RestFul Client, который расширит AsyncTask. Смотрите RestFulPost.Java.

Step5

Сделайте класс DTO для запросов и ответов RestFull.

RestFulPost.Java

package javaant.com.consuming_restful.restclient;
import Android.app.ProgressDialog;
import Android.content.Context;
import Android.os.AsyncTask;
import Android.util.Log;
import com.google.gson.Gson;
import org.Apache.http.HttpResponse;
import org.Apache.http.client.methods.HttpPost;
import org.Apache.http.entity.StringEntity;
import org.Apache.http.impl.client.DefaultHttpClient;
import org.Apache.http.util.EntityUtils;
import Java.util.Map;
import javaant.com.consuming_restful.util.Util;
/**
 * Created by Nirmal Dhara on 29-10-2015.
 */
public class RestFulPost extends AsyncTask<map, void,="" string=""> {
    RestFulResult restFulResult = null;
    ProgressDialog Asycdialog;
    String msg;
    String task;
    public RestFulPost(RestFulResult restFulResult, Context context, String msg,String task) {
        this.restFulResult = restFulResult;
        this.task=task;
        this.msg = msg;
        Asycdialog = new ProgressDialog(context);
    }
    @Override
    protected String doInBackground(Map... params) {
        String responseStr = null;
        Object dataMap = null;
        HttpPost httpost = new HttpPost(params[0].get("url").toString());

        try {
            dataMap = (Object) params[0].get("data");
            Gson gson = new Gson();
            Log.d("data  map", "data map------" + gson.toJson(dataMap));
            httpost.setEntity(new StringEntity(gson.toJson(dataMap)));
            httpost.setHeader("Accept", "application/json");
            httpost.setHeader("Content-type", "application/json");
            DefaultHttpClient httpclient= Util.getClient();
            HttpResponse response = httpclient.execute(httpost);
            int statusCode = response.getStatusLine().getStatusCode();
            Log.d("resonse code", "----------------" + statusCode);

            if (statusCode == 200)
                responseStr = EntityUtils.toString(response.getEntity());
            if (statusCode == 404) {
                responseStr = "{\n" +
                        "\"status\":\"fail\",\n" +
                        " \"data\":{\n" +
                        "\"ValidUser\":\"Service not available\",\n" +
                        "\"code\":\"404\"\n" +
                        "}\n" +
                        "}";
            }

        } catch (Exception e) {
            e.printStackTrace();
        }
        return responseStr;
    }
    @Override
    protected void onPreExecute() {
        Asycdialog.setMessage(msg);
        //show dialog
        Asycdialog.show();
        super.onPreExecute();
    }
    @Override
    protected void onPostExecute(String s) {
        Asycdialog.dismiss();
        restFulResult.onResfulResponse(s,task);
    }
}

Для получения более подробной информации и полного кода, пожалуйста, посетите http://javaant.com/consume-a-restful-webservice-in-Android/#.VwzbipN96Hs

0
Nirmal Dhara

Какой бэкэнд? Если Java, то вы можете использовать REST с Java (JAX-RS), используя Джерси.

На стороне Android вы можете использовать этот простой RestClient для работы с этим сервисом REST.

Для JSON <-> сопоставления объектов с обеих сторон (Android, Java back-end) вы можете использовать GSON.

0
Komal Nikhare

Возможно, я опоздал или, может быть, вы уже использовали его раньше, но есть другой, называемый ksoap , и он довольно удивительный. Он также включает тайм-ауты и может эффективно анализировать любой веб-сервис на основе SOAP. Я также сделал несколько изменений, чтобы удовлетворить мой анализ .. Посмотрите это 

0
Olu Smith

Вот моя библиотека, которую я создал для простого вызова Webservice,

Вы можете использовать это, добавив однострочную зависимость - 

compile 'com.scantity.ScHttpLibrary:ScHttpLibrary:1.0.0'

Вот демонстрация использования.

https://github.com/vishalchhodwani1992/httpLibrary

0
Vishal Chhodwani

Для этого есть множество библиотек. 

Retrofit заменяет традиционный AsyncTask и имеет собственную фоновую задачу, так что вам не нужно об этом беспокоиться. Производительность также очень хорошая по сравнению с AsyncTask.

Проверьте это здесь,

http://square.github.io/retrofit/

Полный пример модернизации можно найти здесь,

https://futurestud.io/blog/retrofit-getting-started-and-Android-client/

Volley также эффективен и прост в использовании. Вы можете посмотреть здесь:

https://github.com/mcxiaoke/Android-volley

В сети есть куча ресурсов о том, как его использовать:

http://www.androidhive.info/2014/05/Android-working-with-volley-library-1

AsyncTask 

ИЛИ Вы должны использовать AsyncTask, а затем переопределить метод doInTheBackground(), где вы можете реализовать вызов REST.

Затем вы можете использовать onPostExecute(), чтобы позволить потоку пользовательского интерфейса обрабатывать результаты, которые были возвращены на предыдущем шаге.

Этот ответ является хорошим примером того, как реализовать AsyncTask. см. пример Android AsyncTask

В соответствии с комментарием Раффлса ниже приведен более уместный пример вызова REST с использованием AsyncTask: http://alvinalexander.com/Android/android-asynctask-http-client-rest-example-tutorial

0
Umer