Parse Json array with multiple objects using retrofit 2 in android - java

I'm using retrofit 2 for networking functions in my project, and I'm able to parse the json object responses from the server but now I'm supposed to parse a json array that look like this
[
{
"id_asset": 1,
"id_category": 1,
"id_brand": 2,
"name": "Samsung Galaxy 6",
"status": 1,
"updated_at": "Oct 3, 2016 10:24:28 AM",
"rank": 1,
"rate": {
"id_asset_rate": 2,
"id_asset": 1,
"value": 5000,
"loan_to_value": 50,
"offered": 2500,
"annual_rate": 3,
"quantity": 5,
"created_at": "Oct 23, 2016 5:31:31 AM",
"updated_at": "Oct 23, 2016 5:32:31 AM"
},
"best_rate": {
"id_asset": "1",
"value": "5000",
"loan_to_value": "50",
"offered": "2500",
"annual_rate": "3",
"quantity": "5",
"rank": "1"
},
"category": {
"id_category": 1,
"id_parent": 0,
"name": "Mobile Phones",
"image": "",
"sort": 1,
"status": 1,
"created_at": null,
"updated_at": null,
"_links": {
"self": {
"href": "/v1/categories/1"
}
}
},
"brand": {
"id_brand": 2,
"name": "Samsung",
"status": 1,
"created_at": null,
"updated_at": null
},
"_links": {
"self": {
"href": "/v1/assets/1"
}
}
},
{
"id_asset": 2,
"id_category": 1,
"id_brand": 1,
"name": "i Phone 5",
"status": 1,
"updated_at": "Oct 3, 2016 8:04:36 AM",
"rank": false,
"rate": null,
"best_rate": false,
"category": {
"id_category": 1,
"id_parent": 0,
"name": "Mobile Phones",
"image": "",
"sort": 1,
"status": 1,
"created_at": null,
"updated_at": null,
"_links": {
"self": {
"href": "/v1/categories/1"
}
}
},
"brand": {
"id_brand": 1,
"name": "Apple",
"status": 1,
"created_at": null,
"updated_at": null
},
"_links": {
"self": {
"href": "/v1/assets/2"
}
}
}
]
This is the response from the server and I created this POJO for the response
public class AssetResponse {
private Integer id_asset;
private Integer id_category;
private Integer id_brand;
private String name;
private Integer status;
private String updated_at;
private AssetRate assetRate;
private AssetCategory assetCategory;
private Links links;
private Self self;
private AssetBrand assetBrand;
private HasLinked hasLinked;
public Integer getId_asset() {
return id_asset;
}
public void setId_asset(Integer id_asset) {
this.id_asset = id_asset;
}
public Integer getId_category() {
return id_category;
}
public void setId_category(Integer id_category) {
this.id_category = id_category;
}
public Integer getId_brand() {
return id_brand;
}
public void setId_brand(Integer id_brand) {
this.id_brand = id_brand;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Integer getStatus() {
return status;
}
public void setStatus(Integer status) {
this.status = status;
}
public String getUpdated_at() {
return updated_at;
}
public void setUpdated_at(String updated_at) {
this.updated_at = updated_at;
}
public AssetRate getAssetRate() {
return assetRate;
}
public void setAssetRate(AssetRate assetRate) {
this.assetRate = assetRate;
}
public AssetCategory getAssetCategory() {
return assetCategory;
}
public void setAssetCategory(AssetCategory assetCategory) {
this.assetCategory = assetCategory;
}
public Links getLinks() {
return links;
}
public void setLinks(Links links) {
this.links = links;
}
public Self getSelf() {
return self;
}
public void setSelf(Self self) {
this.self = self;
}
public AssetBrand getAssetBrand() {
return assetBrand;
}
public void setAssetBrand(AssetBrand assetBrand) {
this.assetBrand = assetBrand;
}
public HasLinked getHasLinked() {
return hasLinked;
}
public void setHasLinked(HasLinked hasLinked) {
this.hasLinked = hasLinked;
}
private class AssetRate {
private Integer id_asset_rate;
private Integer id_asset;
private Double value;
private Double loan_to_value;
private Double offered;
private Double annual_rate;
private String updated_at;
public Integer getId_asset_rate() {
return id_asset_rate;
}
public void setId_asset_rate(Integer id_asset_rate) {
this.id_asset_rate = id_asset_rate;
}
public Integer getId_asset() {
return id_asset;
}
public void setId_asset(Integer id_asset) {
this.id_asset = id_asset;
}
public Double getValue() {
return value;
}
public void setValue(Double value) {
this.value = value;
}
public Double getLoan_to_value() {
return loan_to_value;
}
public void setLoan_to_value(Double loan_to_value) {
this.loan_to_value = loan_to_value;
}
public Double getOffered() {
return offered;
}
public void setOffered(Double offered) {
this.offered = offered;
}
public Double getAnnual_rate() {
return annual_rate;
}
public void setAnnual_rate(Double annual_rate) {
this.annual_rate = annual_rate;
}
public String getUpdated_at() {
return updated_at;
}
public void setUpdated_at(String updated_at) {
this.updated_at = updated_at;
}
}
private class AssetCategory {
private Integer id_category;
private Integer id_parent;
private String name;
private String image;
private Integer sort;
private Integer status;
private String created_at;
private String updated_at;
private Links links;
public Integer getId_category() {
return id_category;
}
public void setId_category(Integer id_category) {
this.id_category = id_category;
}
public Integer getId_parent() {
return id_parent;
}
public void setId_parent(Integer id_parent) {
this.id_parent = id_parent;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getImage() {
return image;
}
public void setImage(String image) {
this.image = image;
}
public Integer getSort() {
return sort;
}
public void setSort(Integer sort) {
this.sort = sort;
}
public Integer getStatus() {
return status;
}
public void setStatus(Integer status) {
this.status = status;
}
public String getCreated_at() {
return created_at;
}
public void setCreated_at(String created_at) {
this.created_at = created_at;
}
public String getUpdated_at() {
return updated_at;
}
public void setUpdated_at(String updated_at) {
this.updated_at = updated_at;
}
public Links getLinks() {
return links;
}
public void setLinks(Links links) {
this.links = links;
}
}
private class Links {
#SerializedName("self")
#Expose
private Self self;
/**
*
* #return
* The self
*/
public Self getSelf() {
return self;
}
/**
*
* #param self
* The self
*/
public void setSelf(Self self) {
this.self = self;
}
}
private class Self {
#SerializedName("href")
#Expose
private String href;
/**
*
* #return
* The href
*/
public String getHref() {
return href;
}
/**
*
* #param href
* The href
*/
public void setHref(String href) {
this.href = href;
}
}
private class AssetBrand {
private Integer id_brand;
private String name;
private Integer status;
private String created_at;
private String updated_at;
public Integer getId_brand() {
return id_brand;
}
public void setId_brand(Integer id_brand) {
this.id_brand = id_brand;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Integer getStatus() {
return status;
}
public void setStatus(Integer status) {
this.status = status;
}
public String getCreated_at() {
return created_at;
}
public void setCreated_at(String created_at) {
this.created_at = created_at;
}
public String getUpdated_at() {
return updated_at;
}
public void setUpdated_at(String updated_at) {
this.updated_at = updated_at;
}
}
private class HasLinked {
private Integer has_linked;
private Links links;
public Integer getHas_linked() {
return has_linked;
}
public void setHas_linked(Integer has_linked) {
this.has_linked = has_linked;
}
public Links getLinks() {
return links;
}
public void setLinks(Links links) {
this.links = links;
}
}
}
}
Is my pojo is right ?
My problem is, I can't parse this response. Any help will be appreciated.
Thanks in advance
EDIT :
This is my request to server (using rest api)
#GET("url")
Call<AssetResponse> getAssetList();
EDIT 2: I've changed the code to List, as suggested by Niko Adrianus Yuwono.
This is the new changes
private void getAssets() {
HttpLoggingInterceptor logging = new HttpLoggingInterceptor();
logging.setLevel(HttpLoggingInterceptor.Level.BODY);
OkHttpClient.Builder httpClient = new OkHttpClient.Builder();
httpClient.addInterceptor(logging);
Retrofit retrofit = new Retrofit.Builder()
.baseUrl(Constants.BASE_URL)
.addConverterFactory(GsonConverterFactory.create())
.client(httpClient.build())
.build();
final ApiInterface apiInterface = retrofit.create(ApiInterface.class);
final AssetRequest assetRequest = new AssetRequest();
assetRequest.setAcc_tok(ACCESS_TOKEN);
final Call<List<AssetResponse>> assetList = apiInterface.getAssetList();
assetList.enqueue(new Callback <List<AssetResponse>>() {
#Override
public void onResponse(Call<List<AssetResponse>> call, Response<List<AssetResponse>> response) {
int statusCode = response.code();
List<AssetResponse> assetResponseList = response.body();
if (statusCode == 200) {
for (int i = 0; i < assetResponseList.size(); i++ ){
Integer id_asset = assetResponseList.get(i).getId_asset();
Integer id_category = assetResponseList.get(i).getId_category();
Integer status = assetResponseList.get(i).getStatus();
String name = assetResponseList.get(i).getName();
Log.d("Assets ","Asset id_asset bb : " + id_asset);
Log.d("Assets ","Asset id_category bb : " + id_category);
Log.d("Assets ","Asset name bb : " + name);
Log.d("Assets ","Asset status bb : " + status);
Double val = assetResponseList.get(i).getAssetRate().getValue();
Log.d("val ","val is : " +val);
}
} else {
Toast.makeText(getContext(), "network error " + statusCode, Toast.LENGTH_LONG).show();
}
}
#Override
public void onFailure(Call<List<AssetResponse>> call, Throwable t) {
Log.d("Asset GET Failure", "onFailure: " + t.getMessage());
//showProgress(false);
}
});
}
and this is the response from the server
D/Assets: Asset id_asset bb : 1 D/Assets: Asset id_category bb : 1 D/Assets: Asset name bb : Samsung Galaxy 6 D/Assets: Asset status
bb : 1 10-26 13:13:17.898 22784-22784/ D/AndroidRuntime: Shutting down
VM 10-26 13:13:17.898 22784-22784/ E/AndroidRuntime: FATAL EXCEPTION:
main Process: , PID: 22784 java.lang.NullPointerException: Attempt to
invoke virtual method 'java.lang.Double
.api.model.AssetResponse$AssetRate.getValue()' on a null object
reference
.AssetDatabaseFragment$2.onResponse(AssetDatabaseFragment.java:133)
retrofit2.ExecutorCallAdapterFactory$ExecutorCallbackCall$1$1.run(ExecutorCallAdapterFactory.java:68)
android.os.Handler.handleCallback(Handler.java:739)
android.os.Handler.dispatchMessage(Handler.java:95)
android.os.Looper.loop(Looper.java:148)
android.app.ActivityThread.main(ActivityThread.java:5417)
java.lang.reflect.Method.invoke(Native Method)
com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:726)
com.android.internal.os.ZygoteInit.main(ZygoteInit.java:616)
Whenever I access the inner objects it throws error like the above

Your POJO looks right, but your JSON response is a JSONArray so you need to declare it as a List of Objects rather than an Object
#GET("url")
Call<List<AssetResponse>> getAssetList();
And you need to change your inner class access to public so GSON can see the setter and getter of that class.

Your Json key value data is changing from one index to another.
Wrong Json:
[{
//Make this either integer or boolean
"rank": 1,
// best rate is object here in the next index, it's treated as boolean.
"best_rate": {
"id_asset": "1",
"value": "5000",
"loan_to_value": "50",
"offered": "2500",
"annual_rate": "3",
"quantity": "5",
"rank": "1"
}
},
{
"rank":false,
"best_rate":false,
}
]
I have a complete project shared on github with your json.
https://github.com/lingarajsankaravelu/retrofit2v.git
Retrofit code should be like this as i mentioned in the question comment.
#GET("url")
Call<List<AssetResponse>> getAssetList();
As you have requested to explain the changes in your pojo class it should be like this.
AssetReponse.class:
public class AssetResponse {
private Integer id_asset;
private Integer id_category;
private Integer id_brand;
private String name;
private Integer status;
private String updated_at;
private AssetRate assetRate;
private AssetCategory assetCategory;
private Links links;
private Self self;
private AssetBrand assetBrand;
private HasLinked hasLinked;
public Integer getId_asset() {
return id_asset;
}
public void setId_asset(Integer id_asset) {
this.id_asset = id_asset;
}
public Integer getId_category() {
return id_category;
}
public void setId_category(Integer id_category) {
this.id_category = id_category;
}
public Integer getId_brand() {
return id_brand;
}
public void setId_brand(Integer id_brand) {
this.id_brand = id_brand;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Integer getStatus() {
return status;
}
public void setStatus(Integer status) {
this.status = status;
}
public String getUpdated_at() {
return updated_at;
}
public void setUpdated_at(String updated_at) {
this.updated_at = updated_at;
}
public AssetRate getAssetRate() {
return assetRate;
}
public void setAssetRate(AssetRate assetRate) {
this.assetRate = assetRate;
}
public AssetCategory getAssetCategory() {
return assetCategory;
}
public void setAssetCategory(AssetCategory assetCategory) {
this.assetCategory = assetCategory;
}
public Links getLinks() {
return links;
}
public void setLinks(Links links) {
this.links = links;
}
public Self getSelf() {
return self;
}
public void setSelf(Self self) {
this.self = self;
}
public AssetBrand getAssetBrand() {
return assetBrand;
}
public void setAssetBrand(AssetBrand assetBrand) {
this.assetBrand = assetBrand;
}
public HasLinked getHasLinked() {
return hasLinked;
}
public void setHasLinked(HasLinked hasLinked) {
this.hasLinked = hasLinked;
}
}
AssetRate.class
public class AssetRate {
private Integer id_asset_rate;
private Integer id_asset;
private Double value;
private Double loan_to_value;
private Double offered;
private Double annual_rate;
private String updated_at;
public Integer getId_asset_rate() {
return id_asset_rate;
}
public void setId_asset_rate(Integer id_asset_rate) {
this.id_asset_rate = id_asset_rate;
}
public Integer getId_asset() {
return id_asset;
}
public void setId_asset(Integer id_asset) {
this.id_asset = id_asset;
}
public Double getValue() {
return value;
}
public void setValue(Double value) {
this.value = value;
}
public Double getLoan_to_value() {
return loan_to_value;
}
public void setLoan_to_value(Double loan_to_value) {
this.loan_to_value = loan_to_value;
}
public Double getOffered() {
return offered;
}
public void setOffered(Double offered) {
this.offered = offered;
}
public Double getAnnual_rate() {
return annual_rate;
}
public void setAnnual_rate(Double annual_rate) {
this.annual_rate = annual_rate;
}
public String getUpdated_at() {
return updated_at;
}
public void setUpdated_at(String updated_at) {
this.updated_at = updated_at;
}
}
Seperate your inner class like above. Seperating your inner class model will be useful if you are working on a large project. where you don't have to write the same pojo class again. you can use this seperate class structure instead.

You can use this site to generate POJO class. Just enter your JSON response and choose which JSON type you using like GSON,Jackson.etc. and You get perfect POJO classes. no need to change anything.
http://www.jsonschema2pojo.org/

Your Retrofit interface should be
#GET("url")
Call<List<AssetReponse>> getAssessList();
And make sure that your variable name same with key on JSON Response Or you can use annotation #SerializedName for that & for make it simple you can use JSON to POJO Online converter : http://www.jsonschema2pojo.org/

Related

Unable to deserialize HATEOS JSON using RestTemplate

I am trying to call a Spring Cloud Data Flow REST Endpoint which is supposed to return a list of all the executions of a task whose name is passed in the input.
For starters, I ran the following URL in the browser :
http://dataflow-server.myhost.net/tasks/executions?task1225
The following JSON is shown on the browser :
{
"_embedded": {
"taskExecutionResourceList": [
{
"executionId": 2908,
"exitCode": 0,
"taskName": "task1225",
"startTime": "2021-06-25T18:40:24.823+0000",
"endTime": "2021-06-25T18:40:27.585+0000",
"exitMessage": null,
"arguments": [
"--spring.datasource.username=******",
"--spring.cloud.task.name=task1225",
"--spring.datasource.url=******",
"--spring.datasource.driverClassName=org.h2.Driver",
"key=******",
"batchId=20210625_025755702",
"--spring.cloud.data.flow.platformname=default",
"--spring.cloud.task.executionid=2908"
],
"jobExecutionIds": [],
"errorMessage": null,
"externalExecutionId": "task1225-kp7mvwkmll",
"parentExecutionId": null,
"resourceUrl": "Docker Resource [docker:internal.artifactrepository.myhost.net/myProject/myimage:0.1]",
"appProperties": {
"spring.datasource.username": "******",
"spring.cloud.task.name": "task1225",
"spring.datasource.url": "******",
"spring.datasource.driverClassName": "org.h2.Driver"
},
"deploymentProperties": {
"spring.cloud.deployer.kubernetes.requests.memory": "512Mi",
"spring.cloud.deployer.kubernetes.limits.cpu": "1000m",
"spring.cloud.deployer.kubernetes.limits.memory": "8192Mi",
"spring.cloud.deployer.kubernetes.requests.cpu": "100m"
},
"taskExecutionStatus": "COMPLETE",
"_links": {
"self": {
"href": "http://dataflow-server.myhost.net/tasks/executions/2908"
}
}
}
]
},
"_links": {
"first": {
"href": "http://dataflow-server.myhost.net/tasks/executions?page=0&size=20"
},
"self": {
"href": "http://dataflow-server.myhost.net/tasks/executions?page=0&size=20"
},
"next": {
"href": "http://dataflow-server.myhost.net/tasks/executions?page=1&size=20"
},
"last": {
"href": "http://dataflow-server.myhost.net/tasks/executions?page=145&size=20"
}
},
"page": {
"size": 20,
"totalElements": 2908,
"totalPages": 146,
"number": 0
}
}
Next, I tried to call the same REST endpoint through Java; however, no matter what I try, the response object seems to be empty with none of the attributes populated :
Approach 1 : Custom domain classes created to deserialize the response. (Did not work. Empty content recieved in response)
ParameterizedTypeReference<Resources<TaskExecutions>> ptr = new ParameterizedTypeReference<Resources<TaskExecutions>>() {
};
ResponseEntity<Resources<TaskExecutions>> entity = restTemplate.exchange(
"http://dataflow-server.myhost.net/tasks/executions?task1225",
HttpMethod.GET, null, ptr);
System.out.println(entity.getBody().getContent()); **//empty content**
Where, TaskExecutions domain is as follows :
#JsonInclude(JsonInclude.Include.NON_NULL)
#JsonPropertyOrder({ "taskExecutionResourceList" })
#JsonIgnoreProperties(ignoreUnknown = true)
public class TaskExecutions {
public TaskExecutions() {
}
#JsonProperty("taskExecutionResourceList")
List<TaskExecutionResource> taskExecutionResourceList = new ArrayList<>();
#JsonProperty("taskExecutionResourceList")
public List<TaskExecutionResource> getTaskExecutionResourceList() {
return taskExecutionResourceList;
}
#JsonProperty("taskExecutionResourceList")
public void setTaskExecutionResourceList(List<TaskExecutionResource> taskExecutionResourceList) {
this.taskExecutionResourceList = taskExecutionResourceList;
}
}
And TaskExecutionResource is as follows :
#JsonInclude(JsonInclude.Include.NON_NULL)
#JsonPropertyOrder({
"executionId",
"exitCode",
"taskName",
"startTime",
"endTime",
"exitMessage",
"arguments",
"jobExecutionIds",
"errorMessage",
"externalExecutionId",
"parentExecutionId",
"resourceUrl",
"appProperties",
"deploymentProperties",
"taskExecutionStatus",
"_links" })
#JsonIgnoreProperties(ignoreUnknown = true)
public class TaskExecutionResource {
#JsonProperty("executionId")
private Integer executionId;
#JsonProperty("exitCode")
private Integer exitCode;
#JsonProperty("taskName")
private String taskName;
#JsonProperty("startTime")
private String startTime;
#JsonProperty("endTime")
private String endTime;
#JsonProperty("exitMessage")
private Object exitMessage;
#JsonProperty("arguments")
private List<String> arguments = new ArrayList<String>();
#JsonProperty("jobExecutionIds")
private List<Object> jobExecutionIds = new ArrayList<Object>();
#JsonProperty("errorMessage")
private Object errorMessage;
#JsonProperty("externalExecutionId")
private String externalExecutionId;
#JsonProperty("parentExecutionId")
private Object parentExecutionId;
#JsonProperty("resourceUrl")
private String resourceUrl;
#JsonProperty("appProperties")
private AppProperties appProperties;
#JsonProperty("deploymentProperties")
private DeploymentProperties deploymentProperties;
#JsonProperty("taskExecutionStatus")
private String taskExecutionStatus;
#JsonProperty("_links")
private Links links;
#JsonProperty("executionId")
public Integer getExecutionId() {
return executionId;
}
#JsonProperty("executionId")
public void setExecutionId(Integer executionId) {
this.executionId = executionId;
}
#JsonProperty("exitCode")
public Integer getExitCode() {
return exitCode;
}
#JsonProperty("exitCode")
public void setExitCode(Integer exitCode) {
this.exitCode = exitCode;
}
#JsonProperty("taskName")
public String getTaskName() {
return taskName;
}
#JsonProperty("taskName")
public void setTaskName(String taskName) {
this.taskName = taskName;
}
#JsonProperty("startTime")
public String getStartTime() {
return startTime;
}
#JsonProperty("startTime")
public void setStartTime(String startTime) {
this.startTime = startTime;
}
#JsonProperty("endTime")
public String getEndTime() {
return endTime;
}
#JsonProperty("endTime")
public void setEndTime(String endTime) {
this.endTime = endTime;
}
#JsonProperty("exitMessage")
public Object getExitMessage() {
return exitMessage;
}
#JsonProperty("exitMessage")
public void setExitMessage(Object exitMessage) {
this.exitMessage = exitMessage;
}
#JsonProperty("arguments")
public List<String> getArguments() {
return arguments;
}
#JsonProperty("arguments")
public void setArguments(List<String> arguments) {
this.arguments = arguments;
}
#JsonProperty("jobExecutionIds")
public List<Object> getJobExecutionIds() {
return jobExecutionIds;
}
#JsonProperty("jobExecutionIds")
public void setJobExecutionIds(List<Object> jobExecutionIds) {
this.jobExecutionIds = jobExecutionIds;
}
#JsonProperty("errorMessage")
public Object getErrorMessage() {
return errorMessage;
}
#JsonProperty("errorMessage")
public void setErrorMessage(Object errorMessage) {
this.errorMessage = errorMessage;
}
#JsonProperty("externalExecutionId")
public String getExternalExecutionId() {
return externalExecutionId;
}
#JsonProperty("externalExecutionId")
public void setExternalExecutionId(String externalExecutionId) {
this.externalExecutionId = externalExecutionId;
}
#JsonProperty("parentExecutionId")
public Object getParentExecutionId() {
return parentExecutionId;
}
#JsonProperty("parentExecutionId")
public void setParentExecutionId(Object parentExecutionId) {
this.parentExecutionId = parentExecutionId;
}
#JsonProperty("resourceUrl")
public String getResourceUrl() {
return resourceUrl;
}
#JsonProperty("resourceUrl")
public void setResourceUrl(String resourceUrl) {
this.resourceUrl = resourceUrl;
}
#JsonProperty("appProperties")
public AppProperties getAppProperties() {
return appProperties;
}
#JsonProperty("appProperties")
public void setAppProperties(AppProperties appProperties) {
this.appProperties = appProperties;
}
#JsonProperty("deploymentProperties")
public DeploymentProperties getDeploymentProperties() {
return deploymentProperties;
}
#JsonProperty("deploymentProperties")
public void setDeploymentProperties(DeploymentProperties deploymentProperties) {
this.deploymentProperties = deploymentProperties;
}
#JsonProperty("taskExecutionStatus")
public String getTaskExecutionStatus() {
return taskExecutionStatus;
}
#JsonProperty("taskExecutionStatus")
public void setTaskExecutionStatus(String taskExecutionStatus) {
this.taskExecutionStatus = taskExecutionStatus;
}
#JsonProperty("_links")
public Links getLinks() {
return links;
}
#JsonProperty("_links")
public void setLinks(Links links) {
this.links = links;
}
}
Approach 2 : Add spring-cloud-data-flow-rest as a maven dependency in my project and use the TaskExectuionResource entity defined in this project. :
TaskExecutionResource.Page = restTemplate.getForObject("http://dataflow-server.myhost.net/tasks/executions?task1225",
TaskExecutionResource.Page.class);//**Empty content**
Question : How can I deserialize the response of the JSON returned by a rest enndpoint that is using HATEOAS? It seems like a very daunting task to get this to work.
Not sure how you constructed RestTemplate but it doesn't work as is with hateoas and there's some additional steps you need to do.
To get idea what we've done see ObjectMapper config. There's hal module and additional mixin's what mapper needs to be aware of for these things to work.

I am gettion json response in Object but i want to be in Json Array

I am getting list of coins from API https://min-api.cryptocompare.com/data/all/coinlist?api-key.
It returns json response like this -
{
"Response": "Success",
"Message": "Coin list succesfully returned!",
"Data": {
"42": {
"Id": "4321",
"Url": "/coins/42/overview",
"ImageUrl": "/media/35650717/42.jpg",
"ContentCreatedOn": 1427211129,
"Name": "42",
"Symbol": "42",
"CoinName": "42 Coin",
"FullName": "42 Coin (42)",
"Algorithm": "Scrypt",
"ProofType": "PoW/PoS",
"FullyPremined": "0",
"TotalCoinSupply": "42",
"BuiltOn": "N/A",
"SmartContractAddress": "N/A",
"DecimalPlaces": 0,
"PreMinedValue": "N/A",
"TotalCoinsFreeFloat": "N/A",
"SortOrder": "34",
"Sponsored": false,
"Taxonomy": {
"Access": "",
"FCA": "",
"FINMA": "",
"Industry": "",
"CollateralizedAsset": "",
"CollateralizedAssetType": "",
"CollateralType": "",
"CollateralInfo": ""
},
"Rating": {
"Weiss": {
"Rating": "",
"TechnologyAdoptionRating": "",
"MarketPerformanceRating": ""
}
},
"IsTrading": true,
"TotalCoinsMined": 41.9999528,
"BlockNumber": 173122,
"NetHashesPerSecond": 0,
"BlockReward": 0,
"BlockTime": 0
},
"300": {
"Id": "749869",
"Url": "/coins/300/overview",
"ImageUrl": "/media/27010595/300.png",
"ContentCreatedOn": 1517935016,
"Name": "300",
"Symbol": "300",
"CoinName": "300 token",
"FullName": "300 token (300)",
"Algorithm": "N/A",
"ProofType": "N/A",
"FullyPremined": "0",
"TotalCoinSupply": "300",
"BuiltOn": "7605",
"SmartContractAddress": "0xaec98a708810414878c3bcdf46aad31ded4a4557",
"DecimalPlaces": 18,
"PreMinedValue": "N/A",
"TotalCoinsFreeFloat": "N/A",
"SortOrder": "2212",
"Sponsored": false,
"Taxonomy": {
"Access": "",
"FCA": "",
"FINMA": "",
"Industry": "",
"CollateralizedAsset": "",
"CollateralizedAssetType": "",
"CollateralType": "",
"CollateralInfo": ""
},
"Rating": {
"Weiss": {
"Rating": "",
"TechnologyAdoptionRating": "",
"MarketPerformanceRating": ""
}
},
"IsTrading": true,
"TotalCoinsMined": 300,
"BlockNumber": 0,
"NetHashesPerSecond": 0,
"BlockReward": 0,
"BlockTime": 0
}
}
}
When I am generating pojo class for it, it is creating class _42 as well as class _300 means for every object it is creating new class.
Here it is :-
package com.mountblue.cryptocoin.entity;
import com.google.gson.annotations.SerializedName;
public class CoinBean {
/**
* Response : Success
* Message : Coin list succesfully returned!
* Data : {"42":{"Id":"4321","Url":"/coins/42/overview","ImageUrl":"/media/35650717/42.jpg","ContentCreatedOn":1427211129,"Name":"42","Symbol":"42","CoinName":"42 Coin","FullName":"42 Coin (42)","Algorithm":"Scrypt","ProofType":"PoW/PoS","FullyPremined":"0","TotalCoinSupply":"42","BuiltOn":"N/A","SmartContractAddress":"N/A","DecimalPlaces":0,"PreMinedValue":"N/A","TotalCoinsFreeFloat":"N/A","SortOrder":"34","Sponsored":false,"Taxonomy":{"Access":"","FCA":"","FINMA":"","Industry":"","CollateralizedAsset":"","CollateralizedAssetType":"","CollateralType":"","CollateralInfo":""},"Rating":{"Weiss":{"Rating":"","TechnologyAdoptionRating":"","MarketPerformanceRating":""}},"IsTrading":true,"TotalCoinsMined":41.9999528,"BlockNumber":173122,"NetHashesPerSecond":0,"BlockReward":0,"BlockTime":0},"300":{"Id":"749869","Url":"/coins/300/overview","ImageUrl":"/media/27010595/300.png","ContentCreatedOn":1517935016,"Name":"300","Symbol":"300","CoinName":"300 token","FullName":"300 token (300)","Algorithm":"N/A","ProofType":"N/A","FullyPremined":"0","TotalCoinSupply":"300","BuiltOn":"7605","SmartContractAddress":"0xaec98a708810414878c3bcdf46aad31ded4a4557","DecimalPlaces":18,"PreMinedValue":"N/A","TotalCoinsFreeFloat":"N/A","SortOrder":"2212","Sponsored":false,"Taxonomy":{"Access":"","FCA":"","FINMA":"","Industry":"","CollateralizedAsset":"","CollateralizedAssetType":"","CollateralType":"","CollateralInfo":""},"Rating":{"Weiss":{"Rating":"","TechnologyAdoptionRating":"","MarketPerformanceRating":""}},"IsTrading":true,"TotalCoinsMined":300,"BlockNumber":0,"NetHashesPerSecond":0,"BlockReward":0,"BlockTime":0}}
*/
private String Response;
private String Message;
private DataBean Data;
public String getResponse() {
return Response;
}
public void setResponse(String Response) {
this.Response = Response;
}
public String getMessage() {
return Message;
}
public void setMessage(String Message) {
this.Message = Message;
}
public DataBean getData() {
return Data;
}
public void setData(DataBean Data) {
this.Data = Data;
}
public static class DataBean {
/**
* 42 : {"Id":"4321","Url":"/coins/42/overview","ImageUrl":"/media/35650717/42.jpg","ContentCreatedOn":1427211129,"Name":"42","Symbol":"42","CoinName":"42 Coin","FullName":"42 Coin (42)","Algorithm":"Scrypt","ProofType":"PoW/PoS","FullyPremined":"0","TotalCoinSupply":"42","BuiltOn":"N/A","SmartContractAddress":"N/A","DecimalPlaces":0,"PreMinedValue":"N/A","TotalCoinsFreeFloat":"N/A","SortOrder":"34","Sponsored":false,"Taxonomy":{"Access":"","FCA":"","FINMA":"","Industry":"","CollateralizedAsset":"","CollateralizedAssetType":"","CollateralType":"","CollateralInfo":""},"Rating":{"Weiss":{"Rating":"","TechnologyAdoptionRating":"","MarketPerformanceRating":""}},"IsTrading":true,"TotalCoinsMined":41.9999528,"BlockNumber":173122,"NetHashesPerSecond":0,"BlockReward":0,"BlockTime":0}
* 300 : {"Id":"749869","Url":"/coins/300/overview","ImageUrl":"/media/27010595/300.png","ContentCreatedOn":1517935016,"Name":"300","Symbol":"300","CoinName":"300 token","FullName":"300 token (300)","Algorithm":"N/A","ProofType":"N/A","FullyPremined":"0","TotalCoinSupply":"300","BuiltOn":"7605","SmartContractAddress":"0xaec98a708810414878c3bcdf46aad31ded4a4557","DecimalPlaces":18,"PreMinedValue":"N/A","TotalCoinsFreeFloat":"N/A","SortOrder":"2212","Sponsored":false,"Taxonomy":{"Access":"","FCA":"","FINMA":"","Industry":"","CollateralizedAsset":"","CollateralizedAssetType":"","CollateralType":"","CollateralInfo":""},"Rating":{"Weiss":{"Rating":"","TechnologyAdoptionRating":"","MarketPerformanceRating":""}},"IsTrading":true,"TotalCoinsMined":300,"BlockNumber":0,"NetHashesPerSecond":0,"BlockReward":0,"BlockTime":0}
*/
#SerializedName("42")
private _$42Bean _$42;
#SerializedName("300")
private _$300Bean _$300;
public _$42Bean get_$42() {
return _$42;
}
public void set_$42(_$42Bean _$42) {
this._$42 = _$42;
}
public _$300Bean get_$300() {
return _$300;
}
public void set_$300(_$300Bean _$300) {
this._$300 = _$300;
}
public static class _$42Bean {
/**
* Id : 4321
* Url : /coins/42/overview
* ImageUrl : /media/35650717/42.jpg
* ContentCreatedOn : 1427211129
* Name : 42
* Symbol : 42
* CoinName : 42 Coin
* FullName : 42 Coin (42)
* Algorithm : Scrypt
* ProofType : PoW/PoS
* FullyPremined : 0
* TotalCoinSupply : 42
* BuiltOn : N/A
* SmartContractAddress : N/A
* DecimalPlaces : 0
* PreMinedValue : N/A
* TotalCoinsFreeFloat : N/A
* SortOrder : 34
* Sponsored : false
* Taxonomy : {"Access":"","FCA":"","FINMA":"","Industry":"","CollateralizedAsset":"","CollateralizedAssetType":"","CollateralType":"","CollateralInfo":""}
* Rating : {"Weiss":{"Rating":"","TechnologyAdoptionRating":"","MarketPerformanceRating":""}}
* IsTrading : true
* TotalCoinsMined : 41.9999528
* BlockNumber : 173122
* NetHashesPerSecond : 0
* BlockReward : 0
* BlockTime : 0
*/
private String Id;
private String Url;
private String ImageUrl;
private int ContentCreatedOn;
private String Name;
private String Symbol;
private String CoinName;
private String FullName;
private String Algorithm;
private String ProofType;
private String FullyPremined;
private String TotalCoinSupply;
private String BuiltOn;
private String SmartContractAddress;
private int DecimalPlaces;
private String PreMinedValue;
private String TotalCoinsFreeFloat;
private String SortOrder;
private boolean Sponsored;
private TaxonomyBean Taxonomy;
private RatingBean Rating;
private boolean IsTrading;
private double TotalCoinsMined;
private int BlockNumber;
private int NetHashesPerSecond;
private int BlockReward;
private int BlockTime;
public String getId() {
return Id;
}
public void setId(String Id) {
this.Id = Id;
}
public String getUrl() {
return Url;
}
public void setUrl(String Url) {
this.Url = Url;
}
public String getImageUrl() {
return ImageUrl;
}
public void setImageUrl(String ImageUrl) {
this.ImageUrl = ImageUrl;
}
public int getContentCreatedOn() {
return ContentCreatedOn;
}
public void setContentCreatedOn(int ContentCreatedOn) {
this.ContentCreatedOn = ContentCreatedOn;
}
public String getName() {
return Name;
}
public void setName(String Name) {
this.Name = Name;
}
public String getSymbol() {
return Symbol;
}
public void setSymbol(String Symbol) {
this.Symbol = Symbol;
}
public String getCoinName() {
return CoinName;
}
public void setCoinName(String CoinName) {
this.CoinName = CoinName;
}
public String getFullName() {
return FullName;
}
public void setFullName(String FullName) {
this.FullName = FullName;
}
public String getAlgorithm() {
return Algorithm;
}
public void setAlgorithm(String Algorithm) {
this.Algorithm = Algorithm;
}
public String getProofType() {
return ProofType;
}
public void setProofType(String ProofType) {
this.ProofType = ProofType;
}
public String getFullyPremined() {
return FullyPremined;
}
public void setFullyPremined(String FullyPremined) {
this.FullyPremined = FullyPremined;
}
public String getTotalCoinSupply() {
return TotalCoinSupply;
}
public void setTotalCoinSupply(String TotalCoinSupply) {
this.TotalCoinSupply = TotalCoinSupply;
}
public String getBuiltOn() {
return BuiltOn;
}
public void setBuiltOn(String BuiltOn) {
this.BuiltOn = BuiltOn;
}
public String getSmartContractAddress() {
return SmartContractAddress;
}
public void setSmartContractAddress(String SmartContractAddress) {
this.SmartContractAddress = SmartContractAddress;
}
public int getDecimalPlaces() {
return DecimalPlaces;
}
public void setDecimalPlaces(int DecimalPlaces) {
this.DecimalPlaces = DecimalPlaces;
}
public String getPreMinedValue() {
return PreMinedValue;
}
public void setPreMinedValue(String PreMinedValue) {
this.PreMinedValue = PreMinedValue;
}
public String getTotalCoinsFreeFloat() {
return TotalCoinsFreeFloat;
}
public void setTotalCoinsFreeFloat(String TotalCoinsFreeFloat) {
this.TotalCoinsFreeFloat = TotalCoinsFreeFloat;
}
public String getSortOrder() {
return SortOrder;
}
public void setSortOrder(String SortOrder) {
this.SortOrder = SortOrder;
}
public boolean isSponsored() {
return Sponsored;
}
public void setSponsored(boolean Sponsored) {
this.Sponsored = Sponsored;
}
public TaxonomyBean getTaxonomy() {
return Taxonomy;
}
public void setTaxonomy(TaxonomyBean Taxonomy) {
this.Taxonomy = Taxonomy;
}
public RatingBean getRating() {
return Rating;
}
public void setRating(RatingBean Rating) {
this.Rating = Rating;
}
public boolean isIsTrading() {
return IsTrading;
}
public void setIsTrading(boolean IsTrading) {
this.IsTrading = IsTrading;
}
public double getTotalCoinsMined() {
return TotalCoinsMined;
}
public void setTotalCoinsMined(double TotalCoinsMined) {
this.TotalCoinsMined = TotalCoinsMined;
}
public int getBlockNumber() {
return BlockNumber;
}
public void setBlockNumber(int BlockNumber) {
this.BlockNumber = BlockNumber;
}
public int getNetHashesPerSecond() {
return NetHashesPerSecond;
}
public void setNetHashesPerSecond(int NetHashesPerSecond) {
this.NetHashesPerSecond = NetHashesPerSecond;
}
public int getBlockReward() {
return BlockReward;
}
public void setBlockReward(int BlockReward) {
this.BlockReward = BlockReward;
}
public int getBlockTime() {
return BlockTime;
}
public void setBlockTime(int BlockTime) {
this.BlockTime = BlockTime;
}
public static class TaxonomyBean {
/**
* Access :
* FCA :
* FINMA :
* Industry :
* CollateralizedAsset :
* CollateralizedAssetType :
* CollateralType :
* CollateralInfo :
*/
private String Access;
private String FCA;
private String FINMA;
private String Industry;
private String CollateralizedAsset;
private String CollateralizedAssetType;
private String CollateralType;
private String CollateralInfo;
public String getAccess() {
return Access;
}
public void setAccess(String Access) {
this.Access = Access;
}
public String getFCA() {
return FCA;
}
public void setFCA(String FCA) {
this.FCA = FCA;
}
public String getFINMA() {
return FINMA;
}
public void setFINMA(String FINMA) {
this.FINMA = FINMA;
}
public String getIndustry() {
return Industry;
}
public void setIndustry(String Industry) {
this.Industry = Industry;
}
public String getCollateralizedAsset() {
return CollateralizedAsset;
}
public void setCollateralizedAsset(String CollateralizedAsset) {
this.CollateralizedAsset = CollateralizedAsset;
}
public String getCollateralizedAssetType() {
return CollateralizedAssetType;
}
public void setCollateralizedAssetType(String CollateralizedAssetType) {
this.CollateralizedAssetType = CollateralizedAssetType;
}
public String getCollateralType() {
return CollateralType;
}
public void setCollateralType(String CollateralType) {
this.CollateralType = CollateralType;
}
public String getCollateralInfo() {
return CollateralInfo;
}
public void setCollateralInfo(String CollateralInfo) {
this.CollateralInfo = CollateralInfo;
}
}
public static class RatingBean {
/**
* Weiss : {"Rating":"","TechnologyAdoptionRating":"","MarketPerformanceRating":""}
*/
private WeissBean Weiss;
public WeissBean getWeiss() {
return Weiss;
}
public void setWeiss(WeissBean Weiss) {
this.Weiss = Weiss;
}
public static class WeissBean {
/**
* Rating :
* TechnologyAdoptionRating :
* MarketPerformanceRating :
*/
private String Rating;
private String TechnologyAdoptionRating;
private String MarketPerformanceRating;
public String getRating() {
return Rating;
}
public void setRating(String Rating) {
this.Rating = Rating;
}
public String getTechnologyAdoptionRating() {
return TechnologyAdoptionRating;
}
public void setTechnologyAdoptionRating(String TechnologyAdoptionRating) {
this.TechnologyAdoptionRating = TechnologyAdoptionRating;
}
public String getMarketPerformanceRating() {
return MarketPerformanceRating;
}
public void setMarketPerformanceRating(String MarketPerformanceRating) {
this.MarketPerformanceRating = MarketPerformanceRating;
}
}
}
}
public static class _$300Bean {
/**
* Id : 749869
* Url : /coins/300/overview
* ImageUrl : /media/27010595/300.png
* ContentCreatedOn : 1517935016
* Name : 300
* Symbol : 300
* CoinName : 300 token
* FullName : 300 token (300)
* Algorithm : N/A
* ProofType : N/A
* FullyPremined : 0
* TotalCoinSupply : 300
* BuiltOn : 7605
* SmartContractAddress : 0xaec98a708810414878c3bcdf46aad31ded4a4557
* DecimalPlaces : 18
* PreMinedValue : N/A
* TotalCoinsFreeFloat : N/A
* SortOrder : 2212
* Sponsored : false
* Taxonomy : {"Access":"","FCA":"","FINMA":"","Industry":"","CollateralizedAsset":"","CollateralizedAssetType":"","CollateralType":"","CollateralInfo":""}
* Rating : {"Weiss":{"Rating":"","TechnologyAdoptionRating":"","MarketPerformanceRating":""}}
* IsTrading : true
* TotalCoinsMined : 300
* BlockNumber : 0
* NetHashesPerSecond : 0
* BlockReward : 0
* BlockTime : 0
*/
private String Id;
private String Url;
private String ImageUrl;
private int ContentCreatedOn;
private String Name;
private String Symbol;
private String CoinName;
private String FullName;
private String Algorithm;
private String ProofType;
private String FullyPremined;
private String TotalCoinSupply;
private String BuiltOn;
private String SmartContractAddress;
private int DecimalPlaces;
private String PreMinedValue;
private String TotalCoinsFreeFloat;
private String SortOrder;
private boolean Sponsored;
private TaxonomyBeanX Taxonomy;
private RatingBeanX Rating;
private boolean IsTrading;
private int TotalCoinsMined;
private int BlockNumber;
private int NetHashesPerSecond;
private int BlockReward;
private int BlockTime;
public String getId() {
return Id;
}
public void setId(String Id) {
this.Id = Id;
}
public String getUrl() {
return Url;
}
public void setUrl(String Url) {
this.Url = Url;
}
public String getImageUrl() {
return ImageUrl;
}
public void setImageUrl(String ImageUrl) {
this.ImageUrl = ImageUrl;
}
public int getContentCreatedOn() {
return ContentCreatedOn;
}
public void setContentCreatedOn(int ContentCreatedOn) {
this.ContentCreatedOn = ContentCreatedOn;
}
public String getName() {
return Name;
}
public void setName(String Name) {
this.Name = Name;
}
public String getSymbol() {
return Symbol;
}
public void setSymbol(String Symbol) {
this.Symbol = Symbol;
}
public String getCoinName() {
return CoinName;
}
public void setCoinName(String CoinName) {
this.CoinName = CoinName;
}
public String getFullName() {
return FullName;
}
public void setFullName(String FullName) {
this.FullName = FullName;
}
public String getAlgorithm() {
return Algorithm;
}
public void setAlgorithm(String Algorithm) {
this.Algorithm = Algorithm;
}
public String getProofType() {
return ProofType;
}
public void setProofType(String ProofType) {
this.ProofType = ProofType;
}
public String getFullyPremined() {
return FullyPremined;
}
public void setFullyPremined(String FullyPremined) {
this.FullyPremined = FullyPremined;
}
public String getTotalCoinSupply() {
return TotalCoinSupply;
}
public void setTotalCoinSupply(String TotalCoinSupply) {
this.TotalCoinSupply = TotalCoinSupply;
}
public String getBuiltOn() {
return BuiltOn;
}
public void setBuiltOn(String BuiltOn) {
this.BuiltOn = BuiltOn;
}
public String getSmartContractAddress() {
return SmartContractAddress;
}
public void setSmartContractAddress(String SmartContractAddress) {
this.SmartContractAddress = SmartContractAddress;
}
public int getDecimalPlaces() {
return DecimalPlaces;
}
public void setDecimalPlaces(int DecimalPlaces) {
this.DecimalPlaces = DecimalPlaces;
}
public String getPreMinedValue() {
return PreMinedValue;
}
public void setPreMinedValue(String PreMinedValue) {
this.PreMinedValue = PreMinedValue;
}
public String getTotalCoinsFreeFloat() {
return TotalCoinsFreeFloat;
}
public void setTotalCoinsFreeFloat(String TotalCoinsFreeFloat) {
this.TotalCoinsFreeFloat = TotalCoinsFreeFloat;
}
public String getSortOrder() {
return SortOrder;
}
public void setSortOrder(String SortOrder) {
this.SortOrder = SortOrder;
}
public boolean isSponsored() {
return Sponsored;
}
public void setSponsored(boolean Sponsored) {
this.Sponsored = Sponsored;
}
public TaxonomyBeanX getTaxonomy() {
return Taxonomy;
}
public void setTaxonomy(TaxonomyBeanX Taxonomy) {
this.Taxonomy = Taxonomy;
}
public RatingBeanX getRating() {
return Rating;
}
public void setRating(RatingBeanX Rating) {
this.Rating = Rating;
}
public boolean isIsTrading() {
return IsTrading;
}
public void setIsTrading(boolean IsTrading) {
this.IsTrading = IsTrading;
}
public int getTotalCoinsMined() {
return TotalCoinsMined;
}
public void setTotalCoinsMined(int TotalCoinsMined) {
this.TotalCoinsMined = TotalCoinsMined;
}
public int getBlockNumber() {
return BlockNumber;
}
public void setBlockNumber(int BlockNumber) {
this.BlockNumber = BlockNumber;
}
public int getNetHashesPerSecond() {
return NetHashesPerSecond;
}
public void setNetHashesPerSecond(int NetHashesPerSecond) {
this.NetHashesPerSecond = NetHashesPerSecond;
}
public int getBlockReward() {
return BlockReward;
}
public void setBlockReward(int BlockReward) {
this.BlockReward = BlockReward;
}
public int getBlockTime() {
return BlockTime;
}
public void setBlockTime(int BlockTime) {
this.BlockTime = BlockTime;
}
......//
}
}
}
I want json to be in Array response. How can I do this?
ApiService class looks like -
#GET("/data/all/coinlist")
Call<CoinBean> getCurrencyList(
#Query("api_key") String apiKey
);
u can create below class structure to de serialize at ur side.
Class Data {
List<Map<String, ImageInfo>> body = new ArrayList()
}

cannot put values inside Array List

I've tried to set values inside movies ArrayList in BlogRepository class.
but I couldn't find the results in the end.
I want to modify the example so that the storage inside the ArrayList is movies.
so the example works and the results show then the example works.
json data :
[
{
"albumId": 1,
"id": 1,
"title": "accusamus beatae ad facilis cum similique qui sunt",
"url": "https://via.placeholder.com/600/92c952",
"thumbnailUrl": "https://via.placeholder.com/150/92c952"
},
{
"albumId": 1,
"id": 2,
"title": "reprehenderit est deserunt velit ipsam",
"url": "https://via.placeholder.com/600/771796",
"thumbnailUrl": "https://via.placeholder.com/150/771796"
},
{
"albumId": 1,
"id": 3,
"title": "officia porro iure quia iusto qui ipsa ut modi",
"url": "https://via.placeholder.com/600/24f355",
"thumbnailUrl": "https://via.placeholder.com/150/24f355"
}
]
Code:
//
public class BlogRepository {
private ArrayList<Blog2> movies = new ArrayList<>();
private MutableLiveData<List<Blog2>> mutableLiveData = new MutableLiveData<>();
private Application application;
public BlogRepository(Application application){
this.application = application;
}
public MutableLiveData<List<Blog2>> getMutableLiveData() {
RestApiService service = RetrofitInstance.getApiService();
Call<List<BlogWrapper>> call = service.getPopularBlog();
call.enqueue(new Callback<List<BlogWrapper>>(){
#Override
public void onResponse(Call<List<BlogWrapper>> call, Response<List<BlogWrapper>> response) {
List<BlogWrapper> mBlogWrapper = response.body();
for (int i=0; i<mBlogWrapper.size(); i++) {
movies = (ArrayList<Blog2>) mBlogWrapper.get(i).getBlog();
//Log.d("trace_movies : ",""+ movies);
}
}
#Override
public void onFailure(Call<List<BlogWrapper>> call, Throwable t) {
// Toast.makeText(MainActivity.this, "Unable to load users", Toast.LENGTH_SHORT).show();
Log.e("trace_2",""+t.getMessage().toString());
}
});
return mutableLiveData;
}
}
//
public class Blog2 {
#SerializedName("albumId")
private int albumId;
#SerializedName("id")
private int id;
#SerializedName("title")
private String title;
#SerializedName("url")
private String url;
#SerializedName("thumbnailUrl")
private String thumbnailUrl;
public void setAlbumId(int albumId) {
this.albumId = albumId;
}
public void setId(int id) {
this.id = id;
}
public void setTitle(String title) {
this.title = title;
}
public void setUrl(String url) {
this.url = url;
}
public void setThumbnailUrl(String thumbnailUrl) {
this.thumbnailUrl = thumbnailUrl;
}
public int getAlbumId() {
return albumId;
}
public int getId() {
return id;
}
public String getTitle() {
return title;
}
public String getUrl() {
return url;
}
public String getThumbnailUrl() {
return thumbnailUrl;
}
}
///
public class BlogWrapper {
#SerializedName("data")
private List<Blog2> mData;
#SerializedName("error")
private Boolean mError;
#SerializedName("message")
private String mMessage;
#SerializedName("status")
private String mStatus;
public List<Blog2>getBlog() {
return mData;
}
public void setBlog(List<Blog2> data) {
mData = data;
}
public Boolean getError() {
return mError;
}
public void setError(Boolean error) {
mError = error;
}
public String getMessage() {
return mMessage;
}
public void setMessage(String message) {
mMessage = message;
}
public String getStatus() {
return mStatus;
}
public void setStatus(String status) {
mStatus = status;
}
}
///
public interface RestApiService {
#GET("/photos")
public Call<List<BlogWrapper>> getPopularBlog();
}
//
public class RetrofitInstance {
private static Retrofit retrofit = null;
public static final String BASE_URL_ = "https://jsonplaceholder.typicode.com/albums/1/";
// public static final String BASE_URL_ = "https://androidwave.com/api/";
public static RestApiService getApiService() {
Gson gson = new GsonBuilder().setLenient().create();
if (retrofit == null) {
retrofit = new retrofit2.Retrofit
.Builder()
.baseUrl(BASE_URL_)
.addConverterFactory(GsonConverterFactory.create(gson))
.build();
}
return retrofit.create(RestApiService.class);
}
}
Try this code, sorry i am away from laptop... mybe you can understand from this. I just swich response object as List<Blog2>, because you need it
call.enqueue(new Callback<List<Blog2>>(){
#Override
public void onResponse(Call<List<Blog2>> call, Response<List<Blog2>> response) {
List<Blog2> mBlogWrapper = response.body();
for (int i=0; i<mBlogWrapper.size(); i++) {
movies.add(mBlogWrapper.get(i));
//Log.d("trace_movies : ",""+ movies);
}
}
});
now you have values from the List, then you can store its value to MutableLivedata.
Also don't forget to change your Retrofit method
public interface RestApiService {
#GET("/photos")
public Call<List<Blog2>> getPopularBlog();
}

Rest Assured - Post nested POJO in Body

I'm trying to write an API class to send requests and handle responses from an API. Parts of the API have requests that require JSON bodies attached to the request such as this sample:
{
"Title": "string",
"Status": "string",
"ActFinish": "Date",
"ActHrs": "float",
"ActStart": "Date",
"ActualResults": "string",
"AssigneeUserId": "int",
"CustomFields": [
{
"Id": "string",
"Name": "string",
"Value": "string"
}
],
"Description": "string",
"EstFinish": "Date",
"EstHrs": "float",
"EstHrsRemaining": "float",
"EstStart": "Date",
"ExpectedResults": "string",
"FolderId": "int",
"FunctionalAreaCode": "string",
"HowFoundCode": "string",
"IssueCode": "string",
"ModuleCode": "string",
"PctComplete": "int",
"PriorityCode": "string",
"Resolution": "string",
"ResolutionCode": "string",
"SeverityCode": "string",
"SoftwareVersionCode": "string",
"StepsToRepro": "string"
}
The best way to do this I found through reading the Rest Assured documentation is with POJOs mentioned here: https://github.com/rest-assured/rest-assured/wiki/Usage#serialization
My POJO looks like this:
public class RequestDefectPost {
public String title;
public String status;
public Timestamp actFinish;
public float actHours;
public Timestamp actStart;
public String actualResults;
public int assigneeUserId;
public String[] customFields;
public String id;
public String name;
public String value;
public String description;
public Timestamp estFinish;
public float estHours;
public float estHrsRemaining;
public Timestamp estStart;
public String expectedResults;
public int folderId;
public String functionalAreaCode;
public String howFoundCode;
public String issueCode;
public String moduleCode;
public int pctComplete;
public String priorityCode;
public String resolutionCode;
public String severityCode;
public String softwareVersionCode;
public String stepsToRepro;
public RequestDefectPost(String title, String status) {
this.title = title;
this.status = status;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getStatus() {
return status;
}
public void setStatus(String status) {
this.status = status;
}
public Timestamp getActFinish() {
return actFinish;
}
public void setActFinish(Timestamp actFinish) {
this.actFinish = actFinish;
}
public float getActHours() {
return actHours;
}
public void setActHours(float actHours) {
this.actHours = actHours;
}
public Timestamp getActStart() {
return actStart;
}
public void setActStart(Timestamp actStart) {
this.actStart = actStart;
}
public String getActualResults() {
return actualResults;
}
public void setActualResults(String actualResults) {
this.actualResults = actualResults;
}
public int getAssigneeUserId() {
return assigneeUserId;
}
public void setAssigneeUserId(int assigneeUserId) {
this.assigneeUserId = assigneeUserId;
}
public String[] getCustomFields() {
return customFields;
}
public void setCustomFields(String id, String name, String value) {
this.customFields = new String[]{this.id = id, this.name = name, this.value = value};
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getValue() {
return value;
}
public void setValue(String value) {
this.value = value;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
public Timestamp getEstFinish() {
return estFinish;
}
public void setEstFinish(Timestamp estFinish) {
this.estFinish = estFinish;
}
public float getEstHours() {
return estHours;
}
public void setEstHours(float estHours) {
this.estHours = estHours;
}
public float getEstHrsRemaining() {
return estHrsRemaining;
}
public void setEstHrsRemaining(float estHrsRemaining) {
this.estHrsRemaining = estHrsRemaining;
}
public Timestamp getEstStart() {
return estStart;
}
public void setEstStart(Timestamp estStart) {
this.estStart = estStart;
}
public String getExpectedResults() {
return expectedResults;
}
public void setExpectedResults(String expectedResults) {
this.expectedResults = expectedResults;
}
public int getFolderId() {
return folderId;
}
public void setFolderId(int folderId) {
this.folderId = folderId;
}
public String getFunctionalAreaCode() {
return functionalAreaCode;
}
public void setFunctionalAreaCode(String functionalAreaCode) {
this.functionalAreaCode = functionalAreaCode;
}
public String getHowFoundCode() {
return howFoundCode;
}
public void setHowFoundCode(String howFoundCode) {
this.howFoundCode = howFoundCode;
}
public String getIssueCode() {
return issueCode;
}
public void setIssueCode(String issueCode) {
this.issueCode = issueCode;
}
public String getModuleCode() {
return moduleCode;
}
public void setModuleCode(String moduleCode) {
this.moduleCode = moduleCode;
}
public int getPctComplete() {
return pctComplete;
}
public void setPctComplete(int pctComplete) {
this.pctComplete = pctComplete;
}
public String getPriorityCode() {
return priorityCode;
}
public void setPriorityCode(String priorityCode) {
this.priorityCode = priorityCode;
}
public String getResolutionCode() {
return resolutionCode;
}
public void setResolutionCode(String resolutionCode) {
this.resolutionCode = resolutionCode;
}
public String getSeverityCode() {
return severityCode;
}
public void setSeverityCode(String severityCode) {
this.severityCode = severityCode;
}
public String getSoftwareVersionCode() {
return softwareVersionCode;
}
public void setSoftwareVersionCode(String softwareVersionCode) {
this.softwareVersionCode = softwareVersionCode;
}
public String getStepsToRepro() {
return stepsToRepro;
}
public void setStepsToRepro(String stepsToRepro) {
this.stepsToRepro = stepsToRepro;
}
}
With my current POJO, the JSON being spit out by Rest Assured looks like this:
{
"title": "Test",
"status": "New",
"actFinish": null,
"actHours": 0.0,
"actStart": null,
"actualResults": null,
"assigneeUserId": 0,
"customFields": [
"Test",
"test",
"tesT"
],
"id": "Test",
"name": "test",
"value": "tesT",
"description": null,
"estFinish": null,
"estHours": 0.0,
"estHrsRemaining": 0.0,
"estStart": null,
"expectedResults": null,
"folderId": 0,
"functionalAreaCode": null,
"howFoundCode": null,
"issueCode": null,
"moduleCode": null,
"pctComplete": 0,
"priorityCode": null,
"resolutionCode": null,
"severityCode": null,
"softwareVersionCode": null,
"stepsToRepro": null
}
My question is how do I write the the customFields such that it is nested correctly, as outlined in the sample JSON?
You need another POJO that represents a "CustomFields". For example:
public class CustomFields {
private String Id;
private String Name;
private String Value;
<getters and setters>
}
and use List<CustomFields> CustomFields instead of String[] customFields. Also note that your JSON example doesn't use camel case for the property names so your POJO shouldn't use camel case either.
There are ways to avoid using a POJO at all in REST Assured. You can for example use a HashMap instead which could be easier in some situations.

Java to json String ignore null values

I am creating this json string from the server as shown below and I was able to parse the string too. But when creating the json some fields like errormessage,createdDate,priority are null values. I dont want to show them in the string how can I do that?
Json Strin
{
"errormessage": null,
"createdDate": null,
"list": [{
"type": "app1",
"alternateId": "AlternateID",
"priority": null,
"description": "app for desc",
}],
"locationName": null,
"facilityManagerName": null,
"codeName": null,
"sourceKey": null,
"tablename": null,
"path": "list",
"service": "listserver",
"license": null,
"key": null,
}
expected String
{
"list": [{
"type": "app1",
"alternateId": "AlternateID",
"description": "app for desc",
}],
"path": "list",
"service": "listserver",
}
Generic Java Bean For creating the json:
public class AppObject<T> implements Serializable {
private String errormessage;
private Date createdDate;
private List<T> list;
private String locationName;
private String facilityManagerName;
private String codeName;
private Long sourceKey;
private String tablename;
private String path;
private String service;
private String license;
private Long key;
public AppObject() {
list = new ArrayList<T>();
}
public AppObject(List<T> list) {
this.list = list;
}
#XmlAnyElement(lax = true)
public List<T> getList() {
return list;
}
public void setList(List<T> list) {
this.list = list;
}
public String getLicense() {
return license;
}
public void setLicense(String license) {
this.license = license;
}
public String getPath() {
return path;
}
public void setPath(String path) {
this.path = path;
}
public String getService() {
return service;
}
public void setService(String service) {
this.service = service;
}
public String getTablename() {
return tablename;
}
public void setTablename(String tablename) {
this.tablename = tablename;
}
public String getErrormessage() {
return errormessage;
}
public void setErrormessage(String errormessage) {
this.errormessage = errormessage;
}
public Long getKey() {
return key;
}
public void setKey(Long key) {
this.key = key;
}
public String getLocationName() {
return locationName;
}
public void setLocationName(String locationName) {
this.locationName = locationName;
}
public String getFacilityManagerName() {
return facilityManagerName;
}
public void setFacilityManagerName(String facilityManagerName) {
this.facilityManagerName = facilityManagerName;
}
public Date getCreatedFeedFromDate() {
return createdFeedFromDate;
}
#JsonDeserialize(using = com.vxl.JsonDateDeserializer.class)
public void setCreatedFeedFromDate(Date createdFeedFromDate) {
this.createdFeedFromDate = createdFeedFromDate;
}
public Date getCreatedDate() {
return createdFeedToDate;
}
#JsonDeserialize(using = com.vxl.JsonDateDeserializer.class)
public void setCreatedDate(Date createdDate) {
this.createdDate = createdDate;
}
}
Honestly, I really wouldn't spend time on making a payload "look nice". Now if you said that you were motivated to keep the payload small for efficiency reasons I'd buy that.
Perhaps you use Jackson for serialising to JSON as well (I don't see why you are using two different libraries). I think that this question shows that Jackson's treatment of nulls can be controlled.
Change your get method. Set if(something!=null)return something; instead of return something;

Categories