Moor: Enhanced Offline Storage for Flutter

Suravi Rout
Mindful Engineering
4 min readAug 16, 2021
Photo by Tobias Fischer on Unsplash

The title sums it up Entirely 😎

But that is not why we are here, isn’t it? While developing any applications, there comes a time when we find ourselves with the need to save data within the application itself. At that point, we introduce a database in the development of the application.

Moor is a library for Flutter that allows us to work with Flutter’s SQLite database easily and in Dart only. Moor itself uses SQL as its backbone, so in flutter we will have both options, We can write query or directly create a Table using Dart.

Key Features

  • Moor allows us to write queries in both Dart and SQL
  • Moor provides Tables, queries, migration, IDE for SQL, and complex features like WITH and WINDOW clauses
  • Moor help us to keep the code boilerplate-free
  • Identify or catches the error and provides the solution
  • Moor helps us keep our database code simple and easy to understand
  • Moor is fast like FLUTTER and supports multiple isolates
  • Moor can be used in cross-platform, works on iOS, Android, Linux, macOS, Windows and on the web
  • Each component of moor is verified by a wide range of unit and integration tests. It powers up many Flutter apps in production.

Adding dependency to Project

The first step to using Moor in our projects is to install a series of dependencies.

dependencies:
get_it:
moor_flutter:
path_provider:
sqlite3_flutter_libs:

dev_dependencies:
moor_generator:
build_runner:

Here’s a quick overview on uses of each package:

  • moor_flutter: This is the core package defining most apis
  • sqlite3_flutter_libs: Ships the latest sqlite3 version with your Android or iOS app.
  • path_provider: Used to find a suitable location to store the database in our device.
  • get_it: This is a service provider and will help us to establish the AppDatabase class as a singleton, It will help us access the instance from anywhere in our app.
  • moor_generator: Generates query code based on tables of database
  • build_runner: This library is used to generate the database files in Dart language

Creating a Table

The main advantage of Moor is that, when creating a table we can do it directly in Dart, just by extending our dart class with Table. Moor uses this Table and database class to create a Database.

We will create a class named as Users(users.dart), which extends from the Table class.

The Users class will be our table in the database and the id parameter becomes the primaryKey of the table since it is autoIncrement(). While the properties defined as getters will be the columns for the table.

Moor accepts the following types of data:

Database creation

Next, we have to create the Database. By the following code we can create db.sqlite file which will save the data in the application’s sandbox and run the application by calling the AppDatabase(openConnection()).

After creating the Database class, now we need to generate the database_manager.g.dart file. So we have to run the below command in the terminal.

flutter packages pub run build_runner build

Lets add the queries now

Now we can add the queries that will allow us to insert, delete and update those users from the database.
Let’s add those queries to the AppDatabase class we created earlier.

We can create select statements using select query that starts with select(tableName). Any query can be run with get() or else we can update our user list used in UI by auto updating stream using watch().

We also can insert, delete and update the data using insert(), delete() and replace() respectively.

Lets jump to the UI part now

To make the AppDatabase singleton, we have already added the get_it library which is a service provider. Now, create a file named as service_locator.dart to add the following singleton code.

We will call this setupLocator() inside our main() method. It will register the database service before the app starts. Next we need to bind this singleton class with our UI.

So now, as per our above example, we can consider a demo app of user list where user having name, email and the id as a primary key. Now, let’s add the user, that will be stored in our db and after a successful insertion our list will be updated automatically as we are using watch() and we can also update and remove the user from our db.

For deep dive into the code you can refer this repo on GitHub.

I have tried to keep it short & simple for explaining the core things. If you have any questions, feel free to ask in the comments and stay connected for more exciting blogs.

Please don’t forget to clap 👏 , if you find this article helpful.

Thank you 😇

Photo by Hanny Naibaho on Unsplash

--

--