如何从Android调用RESTful Web服务?

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了如何从Android调用RESTful Web服务?相关的知识,希望对你有一定的参考价值。

我使用Jersey Framework和Java在Netbean IDE中编写了一个REST Web服务。

对于用户需要提供用户名和密码的每个请求,我知道此身份验证不是最佳做法(使用curl命令,如:curl -u username:password -X PUT http://localhsot:8080/user)。

现在我想从android类调用REST Web服务。

我该怎么办?

我有一个使用DefaultHttpClientCredentialUsernameAndPassword的Android类,但是当我在Eclipse中运行它时,有时我会遇到运行时异常或SDK异常。

答案

这是一个示例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 + "
");
            }
            is.close();
        }
        catch (IOException e)
        { }
        return sb.toString();
    }
}
另一答案

这是我为简单的Web服务调用创建的库,

你可以通过添加一行gradle依赖来使用它 -

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

这是使用的演示。

https://github.com/vishalchhodwani1992/httpLibrary

另一答案

有很多图书馆可以做到这一点

Retrofit取代了传统的AsyncTask,它有自己的后台任务,所以你真的不用担心它。相对于AsyncTask,性能也非常好。

在这里查看,

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

可以在这里找到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()让UI线程处理上一步中返回的结果。

这个答案提供了一个如何实现AsyncTask的好例子。见AsyncTask Android example

Per Ruffles的评论如下,这是使用AsyncTask进行REST调用的更相关示例:http://alvinalexander.com/android/android-asynctask-http-client-rest-example-tutorial

另一答案

最近发现第三方库 - 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序列化和deserailization。您也可以自定义序列化和反序列化。

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();
另一答案

我用这个REST Client为我的机器人。这看起来很酷。卢克的好作品。

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

另一答案

无论你做什么都停下来! :)

将RESTful客户端实现为SERVICE,并将密集型网络内容委托给与活动无关的组件:SERVICE。

观看这个富有洞察力的视频http://www.youtube.com/watch?v=xHXn3Kg2IQE,其中Virgil Dobjanschi正在解释他对这一挑战的态度......

另一答案

使用Spring for Android与RestTemplate https://spring.io/guides/gs/consuming-rest-android/

// The connection URL 
Stri

以上是关于如何从Android调用RESTful Web服务?的主要内容,如果未能解决你的问题,请参考以下文章

从 Android 向 .net Restful WebService 发送参数

从 PostgreSQL 过程/函数调用 RESTful Web 服务

如何在Informatica Cloud中创建进程实时暴露为Restful服务,可以从浏览器或其他地方调用?

如何自动调用 RESTful Web 服务

创建 Restful Web 服务以在 C# 中调用存储过程

在java中为一次调用执行两次Restful Web服务