Java GSON自定义将字段反序列化为包裹

Java GSON自定义将字段反序列化为包裹,java,android,gson,retrofit,parceler,Java,Android,Gson,Retrofit,Parceler,我正在使用和库与服务器通信 服务器具有以下两种API方法: 获取返回以下JSON的/api/metadata/{id} { "id": 1, "active": true, "location": { "type": "Point", "coordinates": [ 30.0000, 30.0000 ] } } { "id": 1,

我正在使用和库与服务器通信

服务器具有以下两种API方法:

获取返回以下JSON的
/api/metadata/{id}

{
     "id": 1,
     "active": true,
     "location": {
         "type": "Point",
         "coordinates": [
             30.0000,
             30.0000
         ]
     }
}
{
     "id": 1,
     "active": true,
     "location_latitude": 30.0000,
     "location_longitude": 30.0000
}
POST/api/metadata/{id},它需要以下JSON

{
     "id": 1,
     "active": true,
     "location": {
         "type": "Point",
         "coordinates": [
             30.0000,
             30.0000
         ]
     }
}
{
     "id": 1,
     "active": true,
     "location_latitude": 30.0000,
     "location_longitude": 30.0000
}
这是历史原因造成的,不能改变

在我的android应用程序中,我以以下方式声明改装:

public interface ServerApi {
    @GET("/api/metadata/{id}")
    Metadata getMetadata(@Path("id") int id);

    @POST("/api/metadata/{id}")
    Metadata updateMetadata(@Path("id") int id, @Body Metadata metadata);
}
地块类的定义方式如下:

public interface ServerApi {
    @GET("/api/metadata/{id}")
    Metadata getMetadata(@Path("id") int id);

    @POST("/api/metadata/{id}")
    Metadata updateMetadata(@Path("id") int id, @Body Metadata metadata);
}
元数据:

@Parcel
public class Metadata {
    @SerializedName("id")
    private Integer id;

    @SerializedName("location")
    private GeometryPoint location;

    @SerializedName("location_latitude")
    private float locationLatitude;

    @SerializedName("location_longitude")
    private float locationLongitude;

    public void setId(Integer id) {
        this.id = id;
    }

    public void setLocationLatitude(float locationLatitude) {
        this.locationLatitude = locationLatitude;
    }

    public void setLocationLongitude(float locationLongitude) {
        this.locationLongitude = locationLongitude;
    }

    public void setLocation(GeometryPoint location) {
        this.location = location;
    }

    public Integer getId() {
        return id;
    }

    public float getLocationLatitude() {
        return locationLatitude;
    }

    public float getLocationLongitude() {
        return locationLongitude;
    }

    public GeometryPoint getLocation() {
        return location;
    }
}
几何点:

@Parcel
public class GeometryPoint {
    @SerializedName("type")
    private String type;

    @SerializedName("coordinates")
    private float[] coordinates;

    public void setType(String type) {
        this.type = type;
    }

    public void setCoordinates(float[] coordinates) {
        this.coordinates = coordinates;
    }

    public String getType() {
        return type;
    }

    public float[] getCoordinates() {
        return coordinates;
    }
}
我希望在整个应用程序中使用元数据类。我想查询服务器,接收元数据,更新它,并将其发送到服务器。显然,GET和POST的元数据格式不同。因此,我希望在收到它后能转换成POST格式

我的问题是,是否有可能以某种方式声明注释,以便改型和包裹员能够知道
位置
参数,将其从JSON反序列化,但通过
setLocation()
方法将其写入
元数据
类,在这里我可以将其分解为“位置纬度”和“位置经度”

这是所需元数据类的一些伪代码:

@Parcel
public class Metadata {
    @SerializedName("id")
    private Integer id;

    // I'd like not having location variable defined at all 
    // but use some annotation magic :)) to tell GSON to deserialize
    // JSON and call setLocation() when it tries to process location
    // parameter of the server response
    /*
       @SerializedName("location")
       private GeometryPoint location;
    */

    @SerializedName("location_latitude")
    private float locationLatitude;

    @SerializedName("location_longitude")
    private float locationLongitude;

    public void setId(Integer id) {
        this.id = id;
    }

    public void setLocationLatitude(float locationLatitude) {
        this.locationLatitude = locationLatitude;
    }

    public void setLocationLongitude(float locationLongitude) {
        this.locationLongitude = locationLongitude;
    }

    public void setLocation(GeometryPoint location) {
        this.location_latitude = location.getCoordinates()[1];
        this.location_longitude = location.getCoordinates()[0];
    }

    public Integer getId() {
        return id;
    }

    public float getLocationLatitude() {
        return locationLatitude;
    }

    public float getLocationLongitude() {
        return locationLongitude;
    }

    // No need for getLocation method
}

或者我只是傻了一点(我昨天真的学到了改型、Parceler和GSON意识),应该创建两个元数据类
MetadataExternal
MetadataInternal
,用于接收和发送到服务器?

在我看来,错误的定义是服务器端,POST和GET for/api/metadata/{id}应该接受相同的“对象”。事实并非如此,你必须使用“技巧”