如何在Android中使用Retrofit发送JSON POST请求并接收字符串响应

3

我第一次使用Retrofit2,遇到了一些问题。

这是用于调用REST API的代码片段:

    //building retrofit object
    Retrofit retrofit = new Retrofit.Builder()
            .baseUrl("http://192.168.0.71:9000/api/uniapp/")
            .addConverterFactory(GsonConverterFactory.create())
            .addConverterFactory(ScalarsConverterFactory.create())
            .build();

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

    //defining the call
    Call<String> call = service.refreshAppMetaConfig("0");
    //calling the api
    call.enqueue(new Callback<String>() {
        @Override
        public void onResponse(Call<String> call, Response<String> response) {
            //displaying the message from the response as toast
            System.out.println("Uniapp :"+response);
        }

        @Override
        public void onFailure(Call<String> call, Throwable t) {
            System.out.println("Uniapp :"+t.getMessage());
        }
    });

这是APIService类:

public interface APIService {

    //The register call
    @FormUrlEncoded
    @POST("appmetaconfigjson")
    Call<String> refreshAppMetaConfig(@Field("versionId") String versionId);
}

我正在使用Play框架创建REST API,但是遇到了内部服务器错误。API无法读取JSON请求。但是,如果我通过Postman访问API,则会返回响应。有什么建议吗?
我已经添加了Postman请求的截图。 Postman Sample

如何设置头部? - Arjun Issar
请确保您的URL端点和参数正确,可能存在错误。 - Mochamad Taufik Hidayat
当我插入标题时,它会显示“此处不允许注释”。 - Arjun Issar
你的参数使用了raw,因此可能会在API服务上发生更改,请参考以下链接:https://dev59.com/YmEi5IYBdhLWcg3wUK6C - Mochamad Taufik Hidayat
显示剩余5条评论
1个回答

6

从您的Postman截图中可以看出,您正在向REST API发送JSON正文。当您在Postman中选择正文类型为raw - application/json时,它会自动包含。

Content-Type:application/json

作为标题。因此,Postman中的请求成功。

现在,为了使您的Android应用程序成功执行上述请求,您需要在发送到REST API的请求中设置标头。

APIService接口中进行以下更改。

import retrofit2.http.Body;
import okhttp3.ResponseBody;
import java.util.Map;


public interface APIService {

  //The register call
  // @FormUrlEncoded    <====  comment or remove this line

   @Headers({
        "Content-Type:application/json"
   })
   @POST("appmetaconfigjson")
   Call<ResponseBody> refreshAppMetaConfig(@Body Map<String, String> versionId);
}
  1. 移除或注释掉@FormUrlEncoded注解,因为我们发送的是JSON数据而非FormUrlEncoded数据。
  2. 添加带有Content-Type:application/json@Headers()注解。
  3. 将方法参数改为@Body Map<String, String> versionId@Body注解在请求API时将Map(HashMap)数据转换(序列化)为JSON体。
  4. 将返回参数从String更改为ResponseBody

使用以上修改后的方法如下:

// code...

//defining the call

// create parameter with HashMap
Map<String, String> params = new HashMap<>();
params.put("versionId", "0");

Call<ResponseBody> call = service.refreshAppMetaConfig(params);
//calling the api
call.enqueue(new Callback<ResponseBody>() {
    @Override
    public void onResponse(Call<ResponseBody> call, Response<ResponseBody> response) {
        //displaying the message from the response as toast

        // convert ResponseBody data to String
        String data = response.body().string();

        System.out.println("Uniapp : " + data);
    }

    @Override
    public void onFailure(Call<ResponseBody> call, Throwable t) {
        System.out.println("Uniapp : " + t.getMessage());
    }
});

这里你还需要将参数从Call<String>更改为Call<ResponseBody>。然后在onResponse()方法内使用response.body().string();来转换响应。


请仔细检查答案中使用的方法名称、导入和参数,如果有任何疑问,请直接复制粘贴代码。 - Shashanth

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接