Save relationship from retrofit into realm. - android

I'm receiving json from an API with article objects which include an array of images for that article. Take a look.
I'm using retrofit with gson to convert the data to Java objects.
These objects extend RealmObject, so they can be saved to realm immediately.
Article
Image
I use copyToRealmOrUpdate for saving the received objects to realm.
The articles are perfectly stored, but the images aren't although they are in the returned retrofit objects.
It seems like they aren't persisted automatically.
Do I need to loop over those articles and then copyToRealmOrUpdate the images array?
Then simply call setImages() with the images RealmList?
What's the best way to solve this problem?
Let me know if you need more information. I'm currently on my mobile and could give you later more.

The problem seems to be that in the JSON string "images" is not an array of image objects, but it's a "data" object which itself is in turn an array of image objects.
Do you have control over the JSON format or is it just something you receive and have no control over?

Related

How do I use Retrofit2, RxJava2, Gson TypeAdapterFActory to map Gson correctly?

I'm currently using Retrofit2, RxJava2, Retrofit2 RxJava2 Adapter, RxAndroid. FIRST OF ALL, should I be using TypeAdapterFactory to deserialize and serialize my Gson instead of JsonSerializer (I heard the former is faster than the latter)?
My Gson has a very complicated structure:
Picture of JSON complicated structure
First, as I mentioned, I am planning on using TypeAdapterFactory. Is this the best performance solution to map all the different cases of the Gson I have? For example, sometimes just "data" dict, sometimes there's an "errors" field, sometimes "data" has just one field under it, sometimes "data" has another complex json data structure
Even still, I have to make Response objects (ComputerResponse etc) that encapsulate the corresponding Computer object (or map all the json fields to the POJO). I don't want to do this mapping every single time a ComputerResponse is returned, or maybe do the mapping once, in order to improve performance. How should I go about doing that?
I think you just need to create one model that it has all fields in the most complete way, you can create your method with this tool.

Storing JSON on android: sqlite vs SharedPreference

For an application which will allow members of my organisation to see data on their mobile device i need to store pre-formatted data on the device so they can see it offline as well. How they get the data is trough a JSON request-response.
The response is formatted as follows (anonymised ofc):
[{
"firstname":"John",
"lastname":"Smith",
"group":"1",
"age":11,
"installed":"Ja",
"medical":"Is aan zijn linker zijde verlamd geweest.",
"notes":"Heimee. \r\nBeschermend opgevoed. \r\nTerug getrokken persoonlijkheid.",
"Insignes":["test", "Test2"],
"Parents":[]
},
{
"firstname":"Emely",
"lastname":"Watson",
"group":"33",
"age":14,
"installed":"Ja",
"medical":"",
"notes":"Test",
"Insignes":["Veilig & Gezond I","CWO II","CWO III","Kampeertechnieken & Pionieren"],
"Parents":[
{
"name":"ouder ouder",
"address":"op | 0000AA Amsterdam",
"phone1":"",
"phone2":"0612345678",
"mail":"example#google.com"
}]
}]
I have read a couple of discussion on how to best store this:
Is it ok to save a JSON array in SharedPreferences?
How to save JSON Array in SharedPreferences?
Android: what is the best way to store JSON data offline for the app in android?
Android - how to add JSON object to sharedPreferences?
What is the advantage of Using SQLite rather than File?
From reading these I have gathered that SharedPreference files are "faster" than sqlite but are prone to corruption. SQLite is a database and since the data comes from one I am inclined to use that at the cost of processing speed.
Now I only need to store and then read the data, it wont be mutated unless there is an update on the "main server" in which case I will probably wipe the local data and repopulate it. In these threads i have read that storing JSON in sharedpreference is easy but difficult to read.
But after reading these (and more) discussions I am no closer to knowing/deciding what the best way to store my json is.
Any advice is greatly appreciated!
You can try the ORMs like Realm or sugarORM and store the json has object in the database. They also provide the Cipher options by which you can encrypt the data too, Which would be more flexible.
http://www.androidauthority.com/use-android-keystore-store-passwords-sensitive-information-623779/
http://www.androidhive.info/2016/05/android-working-with-realm-database-replacing-sqlite-core-data/
If you don't need to use any ORM by third parties then you can directly encrypt the JSON string with the android keystore keys and then can store the encrypted string in the normal sqlite.
This is opinion based answer. Android no I wouldn't store JSON in a DB or preferences. Store the json in a file. A file can be accessed as stream the same way you stream access json. Virtually no upper limit on size in a file. I might store a link to the json file in a DB or preferences. Depending on application I might just extract json into abstract elements and store in DB for ordering selection.
The data you have provided depending on sensitivity I would extract and insert into the contacts database for the device.
The best option is to go with a database approach, for one it sounds your dataset might be large are rather expected to be large. Database persist large sets of information, however I do not recommend using SQLITE , for it is sql based, no ORM and the operations can get tedious and time consuming and mainly it is slow(debatable). Rather use the hottest and latest no-sql database for android and ios, which Realm, realm is super fast, it is based on java annotations and ORM(like hibernate). To work with json in android I recommend familiarizing yourself with GSON, A Java serialization/deserialization library that can convert Java Objects into JSON and back.
Shared Preferenences are really convenient to store small key value pairs, If you have a relatively small collection of key-values that you'd like to save, you should use the SharedPreferences APIs. A SharedPreferences object points to a file containing key-value pairs and provides simple methods to read and write them. You would of to still work with gson here, I never heard of a shared preference getting corrupted, what I do know is that they are fragile,and live with the existence of your app installation.
Conclusion: If your dataset is large use a database approach to persist large dataset, maintenance and modifications are more fluent here, however if you know that whatever you are storing is relatively small, use a shared pref, and to manipulate json constructs in android to and fro use the google gson library.
SharedPreferences :
If you have small amount of data in Json then you have to store it in SharedPreferences.
You can easily store Json to SharedPreferences using Gson. Just using this :
Convert Json to String :
Gson gson = new Gson();
String jsonString = gson.toJson(jsonData);
Convert String to Json :
gson.fromJson(jsonString, TypeToConvert);
Sqlite Database :
If you have large amount of data in Json then just go with Sqlite.

Best Practice for loading data from server (Android App)

I'm building an Android app, which should:
show some data, loaded from a server in the Internet.
At the moment I have a local SQliteDB used in my app where the data is stored, which should be displayed. I use this, because I want to be able to show the data, even if there is temporarily no internet connection available.
Next step I will work on inserting data in the local SQliteDB from a internet server. I thought about doing it this way:
When app starts, check if internet is available. If yes, connect to a webservice (including username and password). The webservice should deliver the necessary data via json object to the app and I will update the local SQlite DB.
My questions:
Is this a good idea?
Are there any better ways to do this?
The data can be viewed (and edited) by a Zend Website, too.
Thanks in advance.
Best regards
Daniel
The way you put it seems optimal. Maybe you should set a flag or alert which is time or date related..in case the app starts too many times without internet.
>> For updates to your mobile app, you should consider the priority/urgency of having the same data on the server and your app.
> For the better ways to do it, you can opt the way which suits your requirement better.
To fetch the data in one thread and render it in another,
1. Write custom Asynctasks:
http://developer.android.com/reference/android/os/AsyncTask.html
AsyncTask Android example
OR
2. Use something like AsyncHttpClient: http://loopj.com/android-async-http/
where you get onSuccess and onFailure methods to work with the response.
The option 2. is better if you just want to fetch data without doing anything else, and work on it, or save it. For the same, you need to parse the response first.
To parse your data:
As your response is JSON format, you may be better off using Gson to map data and with custom model classes. Eg.:
Gson gson = new Gson();
ModelClass modelClass= new ModelClass();
modelClass= gson.fromJson(responseContent,ModelClass.class);
//where responseContent is your jsonString
Log.i("Web service response", ""+modelClass.toString());
More on: https://code.google.com/p/google-gson/
For Naming discrepancies(according to the variables in webservice), can use annotations like
#SerializedName.
Use a for each loop to verify/browse/access the data that would be populated in/as objects/fields of your model class:
Check these for doubts:
http://docs.oracle.com/javase/1.5.0/docs/guide/language/foreach.html
How does the Java 'for each' loop work?
Now about saving your data:
>> It depends a lot on what the data from server is and how much data do you want to store.
In Android Storage Options:
http://developer.android.com/guide/topics/data/data-storage.html
a. There's Shared Preferences:
These are good for saving/storing data which would be relatively small in size and could be overwritten and fetched frequently. Eg. username, current user's details, password
http://developer.android.com/reference/android/content/SharedPreferences.html
How to use SharedPreferences in Android to store, fetch and edit values
b. Maintaining a database is good for the larger chunk needed in your app.
You can store, update or over-write the data according to your need. There can be multiple tables or more data could be stored in various fields.
http://developer.android.com/reference/android/database/sqlite/SQLiteDatabase.html
http://www.vogella.com/tutorials/AndroidSQLite/article.html
While you use Gson, you also have the option of populating the objects of model class and then storing that response in a String(maybe in SharedPreferences, depending on length/size) using gsonToJson method. I have used that, cheeky but effective.
You need to consider other stuff too, pertaining to UI and memory optimization, ListViews or layouts etc depending on your app and its control flow.
You could start a thread and get new data on loading the app. If you decide this path we had nice results with JSON using the Volley Project.
You can see a walk through here http://www.javacodegeeks.com/2013/06/android-volley-library-example.html
and get the code here
https://android.googlesource.com/platform/frameworks/volley/
Try using this library:-
https://github.com/Abhishekpalodath/FetchServerUtil-Android.git.
You can also load real-time data from the server by using this.

Storing Json parsed in Android using GSON

I'm very new to Android and I'm currently working on Android app that will parse JSON from a Restful API and display some of the data in a list view. I've looked into using GSON for parsing as the JSON was quite complex. Now my main problem is figuring out how to store the data somewhere so the app doesn't need to reload itself every time the activity is clicked on. I've looked at few questions here but they all seem to point to JSON only not GSON. Could anyone recommend an efficient way of doing this?
Thanks
if you want to store the data permanent it's the best way to insert your deserialized objects into a sqlite database or store them local to the disk as a file.
if your intention is to load the data for each startup, it's easier. just put your object into a public static object. so you can check if the object is not null or not. if it's null you have to load the data.
another opportunity is using the SharedPreferences.

Parsed Json (jackson) to objects data saving

To get Data for my application, I parse a Json file, with Jackson, to (lists of) custom Objects. When I start my app, I check if there is a new Json file available and ask the user if they want to download it, else I use the "old" Json file. But every time I start my app I parse the Json. Then I use the Application Class to save my list of objects an go to my data when I want, most of the time I only need one object.
From the huge list, with multiple layer nested object, I create a simple "flat" arraylist of custom objects in which I put only the data I need to create listviews (name, id, second text and url of picture). When something is clicked, i use the id to get all the data.
Parsing this whole Json file every time is pretty time consuming and makes the startup time of my application long. Ofcourse, this sucks.
And having this huge list of custom objects saved in Application Class fills a lot of memory of my device, and sometimes after some use the class gets killed, and I need to reparse again.
Is there a way I don't need to reparse all my data?
I hoped for a process like this:
new Json file
first time parse total JSON to list of multilayered custom objects
create simple list for listviews
delete/clear the big list
some clever way to get only one of the giant items, without keeping the whole list in my memory. (maybe something with Jackson).
on destroying of the application maybe save the simple list, i read something about parceable or serializable?
Anyone knows how to achieve this?
Or has an other awesome idea?
Jackson has a streaming api. Also you can parse the json in a AsyncTask (in the background) and update your user interface once the new data is ready
I'd probably store the data in a SQLite database, in line with how the Android platform was designed.
As an alternative to streaming Jackson API (which is very fast, but still has to scan through most of the content), perhaps you could just save things in different files, one per entry? Or, if there is a way to group things, in multiple files each having some subset?
Of course, if you really have tons of entries, use of SQLite as Bruce suggested makes lots of sense.

Categories

Resources