Data Types
24 min
parse data types on android introduction in this guide, you will learn about the parse datatypes using android you will read and save the parse objects on back4app from an android app storing data on parse is built around the \<font color="#2166ae">parseobject\</font> each \<font color="#2166ae">parseobject\</font> contains key value pairs of json compatible data this data is schemaless, which means that we don’t need to specify ahead of time what keys exist on each \<font color="#2166ae">parseobject\</font> we can set whatever key value pairs we want, and our backend will store them for example, let’s say we’re tracking high scores for a game a single \<font color="#2166ae">parseobject\</font> could contain 1 score 1337 , playername "sean plott" , cheatmode false keys must be alphanumeric strings, and values can be \<font color="#2166ae">string\</font> => \<font color="#2166ae">string\</font> \<font color="#2166ae">number\</font> (primitive numeric values such as \<font color="#2166ae">int\</font> , \<font color="#2166ae">double\</font> ) \<font color="#2166ae">bool\</font> => \<font color="#2166ae">boolean\</font> \<font color="#2166ae">datetime\</font> => java util date \<font color="#2166ae">null\</font> => jsonobject null \<font color="#2166ae">array\</font> =>jsonarray \<font color="#2166ae">file\</font> => parse file \<font color="#2166ae">pointer\</font> => other parseobject \<font color="#2166ae">relation\</font> => parserelation \<font color="#2166ae">geopoint\</font> => parsegeopoint each \<font color="#2166ae">parseobject\</font> has a class name that we can use to distinguish different sorts of data for example, we could call the high score object a \<font color="#2166ae">gamescore\</font> there are also a few fields we don’t need to specify that are provided as a convenience \<font color="#2166ae">objectid\</font> is a unique identifier for each saved object \<font color="#2166ae">createdat\</font> and \<font color="#2166ae">updatedat\</font> represent the time that each object was created and last modified in the cloud each of these fields is automatically filled in by back4app at the moment we save a new \<font color="#2166ae">parseobject\</font> we recommend you \<font color="#2166ae">nameyourclasseslikethis\</font> (uppercamelcase) and \<font color="#2166ae">nameyourkeyslikethis \</font> (lowercamelcase), just to keep your code looking pretty this tutorial uses a basic app created in android studio 4 1 1 with \<font color="#2166ae">buildtoolsversion=30 0 2\</font> , \<font color="#2166ae">compile sdk version\</font> = \<font color="#2166ae">30 0 2\</font> and \<font color="#2166ae">targetsdkversion 30\</font> at any time, you can access the complete project via our github repositories kotlin example repository https //github com/templates back4app/android crud operations kotlin java example repository https //github com/templates back4app/android crud operations java goal our goal is to create an android app that can process all data types provided by parse server here is a preview of what we are gonna achive prerequisites to complete this tutorial, we need android studio https //developer android com/studio/index html an app created on back4app note follow the new parse app tutorial https //www back4app com/docs/get started/new parse app to learn how to create a parse app on back4app an android app connected to back4app note follow the install parse sdk tutoria https //www back4app com/docs/android/parse android sdk l to create an android studio project connected to back4app a device (or virtual device https //developer android com/studio/run/managing avds html ) running android 4 1 (jelly bean) or newer understanding our app you will create an app for a better understanding of parse \<font color="#2166ae">data types\</font> in this \<font color="#2166ae">android\</font> app, you will create all data types in a class named \<font color="#2166ae">datatypes\</font> and assign values to this classes variables then we will read and update this data note the data types \<font color="#2166ae">pointer\</font> , \<font color="#2166ae">relation\</font> , \<font color="#2166ae">file\</font> , \<font color="#2166ae">geopoint\</font> will be covered later in specific guides let’s get started! 1 create app template define the following variables in the \<font color="#2166ae">mainactivity\</font> and replace the code in the \<font color="#2166ae">oncreate\</font> method with the following code 1 private progressdialog progressdialog; 2 private view popupinputdialogview; 3 private recyclerview recyclerview; 4 private string objectid; 5 private static final string tag = "mainactivity"; 6 7 @override 8 protected void oncreate(bundle savedinstancestate) { 9 super oncreate(savedinstancestate); 10 setcontentview(r layout activity main); 11 12 progressdialog = new progressdialog(mainactivity this); 13 14 button savedata = findviewbyid(r id savedata); 15 button readdata = findviewbyid(r id readdata); 16 button updatedata = findviewbyid(r id updatedata); 17 18 savedata setonclicklistener(savedataview > { 19 try { 20 savedatatypes(); 21 } catch (jsonexception e) { 22 e printstacktrace(); 23 } 24 }); 25 26 readdata setonclicklistener(readdataview > readobjects()); 27 28 updatedata setonclicklistener(updatedataview > updateobject()); 29 30 }1 private var progressdialog progressdialog? = null 2 private var objectid string? = null 3 private var popupinputdialogview view? = null 4 private var recyclerview recyclerview? = null 5 private val tag = "mainactivity" 6 7 override fun oncreate(savedinstancestate bundle?) { 8 super oncreate(savedinstancestate) 9 setcontentview(r layout activity main) 10 11 progressdialog = progressdialog(this\@mainactivity) 12 val savedata = findviewbyid\<button>(r id savedata) 13 val readdata = findviewbyid\<button>(r id readdata) 14 val updatedata = findviewbyid\<button>(r id updatedata) 15 16 savedata setonclicklistener { 17 try { 18 savedatatypes() 19 } catch (e jsonexception) { 20 e printstacktrace() 21 } 22 } 23 readdata setonclicklistener { readobjects() } 24 updatedata setonclicklistener { updateobject() } 25 } before next steps, we need to connect \<font color="#2166ae">back4app\</font> to our application you should save the \<font color="#2166ae">appid\</font> and \<font color="#2166ae">clientkey\</font> from the \<font color="#2166ae">back4app\</font> to \<font color="#2166ae">string xml\</font> file and then init \<font color="#2166ae">parse\</font> in our \<font color="#2166ae">app java\</font> or \<font color="#2166ae">app kt\</font> file follow the new parse app tutorial https //www back4app com/docs/android/parse android sdk if you don’t know how to init \<font color="#2166ae">parse\</font> to your app 2 code for save object the create function will create a new object in back4app database we define the \<font color="#2166ae">savedatatypes\</font> function that we call in the \<font color="#2166ae">oncreate\</font> function and use the following code in this function we will save all data types with this function to the datatypes classes object 1 private void savedatatypes() throws jsonexception{ 2 parseobject parseobject = new parseobject("datatypes"); 3 4 parseobject put("stringfield", "string"); 5 parseobject put("doublefield", 1 5); 6 parseobject put("intfield", 2); 7 parseobject put("boolfield", true); 8 parseobject put("datefield", calendar getinstance() gettime()); 9 10 jsonobject myobject = new jsonobject(); 11 myobject put("number", 1); 12 myobject put("string", "42"); 13 14 parseobject put("jsonobject", myobject); 15 16 17 jsonarray myarray = new jsonarray(); 18 myarray put(myobject); 19 myarray put(myobject); 20 myarray put(myobject); 21 22 parseobject put("jsonarray", myarray); 23 24 25 list\<string> list = new arraylist<>(); 26 list add("string1"); 27 list add("string2"); 28 parseobject put("liststringfield", list); 29 30 list\<integer> listint = new arraylist<>(); 31 listint add(1); 32 listint add(2); 33 listint add(3); 34 parseobject put("listintfield", listint); 35 36 list\<boolean> listbool = new arraylist<>(); 37 listbool add(true); 38 listbool add(false); 39 parseobject put("listboolfield", listbool); 40 41 progressdialog show(); 42 parseobject saveinbackground(e > { 43 progressdialog dismiss(); 44 if (e == null) { 45 toast maketext(this, "object created successfully ", toast length short) show(); 46 objectid = parseobject getobjectid(); 47 } else { 48 objectid = null; 49 toast maketext(this, e getmessage(), toast length long) show(); 50 } 51 }); 52 }1 private fun savedatatypes() { 2 val parseobject = parseobject("datatypes") 3 4 parseobject put("stringfield", "string") 5 parseobject put("doublefield", 1 5) 6 parseobject put("intfield", 2) 7 parseobject put("boolfield", true) 8 parseobject put("datefield", calendar getinstance() time) 9 10 11 val myobject = jsonobject() 12 myobject put("number", 1) 13 myobject put("string", "42") 14 15 parseobject put("jsonobject", myobject) 16 17 val myarray = jsonarray() 18 myarray put(myobject) 19 myarray put(myobject) 20 myarray put(myobject) 21 22 parseobject put("jsonarray", myarray) 23 24 val list mutablelist\<string> = arraylist() 25 list add("string1") 26 list add("string2") 27 parseobject put("liststringfield", list) 28 29 val listint mutablelist\<int> = arraylist() 30 listint add(1) 31 listint add(2) 32 listint add(3) 33 parseobject put("listintfield", listint) 34 35 val listbool mutablelist\<boolean> = arraylist() 36 listbool add(true) 37 listbool add(false) 38 parseobject put("listboolfield", listbool) 39 40 progressdialog? show() 41 parseobject saveinbackground { 42 progressdialog? dismiss() 43 if (it == null) { 44 toast maketext(this, "object created successfully ", toast length short) show() 45 objectid = parseobject objectid 46 } else { 47 objectid = null 48 toast maketext(this, it message, toast length long) show() 49 } 50 } 51 } 3 code for read object we will give the \<font color="#2166ae">objectid\</font> variable that we have assigned in the \<font color="#2166ae">savedatatypes\</font> function as a parameter to the query and read the data that we have saved in the \<font color="#2166ae">savedatatypes\</font> function with the \<font color="#2166ae">readobjects\</font> function 1 private void readobjects() { 2 if (objectid == null) { 3 toast maketext(this, "no object click on the 'save data' button before ", toast length short) show(); 4 return; 5 } 6 7 parsequery\<parseobject> query = new parsequery<>("datatypes"); 8 9 progressdialog show(); 10 query getinbackground(objectid, (object, e) > { 11 progressdialog dismiss(); 12 if (e == null) { 13 list\<data> list = new arraylist<>(); 14 list add(new data("int list field",object get("listintfield") tostring())); 15 list add(new data("string field",object get("stringfield") tostring())); 16 list add(new data("double field",object get("doublefield") tostring())); 17 list add(new data("int field",object get("intfield") tostring())); 18 list add(new data("string list field",object get("liststringfield") tostring())); 19 list add(new data("date field",object get("datefield") tostring())); 20 list add(new data("bool field",object get("boolfield") tostring())); 21 list add(new data("list bool field",object get("listboolfield") tostring())); 22 list add(new data("json object field",object get("jsonobject") tostring())); 23 list add(new data("json array field",object get("jsonarray") tostring())); 24 25 showdatatypes(list); 26 27 } else { 28 toast maketext(this, e getmessage(), toast length short) show(); 29 } 30 }); 31 }1 private fun readobjects() { 2 if (objectid == null) { 3 toast maketext( 4 this, 5 "no object click on the 'save data' button before ", 6 toast length short 7 ) show() 8 return 9 } 10 11 val query = parsequery\<parseobject>("datatypes") 12 13 14 progressdialog? show() 15 query getinbackground( 16 objectid 17 ) { obj, e > 18 progressdialog? dismiss() 19 if (e == null) { 20 21 val list mutablelist\<data> = arraylist() 22 list add(data("int list field", obj get("listintfield") tostring())) 23 list add(data("string field",obj get("stringfield") tostring())) 24 list add(data("double field", obj get("doublefield") tostring())) 25 list add(data("int field", obj get("intfield") tostring())) 26 list add(data("string list field", obj get("liststringfield") tostring())) 27 list add(data("date field",obj get("datefield") tostring())) 28 list add(data("bool field", obj get("boolfield") tostring())) 29 list add(data("list bool field", obj get("listboolfield") tostring())) 30 list add(data("json object field", obj get("jsonobject") tostring())) 31 list add(data("json array field", obj get("jsonarray") tostring())) 32 showdatatypes(list) 33 } else { 34 toast maketext(this, e message, toast length short) show() 35 } 36 37 } 38 } in this section, we have created a model class called \<font color="#2166ae">data\</font> we use the data we get in the \<font color="#2166ae">readobjects\</font> function to create objects from this model class we give these objects as elements to the list we created in \<font color="#2166ae">data\</font> type then we give this list as a parameter to the \<font color="#2166ae">showdatatypes\</font> function and list it in the \<font color="#2166ae">alertdialog\</font> this is the \<font color="#2166ae">data\</font> model 1 public class data { 2 private string type; 3 private string value; 4 5 public data(string type, string value) { 6 this type = type; 7 this value = value; 8 } 9 10 public string gettype() { 11 return type; 12 } 13 14 public data settype(string type) { 15 this type = type; 16 return this; 17 } 18 19 public string getvalue() { 20 return value; 21 } 22 23 public data setvalue(string value) { 24 this value = value; 25 return this; 26 } 27 }1 class data(val type\ string?=null,val value\ string?=null) { 2 3 } this is the \<font color="#2166ae">showdatatypes\</font> function 1 private void showdatatypes(list\<data> list){ 2 alertdialog builder alertdialogbuilder = new alertdialog builder(mainactivity this); 3 alertdialogbuilder settitle("data types"); 4 alertdialogbuilder setcancelable(true); 5 initpopupviewcontrols(list); 6 //we are setting our custom popup view by alertdialog builder 7 alertdialogbuilder setview(popupinputdialogview); 8 final alertdialog alertdialog = alertdialogbuilder create(); 9 alertdialog show(); 10 } 11 12 private void initpopupviewcontrols(list\<data> list) { 13 layoutinflater layoutinflater = layoutinflater from(mainactivity this); 14 popupinputdialogview = layoutinflater inflate(r layout custom alert dialog, null); 15 recyclerview = popupinputdialogview\ findviewbyid(r id recyclerview); 16 itemadapter adapter = new itemadapter(list,this); 17 recyclerview\ setlayoutmanager(new linearlayoutmanager(this,linearlayoutmanager vertical,false)); 18 recyclerview\ setadapter(adapter); 19 }1 private fun showdatatypes(list list\<data>) { 2 val alertdialogbuilder = alertdialog builder(this\@mainactivity) 3 alertdialogbuilder settitle("data types") 4 alertdialogbuilder setcancelable(true) 5 initpopupviewcontrols(list) 6 //we are setting our custom popup view by alertdialog builder 7 alertdialogbuilder setview(popupinputdialogview) 8 val alertdialog = alertdialogbuilder create() 9 alertdialog show() 10 } 11 12 @suppresslint("inflateparams") 13 private fun initpopupviewcontrols(list list\<data>) { 14 val layoutinflater = layoutinflater from(this\@mainactivity) 15 popupinputdialogview = layoutinflater inflate(r layout custom alert dialog, null) 16 recyclerview = popupinputdialogview? findviewbyid(r id recyclerview) 17 val adapter = itemadapter(this\@mainactivity, list) 18 recyclerview? layoutmanager = linearlayoutmanager( 19 this, 20 linearlayoutmanager vertical, 21 false 22 ) 23 recyclerview? adapter = adapter 24 } 4 code for update object the \<font color="#2166ae">updateobject\</font> function is responsible for updating data in the object created on the \<font color="#2166ae">savedatatypes\</font> function we are using \<font color="#2166ae">objectid\</font> again for update object 1 public void updateobject() { 2 if (objectid == null) { 3 toast maketext(this, "no object click on the 'save data' button before ", toast length short) show(); 4 return; 5 } 6 7 parseobject parseobject = new parseobject("datatypes"); 8 parseobject setobjectid(objectid); 9 parseobject put("intfield", 5); 10 parseobject put("stringfield", "new string"); 11 12 progressdialog show(); 13 14 parseobject saveinbackground(e > { 15 progressdialog dismiss(); 16 if (e == null) { 17 toast maketext(this, "object updated successfully ", toast length short) show(); 18 } else { 19 toast maketext(this, e getmessage(), toast length short) show(); 20 } 21 }); 22 }1 private fun updateobject() { 2 if (objectid == null) { 3 toast maketext( 4 this, 5 "no object click on the 'save data' button before ", 6 toast length short 7 ) show() 8 return 9 } 10 11 val parseobject = parseobject("datatypes") 12 parseobject objectid = objectid 13 parseobject put("intfield", 5) 14 parseobject put("stringfield", "new string") 15 16 progressdialog? show() 17 18 parseobject saveinbackground { 19 progressdialog? dismiss() 20 if (it == null) { 21 toast maketext(this, "object updated successfully ", toast length short) show() 22 } else { 23 toast maketext(this, it message, toast length short) show() 24 } 25 } 26 } 5 using counters the above example contains a common use case the \<font color="#2166ae">intfield\</font> field can be a counter that we’ll need to update continually the above solution works, but it’s cumbersome and can lead to problems if we have multiple clients trying to update the same counter parse provides methods that atomically increment any number field to help with storing counter type data so, the same update can be rewritten as 1 parseobject parseobject = new parseobject("datatypes"); 2 parseobject setobjectid(objectid); 3 parseobject increment("intfield",1);1 val parseobject = parseobject("datatypes") 2 parseobject objectid = objectid 3 parseobject increment("intfield",1) 6 using lists parse also provides methods to help in storing list data there are three operations that can be used to change a list field atomically \<font color="#2166ae">setadd\</font> and \<font color="#2166ae">setaddall\</font> append the given objects to the end of an array field \<font color="#2166ae">setaddunique\</font> and \<font color="#2166ae">setaddallunique\</font> \ add only the given objects which aren’t already contained in an array field to that field the position of the insert is not guaranteed \<font color="#2166ae">remove\</font> and \<font color="#2166ae">removeall\</font> removes all instances of the given objects from an array field 6 1 examples with add and addall \<font color="#2166ae">liststringfield\</font> has the value \["a","b","c","d","e","f","g","g"] running the code below 1 parseobject parseobject = new parseobject("datatypes"); 2 parseobject setobjectid(objectid); 3 parseobject add("liststringfield","e"); 4 parseobject addall("liststringfield", arrays aslist("e", "f", "g", "g")); 5 parseobject save();1 val parseobject = parseobject("datatypes") 2 parseobject objectid = objectid 3 parseobject add("liststringfield", "e") 4 parseobject addall("liststringfield", arrays aslist("e", "f", "g", "g")) 5 parseobject save() after this command the result of the stringlist field will be \["a","b","c","d","e","e","f","g","g"] 6 2 examples with addunique and addallunique \<font color="#2166ae">liststringfield\</font> has the value \["a","b","c","d","e"] running the code below 1 parseobject parseobject = new parseobject("datatypes"); 2 parseobject setobjectid(objectid); 3 parseobject addunique("liststringfield","e"); 4 parseobject addallunique("liststringfield",arrays aslist("c", "d", "e", "f")); 5 parseobject save();1 val parseobject = parseobject("datatypes") 2 parseobject objectid = objectid 3 parseobject addunique("liststringfield", "e") 4 parseobject addallunique("liststringfield", arrays aslist("c", "d", "e", "f")) 5 parseobject save() after this command the result of the \<font color="#2166ae">stringlist\</font> field will be \["a","b","c","d","e","f"] no values were repeated 6 3 examples with removeall \<font color="#2166ae">liststringfield\</font> has the value \["a","b","c","d","e","f"] running the code below 1 parseobject parseobject = new parseobject("datatypes"); 2 parseobject setobjectid(objectid); 3 parseobject removeall("liststringfield",arrays aslist("c", "d", "e", "f")); 4 parseobject save();1 val parseobject = parseobject("datatypes") 2 parseobject objectid = objectid 3 parseobject removeall("liststringfield", arrays aslist("c", "d", "e", "f")) 4 parseobject save() after this command the result of the \<font color="#2166ae">stringlist\</font> field will be \["a","b"] note that it is not currently possible to atomically add and remove items from an array in the same save we will have to call the save for every different array operation we want to perform separately 7 remove single field from parseobject you can delete a single field from an object by using the \<font color="#2166ae">remove\</font> operation 1 parseobject parseobject = new parseobject("datatypes"); 2 parseobject remove("stringfield"); 3 parseobject save();1 val parseobject = parseobject("datatypes") 2 parseobject remove("stringfield") 3 parseobject save() it’s done! at this point, we have learned \<font color="#2166ae">parse data types\</font> on \<font color="#2166ae">android\</font>