简体   繁体   English

Android Retrofit API的使用

[英]Android Retrofit API usage

I'm still beginner on retrofit API for android, im trying to pass a variable into my dynamic url but it adds extra characters to it these characters are "&=". 我仍然是Android改造API的新手,即时通讯试图将变量传递到我的动态url中,但会向其中添加额外的字符,这些字符为“&=”。

This is what the endpoint im trying to consume looks like: 这是端点即时尝试消耗的内容:

https://www.example.com/api/index.php?/Playlists/getTracks/00978d67f6933af10ec8bd8045f089a4/0673CC13-476A-4786-BF27-13ADD9C44261/9392 https://www.example.com/api/index.php?/Playlists/getTracks/00978d67f6933af10ec8bd8045f089a4/0673CC13-476A-4786-BF27-13ADD9C44261/9392

where "9232" is the id i am trying to pass. 其中“ 9232”是我要传递的ID。 However when i use the retrofit library this is what my generated Url looks like: 但是,当我使用改造库时,这就是我生成的网址的样子:

https://www.example.com/api/index.php?/Playlists/getTracks/00978d67f6933af10ec8bd8045f089a4/0673CC13-476A-4786-BF27-13ADD9C44261/&=9392 https://www.example.com/api/index.php?/Playlists/getTracks/00978d67f6933af10ec8bd8045f089a4/0673CC13-476A-4786-BF27-13ADD9C44261/&=9392

Notice the &= being attached to the Id im sending 请注意, &=附加在ID即时发送中

// Method that receives id and calls the retrofit API
private void getPlaylist(String id) {
    /*Create handle for the RetrofitInstance interface*/
    GetPlaylistRetrofitInterface playlistService = PlaylistClientInstance.getRetrofitInstance().create(GetPlaylistRetrofitInterface.class);

    Call<List<Playlists>> call = playlistService.getPlaylist(id);
    Log.d("URL", "getPlaylist: " + call.request().url());
    call.enqueue(new Callback<List<Playlists>>() {
        @Override
        public void onResponse(Call<List<Playlists>> call, Response<List<Playlists>> response) {
            myProgressBar.setVisibility(View.GONE);
            populatePlayList(response.body());
        }

        @Override
        public void onFailure(Call<List<Playlists>> call, Throwable throwable) {
            myProgressBar.setVisibility(View.GONE);
            Log.d("onFailure", "onFailure: " + throwable);
            Toast.makeText(getActivity(), throwable.getMessage(), Toast.LENGTH_LONG).show();
        }
    });
}

And this is the interface where i am receiving the url id and attaching it to the endpoint 这是我接收网址ID并将其附加到端点的接口

public interface GetPlaylistRetrofitInterface {
    @GET("index.php?/Playlists/getTracks/00978d67f6933af10ec8bd8045f089a4/0673CC13-476A-4786-BF27-13ADD9C44261/")
    Call<List<Playlists>> getPlaylist(@Query(value = "") String id);
}

I have tried using @Path in my interface 我尝试在界面中使用@Path

public interface GetPlaylistRetrofitInterface {
    @GET("index.php?/Playlists/getTracks/00978d67f6933af10ec8bd8045f089a4/0673CC13-476A-4786-BF27-13ADD9C44261/{id}")
    Call<List<Playlists>> getPlaylist(@Path("id") String id);
}

However it made my app crash with this error: 但是,它使我的应用崩溃,并显示以下错误:

 java.lang.RuntimeException: Unable to start activity ComponentInfo{com.demoapp.HomeActivity}:
 java.lang.IllegalArgumentException: URL query string "/Playlists/getTracks/00978d67f6933af10ec8bd8045f089a4/0673CC13-476A-4786-BF27-13ADD9C44261/{id}" must not have replace block. For dynamic query parameters use @Query.
            for method GetPlaylistRetrofitInterface.getPlaylist
            at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2778)
            at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2856)
            at android.app.ActivityThread.-wrap11(Unknown Source:0)
            at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1589)
            at android.os.Handler.dispatchMessage(Handler.java:106)
            at android.os.Looper.loop(Looper.java:164)
            at android.app.ActivityThread.main(ActivityThread.java:6494)
            at java.lang.reflect.Method.invoke(Native Method)
            at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:440)
            at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:807)

Thanks in Advance 提前致谢

Okay so i was able to Fix the issue, I turned out i was trying to pass a query by using @Query to an endpoint which is already a query so this is how i fixed it: 好的,所以我能够解决此问题,事实证明,我试图通过使用@Query传递查询到已经是查询的端点,因此这是我解决的方法:

This is my updated GetPlaylistInterface 这是我更新的GetPlaylistInterface

public interface GetPlaylistRetrofitInterface {
    @GET()
    Call<List<Playlists>> getPlaylist(@Url String url);
}

This is my updated Get Playlist method 这是我更新的“获取播放列表”方法

private void getPlaylist(String id) {
    myProgressBar.setVisibility(View.VISIBLE);
    /*Create handle for the RetrofitInstance interface*/
    GetPlaylistRetrofitInterface playlistService = RetrofitClientInstance.getRetrofitInstance().create(GetPlaylistRetrofitInterface.class);
    Call<List<Playlists>> call = playlistService.getPlaylist(Config.playlist_url+id);
    Log.d("URL", "getPlaylist: " + call.request().url());
    call.enqueue(new Callback<List<Playlists>>() {
        @Override
        public void onResponse(Call<List<Playlists>> call, Response<List<Playlists>> response) {
            myProgressBar.setVisibility(View.GONE);
            populatePlayList(response.body());
        }

        @Override
        public void onFailure(Call<List<Playlists>> call, Throwable throwable) {
            myProgressBar.setVisibility(View.GONE);
            Log.d("onFailure", "onFailure: " + throwable);
            Toast.makeText(getActivity(), throwable.getMessage(), Toast.LENGTH_LONG).show();
        }
    });
}

And this is the config class containing the endpoints: 这是包含端点的配置类:

public class Config {
    public static String playlist_url = "index.php?/Playlists/getTracks/00978d67f6933af10ec8bd8045f089a4/0673CC13-476A-4786-BF27-13ADD9C44261/";
    public static String playlist_details_url = "index.php?/Tracks/get/00978d67f6933af10ec8bd8045f089a4/0673CC13-476A-4786-BF27-13ADD9C44261/";
}

You're using @Query parameter, which has this syntax by default. 您正在使用@Query参数,默认情况下具有此语法。 What your need is to use @Path instead of @Query. 您需要使用@Path而不是@Query。 Also you need to include name of parameter into your url string. 另外,您还需要在网址字符串中包含参数名称。

Your code will look somehow like this: 您的代码看起来像这样:

public interface GetPlaylistRetrofitInterface {
@GET("index.php?/Playlists/getTracks/00978d67f6933af10ec8bd8045f089a4/0673CC13-476A-4786-BF27-13ADD9C44261/{id}")
Call<List<Playlists>> getPlaylist(@Path("id") String id);

} }

You almost Have it first You need to use Query Parameter for you query String and Path for url/uri manipulation seems like you had those mixed up now below example should work 您几乎首先拥有它。您需要使用Query Parameter来查询String和Path以进行url / uri操作,似乎您已经将这些混淆了,下面的示例应该可以工作

public interface ApiServices {
@GET("index.php?/Playlists/getTracks/00978d67f6933af10ec8bd8045f089a4/0673CC13-476A-4786-BF27-13ADD9C44261/{id}")
Call<ResponseBody> getTracks(@Path("id") String id);
}

EDIT: 编辑:

You need to only define Interface and call it once. 您只需要定义接口并调用一次即可。 Above is interface and below is how to call it from a functions like your trying to do... its weird you have index.php? 上面是接口,下面是如何从类似您想要执行的功能中调用它……奇怪的是您拥有index.php? are you sure that is needed. 您确定需要吗?

  // Method that receives id and calls the retrofit API
private void getPlaylist(String id) {
/*Create handle for the RetrofitInstance interface*/
OkHttpClient client = new OkHttpClient.Builder()


               .retryOnConnectionFailure(true)
               .build();
       Retrofit retrofit = new Retrofit.Builder()
               .client(client)
               .baseUrl("https://stepank.com/")
               .build();

       ApiServices service = retrofit.create(ApiServices.class);

       try {


           Call<ResponseBody> call = service.getTracks(id);
           call.enqueue(new Callback<ResponseBody>() {
               @Override
               public void onResponse(Call<ResponseBody> call, Response<ResponseBody> response) {
                   int result = -1;
                   setRefreshActionButtonState(false);

                   if (response.isSuccessful()) {
                       ///DO STUFF HERE WITH RESPONSE
                }
                                   }
               }

               @Override
               public void onFailure(Call<ResponseBody> call, Throwable t) {
                   t.printStackTrace();
               }
           });

} }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM