Reader small image

You're reading from  Android Studio 4.1 Development Essentials – Java Edition

Product typeBook
Published inMay 2021
PublisherPackt
ISBN-139781801815161
Edition1st Edition
Right arrow
Author (1)
Neil Smyth
Neil Smyth
author image
Neil Smyth

Neil Smyth has over 25 years of experience in the IT industry, including roles in software development and enterprise-level UNIX and Linux system administration. In addition to a bachelor’s degree in information technology, he also holds A+, Security+, Network+, Project+, and Microsoft Certified Professional certifications and is a CIW Database Design Specialist. Neil is the co-founder and CEO of Payload Media, Inc. (a technical content publishing company), and the author of the Essentials range of programming and system administration books.
Read more about Neil Smyth

Right arrow

68. An Android Room Database and Repository Tutorial

This chapter will combine the knowledge gained in the chapter entitled “The Android Room Persistence Library” with the initial project created in the previous chapter to provide a detailed tutorial demonstrating how to implement SQLite-based database storage using the Room persistence library. In keeping with the Android architectural guidelines, the project will make use of a view model and repository. The tutorial will make use of all of the elements covered in “The Android Room Persistence Library” including entities, a Data Access Object, a Room Databases and asynchronous database queries.

68.1 About the RoomDemo Project

The user interface layout created in the previous chapter was the first step in creating a rudimentary inventory app designed to store the names and quantities of products. When completed, the app will provide the ability to add, delete and search for database entries while also displaying a scrollable list of all products currently stored in the database. This product list will update automatically as database entries are added or deleted.

68.2 Modifying the Build Configuration

Begin by launching Android Studio and opening the RoomDemo project started in the previous chapter. Before adding any new classes to the project, the first step is to add some additional libraries to the build configuration, including the Room persistence library. Locate and edit the module level build.gradle file (app -> Gradle Scripts -> build.gradle (Module: RoomDemo.app)) and modify it as follows:

dependencies {

.

.

    implementation "androidx.recyclerview:recyclerview:1.1.0"

    implementation "androidx.room:room-runtime:2.2.5"

    implementation "androidx.fragment:fragment-ktx:1.2.5"

    annotationProcessor "androidx.room:room-compiler:2.2.5"

.

.

}

68.3 Building the Entity

This project will begin by creating the entity which defines the schema for the database table. The entity will consist of an integer for the product id, a string column to hold the product name and another integer value to store the quantity. The product id column will serve as the primary key and will be auto-generated. Table 68-3 summarizes the structure of the entity:

Column

Data Type

productid

Integer / Primary Key / Auto Increment

productname

String

productquantity

Integer

Table 68-3

Add a class file for the entity by right clicking on the app -> java -> com.ebookfrenzy.roomdemo entry in the Project tool window and selecting the New -> Java Class menu option. In the new class dialog...

68.4 Creating the Data Access Object

With the product entity defined, the next step is to create the DAO interface. Referring once again to the Project tool window, right-click on the app -> java -> com.ebookfrenzy.roomdemo entry and select the New -> Java Class menu option. In the new class dialog, enter ProductDao into the Name field and select Interface from the list as highlighted in Figure 68-1:

Figure 68-1

Click on OK to generate the new interface and, with the ProductDao.java file loaded into the code editor, make the following changes:

package com.ebookfrenzy.roomdemo;

 

import androidx.lifecycle.LiveData;

import androidx.room.Dao;

import androidx.room.Insert;

import androidx.room.Query;

 

import java.util.List;

 

@Dao

public interface ProductDao {

 

    @Insert

    void insertProduct(Product product);

 

    @Query("SELECT...

68.5 Adding the Room Database

The last task before adding the repository to the project is to implement the Room Database instance. Add a new class to the project named ProductRoomDatabase, this time with the Class option selected.

Once the file has been generated, modify it as follows using the steps outlined in the “The Android Room Persistence Library” chapter:

package com.ebookfrenzy.roomdemo;

 

import android.content.Context;

 

import androidx.room.Database;

import androidx.room.Room;

import androidx.room.RoomDatabase;

 

@Database(entities = {Product.class}, version = 1)

public abstract class ProductRoomDatabase extends RoomDatabase {

 

    public abstract ProductDao productDao();

    private static ProductRoomDatabase INSTANCE;

 

    static ProductRoomDatabase getDatabase(final Context context) {

     &...

68.6 Adding the Repository

Add a new class named ProductRepository to the project, with the Class option selected.

The repository class will be responsible for interacting with the Room database on behalf of the ViewModel and will need to provide methods that use the DAO to insert, delete and query product records. With the exception of the getAllProducts() DAO method (which returns a LiveData object) these database operations will need to be performed on separate threads from the main thread using the AsyncTask class.

Remaining within the ProductRepository.java file, add the code for the search AsyncTask. Also add a method named asyncFinished() which will be called by the query AsyncTask to return the search results to the repository thread:

package com.ebookfrenzy.roomdemo;

 

import android.os.AsyncTask;

import androidx.lifecycle.MutableLiveData;

import java.util.List;

 

public class ProductRepository {

 

    private...

68.7 Modifying the ViewModel

The ViewModel is responsible for creating an instance of the repository and for providing methods and LiveData objects that can be utilized by the UI controller to keep the user interface synchronized with the underlying database. As implemented in ProductRepository.java, the repository constructor requires access to the application context in order to be able to get a Room Database instance. To make the application context accessible within the ViewModel so that it can be passed to the repository, the ViewModel needs to subclass AndroidViewModel instead of ViewModel. Begin, therefore, by editing the MainViewModel.java file (located in the Project tool window under app -> java -> com.ebookfrenzy.roomdemo -> ui.main) and changing the class to extend AndroidViewModel and to implement the default constructor:

package com.ebookfrenzy.roomdemo.ui.main;

 

import android.app.Application;

import androidx.lifecycle.AndroidViewModel;

...

68.8 Creating the Product Item Layout

The name of each product in the database will appear within the RecyclerView list in the main user interface. This will require a layout resource file containing a TextView to be used for each row in the list. Add this file now by right-clicking on the app -> res -> layout entry in the Project tool window and selecting the New -> Layout resource file menu option. Name the file product_list_item and change the root element to LinearLayout before clicking on OK to create the file and load it into the layout editor. With the layout editor in Design mode, drag a TextView object from the palette onto the layout where it will appear by default at the top of the layout:

Figure 68-2

With the TextView selected in the layout, use the Attributes tool window to set the ID of the view to product_row and the layout_height to 30dp. Select the LinearLayout entry in the Component Tree window and set the layout_height attribute to wrap_content...

68.9 Adding the RecyclerView Adapter

As outlined in detail in the chapter entitled “Working with the RecyclerView and CardView Widgets”, a RecyclerView instance requires an adapter class to provide the data to be displayed. Add this class now by right clicking on the app -> java -> com.ebookfrenzy.roomdemo -> ui.main entry in the Project tool window and selecting the New -> Java Class... menu. In the dialog, name the class ProductListAdapter. With the resulting ProductListAdapter.java class loaded into the editor, implement the class as follows:

package com.ebookfrenzy.roomdemo.ui.main;

 

import android.view.LayoutInflater;

import android.view.View;

import android.view.ViewGroup;

import android.widget.TextView;

import com.ebookfrenzy.roomdemo.R;

import androidx.recyclerview.widget.RecyclerView;

import androidx.annotation.NonNull;

import com.ebookfrenzy.roomdemo.Product;

 

import java.util.List;

 

public...

68.10 Preparing the Main Fragment

The last remaining component to modify is the MainFragment class which needs to configure listeners on the Button views and observers on the live data objects located in the ViewModel class. Before adding this code, some preparation work needs to be performed to add some imports, variables and to obtain references to view ids. Edit the MainFragment.java file and modify it as follows:

.

.

import android.widget.EditText;

import android.widget.TextView;

import com.ebookfrenzy.roomdemo.ProductListAdapter;

.

.

public class MainFragment extends Fragment {

 

    private MainViewModel mViewModel;

 private ProductListAdapter adapter;

 

    private TextView productId;

    private EditText productName;

    private EditText productQuantity;

.

.

   @Override

    public void...

68.11 Adding the Button Listeners

The user interface layout for the main fragment contains three buttons each of which needs to perform a specific task when clicked by user. Edit the MainFragment.java file and add the listenerSetup() method:

.

.

import android.widget.Button;

 

import com.ebookfrenzy.roomdemo.Product;

.

.

    private void listenerSetup() {

 

        Button addButton = getView().findViewById(R.id.addButton);

        Button findButton = getView().findViewById(R.id.findButton);

        Button deleteButton = getView().findViewById(R.id.deleteButton);

 

        addButton.setOnClickListener(new View.OnClickListener() {

            @Override

      ...

68.12 Adding LiveData Observers

The user interface now needs to add observers to remain synchronized with the searchResults and allProducts live data objects within the ViewModel. Remaining in the Mainfragment.java file, implement the observer setup method as follows:

.

.

import androidx.lifecycle.Observer;

.

.

import java.util.List;

import java.util.Locale;

.

.

   private void observerSetup() {

 

        mViewModel.getAllProducts().observe(getViewLifecycleOwner(),

                              new Observer<List<Product>>() {

            @Override

            public void onChanged(@Nullable final List...

68.13 Initializing the RecyclerView

Add the final setup method to initialize and configure the RecyclerView and adapter as follows:

.

.

import androidx.recyclerview.widget.LinearLayoutManager;

import androidx.recyclerview.widget.RecyclerView;

.

.

    private void recyclerSetup() {

 

        RecyclerView recyclerView;

 

        adapter = new ProductListAdapter(R.layout.product_list_item);

        recyclerView = getView().findViewById(R.id.product_recycler);

        recyclerView.setLayoutManager(new LinearLayoutManager(getContext()));

        recyclerView.setAdapter(adapter);

    }

.

.

}

68.14 Testing the RoomDemo App

Compile and run the app on a device or emulator, add some products and make sure that they appear automatically in the RecyclerView. Perform a search for an existing product and verify that the product ID and quantity fields update accordingly. Finally, enter the name for an existing product, delete it from the database and confirm that it is removed from the RecyclerView product list.

68.15 Using the Database Inspector

As previously outlined in “The Android Room Persistence Library”, the Database Inspector tool window may be used to inspect the content of Room databases associated with a running app and to perform minor data changes. After adding some database records using the RoomDemo app, display the Database Inspector tool window using the tab button indicated in Figure 68-3:

Figure 68-3

From within the inspector window, select the running app from the menu marked A in Figure 68-4 below:

Figure 68-4

From the Databases panel (B) double-click on the products table to view the table rows currently stored in the database. Enable the Live updates option (C) and then use the running app to add more records to the database. Note that the Database Inspector updates the table data (D) in real-time to reflect the changes.

Turn off Live updates so that the table is no longer read only, double-click on the quantity cell for a table row...

68.16 Summary

This chapter has demonstrated the use of the Room persistence library to store data in a SQLite database. The finished project made use of a repository to separate the ViewModel from all database operations and demonstrated the creation of entities, a DAO and a room database instance, including the use of asynchronous tasks when performing some database operations.

lock icon
The rest of the chapter is locked
You have been reading a chapter from
Android Studio 4.1 Development Essentials – Java Edition
Published in: May 2021Publisher: PacktISBN-13: 9781801815161
Register for a free Packt account to unlock a world of extra content!
A free Packt account unlocks extra newsletters, articles, discounted offers, and much more. Start advancing your knowledge today.
undefined
Unlock this book and the full library FREE for 7 days
Get unlimited access to 7000+ expert-authored eBooks and videos courses covering every tech area you can think of
Renews at £13.99/month. Cancel anytime

Author (1)

author image
Neil Smyth

Neil Smyth has over 25 years of experience in the IT industry, including roles in software development and enterprise-level UNIX and Linux system administration. In addition to a bachelor’s degree in information technology, he also holds A+, Security+, Network+, Project+, and Microsoft Certified Professional certifications and is a CIW Database Design Specialist. Neil is the co-founder and CEO of Payload Media, Inc. (a technical content publishing company), and the author of the Essentials range of programming and system administration books.
Read more about Neil Smyth