如何使用 Retrofit2 在 API 请求中传递原始数据

How to pass raw data in API request using Retrofit2

我正在尝试使用 Retrofit2 调用 login API

但是在 onResponse 中,我总是得到 null 作为响应。

登录API端点

@FormUrlEncoded 
@POST("/api/login/{mobile}") 
Call<ResObj> userLogin( @Field("phoneNumber") String mobile );

API实现

private void doLogin(final String mobile){
        Call<ResObj> call = userService.login(mobile);
        call.enqueue(new Callback<ResObj>() {
            @Override
            public void onResponse(Call<ResObj> call, Response<ResObj> response) {

                    ResObj resObj = response.body(); // here i am getting null response.body()

                    if(resObj.getMessage().equals("true")){

                        Intent intent = new Intent(Login.this, ListActivity.class);
                        intent.putExtra("mobile", mobile);
                        startActivity(intent);

                    } else{
                        Toast.makeText(Login.this, "Phone Number is incorrect!", Toast.LENGTH_SHORT).show();

                    }
                }

            @Override
            public void onFailure(Call<ResObj> call, Throwable t) {
                Toast.makeText(Login.this, t.getMessage(), Toast.LENGTH_SHORT).show();
            }
        });

    }

ResObj class:

public class ResObj {
    private String message;

    public String getMessage() {
        return message;
    }

    public void setMessage(String message) {
        this.message = message;
    }
}

我只想知道导致错误的原因以及可能的解决方案。

更新

邮递员[=3​​9=]

您在登录 API 中收到 null 响应。这可能是由于许多原因。您可以使用 POSTMAN.

检查您的 API 是否按预期工作

在您的代码中,您可以通过检查 OBJECT 是否为 null 来防止此类 exception。像下面这样。

@Override
public void onResponse(Call<ResObj> call, Response<ResObj> response) {

       ResObj resObj = response.body();

       if(resObj != null){ // checking object is not null

          if(resObj.getStatus()){

              Intent intent = new Intent(Login.this, ListActivity.class);
              intent.putExtra("mobile", mobile);
              startActivity(intent);

          } else{
              Toast.makeText(Login.this, "Phone Number is incorrect!", Toast.LENGTH_SHORT).show();
          }
       }else{
          // handle null response here.
       }
}

更新:

根据您的 Response JSON,您的模型 (ResObj) class 应该如下所示。

public class ResObj 
{
    private String date;

    private String address;

    private String accountName;

    private String contactPerson;

    private String timeOut;

    private String problem;

    private String srNo;

    private String fieldEngineer;

    private String joNo;

    private String irNo;

    private String designation;

    private String email;

    private String timeIn;

    private String productType;

    private boolean status;

    private String contactNo;

    public String getDate ()
    {
        return date;
    }

    public void setDate (String date)
    {
        this.date = date;
    }

    public String getAddress ()
    {
        return address;
    }

    public void setAddress (String address)
    {
        this.address = address;
    }

    public String getAccountName ()
    {
        return accountName;
    }

    public void setAccountName (String accountName)
    {
        this.accountName = accountName;
    }

    public String getContactPerson ()
    {
        return contactPerson;
    }

    public void setContactPerson (String contactPerson)
    {
        this.contactPerson = contactPerson;
    }

    public String getTimeOut ()
    {
        return timeOut;
    }

    public void setTimeOut (String timeOut)
    {
        this.timeOut = timeOut;
    }

    public String getProblem ()
    {
        return problem;
    }

    public void setProblem (String problem)
    {
        this.problem = problem;
    }

    public String getSrNo ()
    {
        return srNo;
    }

    public void setSrNo (String srNo)
    {
        this.srNo = srNo;
    }

    public String getFieldEngineer ()
    {
        return fieldEngineer;
    }

    public void setFieldEngineer (String fieldEngineer)
    {
        this.fieldEngineer = fieldEngineer;
    }

    public String getJoNo ()
    {
        return joNo;
    }

    public void setJoNo (String joNo)
    {
        this.joNo = joNo;
    }

    public String getIrNo ()
    {
        return irNo;
    }

    public void setIrNo (String irNo)
    {
        this.irNo = irNo;
    }

    public String getDesignation ()
    {
        return designation;
    }

    public void setDesignation (String designation)
    {
        this.designation = designation;
    }

    public String getEmail ()
    {
        return email;
    }

    public void setEmail (String email)
    {
        this.email = email;
    }

    public String getTimeIn ()
    {
        return timeIn;
    }

    public void setTimeIn (String timeIn)
    {
        this.timeIn = timeIn;
    }

    public String getProductType ()
    {
        return productType;
    }

    public void setProductType (String productType)
    {
        this.productType = productType;
    }

    public boolean getStatus ()
    {
        return status;
    }

    public void setStatus (boolean status)
    {
        this.status = status;
    }

    public String getContactNo ()
    {
        return contactNo;
    }

    public void setContactNo (String contactNo)
    {
        this.contactNo = contactNo;
    }
}

您正在将参数作为 raw 数据传递(根据您的屏幕截图)。因此,您的 API 端点将如下所示。

@Headers("Content-Type: application/json")
@POST("/api/login") 
Call<ResObj> userLogin(@Body JsonObject jsonObject); 

然后这样称呼你的 API

private void doLogin(final String mobile){
      try {
           JsonObject paramObject = new JsonObject();
           paramObject.addProperty("mobile", mobile);
        } catch (JSONException e) {
            e.printStackTrace();
        }

      Call<ResObj> call = userService.login(paramObject);
      call.enqueue(new Callback<ResObj>() {

        //your rest of code

      });
}

更新 2:

要使用 intentobject 从一个 Activity 发送到另一个,您必须制作模型 class Percelable。像这样

// implements Parcelable

public class ResObj implements Parcelable { 
    // ...........your previous code here

    // just simply add the following methods

    @Override
    public int describeContents() {
        return 0;
    }

    @Override
    public void writeToParcel(Parcel dest, int flags) {
        dest.writeString(date);
        dest.writeString(address);
        dest.writeString(accountName);
        dest.writeString(contactPerson);
        dest.writeString(timeOut);
        dest.writeString(problem);
        dest.writeString(srNo);
        dest.writeString(fieldEngineer);
        dest.writeString(joNo);
        dest.writeString(irNo);
        dest.writeString(designation);
        dest.writeString(email);
        dest.writeString(timeIn);
        dest.writeString(productType);
        dest.writeByte((byte) (status ? 1 : 0));
        dest.writeString(contactNo);
    }
    public static final Parcelable.Creator<ResObj> CREATOR
            = new Parcelable.Creator<ResObj>() {
        public ResObj createFromParcel(Parcel in) {
            return new ResObj(in);
        }

        public ResObj[] newArray(int size) {
            return new ResObj[size];
        }
    };

    protected ResObj(Parcel in) {
        date = in.readString();
        address = in.readString();
        accountName = in.readString();
        contactPerson = in.readString();
        timeOut = in.readString();
        problem = in.readString();
        srNo = in.readString();
        fieldEngineer = in.readString();
        joNo = in.readString();
        irNo = in.readString();
        designation = in.readString();
        email = in.readString();
        timeIn = in.readString();
        productType = in.readString();
        status = in.readByte() != 0;
        contactNo = in.readString();

    }
}

现在像下面这样通过 intent 传递你的对象。

if(resObj != null){

    if(resObj.getStatus()){

        Intent intent = new Intent(Login.this, ListActivity.class);
        intent.putExtra("your_key", resObj); // pass resObj and use same key to get data
        startActivity(intent);

    } else{
        Toast.makeText(Login.this, "Phone Number is incorrect!", Toast.LENGTH_SHORT).show();
    }
}

像这样从您的 ListActivity 获取数据

@Override
protected void onCreate(Bundle savedInstanceState) {
     super.onCreate(savedInstanceState);
     setContentView(R.layout.activity_second);

     final ResObj yourObject = getIntent().getParcelableExtra("your_key"); // make sure you use same key like data.

     // Now you can use your data like that
     yourEditText.setText(yourObject.getEmail()); 
}