我正在尝试使用Retrofit访问Google News API,但遇到了我的实施问题,如果有经验的人可以看一眼我的代码,我会很高兴。问题是查询已成功构建并输入response.isSuccessful(),但它没有任何条目。
我确保API正常运行(http://ajax.googleapis.com/ajax/services/feed/find?v=1.0&q=technology)。此外,通过使用参数构建查询,使用Postman进行测试:
我用http://www.jsonschema2pojo.org/生成了我的pojo。以下是课程:
NewsEntryApiEntry
public class NewsApiEntry {
@SerializedName("url")
@Expose
private String url;
@SerializedName("title")
@Expose
private String title;
@SerializedName("contentSnippet")
@Expose
private String contentSnippet;
@SerializedName("link")
@Expose
private String link;
/**
*
* @return
* The url
*/
public String getUrl() {
return url;
}
/**
*
* @param url
* The url
*/
public void setUrl(String url) {
this.url = url;
}
/**
*
* @return
* The title
*/
public String getTitle() {
return title;
}
/**
*
* @param title
* The title
*/
public void setTitle(String title) {
this.title = title;
}
/**
*
* @return
* The contentSnippet
*/
public String getContentSnippet() {
return contentSnippet;
}
/**
*
* @param contentSnippet
* The contentSnippet
*/
public void setContentSnippet(String contentSnippet) {
this.contentSnippet = contentSnippet;
}
/**
*
* @return
* The link
*/
public String getLink() {
return link;
}
/**
*
* @param link
* The link
*/
public void setLink(String link) {
this.link = link;
}
}
NewsApiResult
public class NewsApiResult {
@SerializedName("query")
@Expose
private String query;
@SerializedName("entries")
@Expose
private List<NewsApiEntry> entries = new ArrayList<NewsApiEntry>();
/**
*
* @return
* The query
*/
public String getQuery() {
return query;
}
/**
*
* @param query
* The query
*/
public void setQuery(String query) {
this.query = query;
}
/**
*
* @return
* The entries
*/
public List<NewsApiEntry> getEntries() {
return entries;
}
/**
*
* @param entries
* The entries
*/
public void setEntries(List<NewsApiEntry> entries) {
this.entries = entries;
}
}
改造服务生成器
public class NewsApiServiceGenerator {
public static final String API_BASE_URL = "http://ajax.googleapis.com/ajax/services/feed/";
private static OkHttpClient.Builder httpClient = new OkHttpClient.Builder();
private static Gson gson = new GsonBuilder()
.setDateFormat("yyyy-MM-dd'T'HH:mm:ssZ")
.create();
private static Retrofit.Builder retroBuilder = new Retrofit.Builder()
.baseUrl(API_BASE_URL)
.addConverterFactory(GsonConverterFactory.create(gson));
public static <S> S createService(Class<S> serviceClass) {
Retrofit retrofit = retroBuilder.client(httpClient.build()).build();
return retrofit.create(serviceClass);
}
}
最后,MainActivity:
public class MainActivity extends AppCompatActivity {
public static List<NewsApiEntry> newsArticles;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ButterKnife.bind(this);
newsArticles= new ArrayList<>();
fetchNewsArticles("technology");
}
private void fetchNewsArticles(String topic) {
NewsApiClient client = NewsApiServiceGenerator.createService(NewsApiClient.class);
Call<NewsApiResult> call = client.fetchNews("1.1", topic);
call.enqueue(new Callback<NewsApiResult>() {
@Override
public void onResponse(Call<NewsApiResult> call, Response<NewsApiResult> response) {
if(response.isSuccessful()) {
NewsApiResult res = response.body();
Log.d("API REQUEST URL: ", call.request().url().toString());
Log.d("API RESPONSE: ", response.raw().toString());
Log.d("API ENTRY COUNT: ", Integer.toString(res.getEntries().size()));
for(NewsApiEntry newsArticle : res.getEntries()) {
Log.d("API NEWS ENTRY TITLE: ", newsArticle.getTitle());
newsArticles.add(newsArticle);
}
} else {
int statusCode = response.code();
ResponseBody errorBody = response.errorBody();
Log.e("Network Error: ", errorBody.toString());
}
}
@Override
public void onFailure(Call<NewsApiResult> call, Throwable t) {
t.printStackTrace();
}
});
}
}
查询构建正确且响应的状态为200,但为什么我没有填充条目? 注意:我的库已正确加载,项目构建成功。
答案 0 :(得分:3)
{"responseData": {"query":"technology","entries":[...]}}
了解您的NewsApiResult
类如何映射包含在外部对象的responseData
属性中的属性。您还需要使用这样的新类映射该外部对象:
public class NewsApiResponse {
@SerializedName("responseData")
@Expose
private NewsApiResult responseData;
...
}
您的Retrofit调用必须如此声明:
Call<NewsApiResponse> call = client.fetchNews("1.1", topic);
那应该解决你的问题。