Elijah Asaolu I am a programmer, I have a life.

Using TinyBase for reactive state management

4 min read 1396

Using TinyBase For Reactive State Management

Introducing TinyBase

TinyBase is a new state management library that provides a more structured, SQL-like approach to data manipulation. This new library provides a straightforward syntax for incorporating state management into your application, and its npm library uses no dependencies.

In this tutorial, we’ll walk you through the fundamentals of getting started with TinyBase. Note that TinyBase is a new project that hasn’t withstood critical production environments, so this walkthrough is experimental.

First, however, let’s look at what sets TinyBase apart from other state management libraries.

Features of TinyBase

Before now, we had a variety of state management libraries, each with its own set of functionalities. On top of that, we had other libraries that extended the features of previous ones. Here are some of TinyBase’s advantages over the competition:

  • Familiar, SQL-like concept — If you have prior experience working with SQL, getting started with TinyBase would be a breeze because it has a familiar SQL syntax and its own concept of tables, rows, and cells
  • Persistent data — TinyBase also offers an integrated module for persisting data to various browser storage mediums such as localStorage, sessionStorage, and even the ability to specify a custom storage medium
  • Event listeners — You can also register listeners for storing data with TinyBase so that when any changes are made to these data, your desired function is called. Hence, TinyBase is reactive!
  • Data schema — You can use schemas to ensure that the value entries in a store always match what you anticipate. For each defined schema, you may additionally set a default type

Installation

You can easily download the TinyBase core file or copy and paste its CDN link into your application:

<html>
  <head>
    <title>TinyBase App</title>
    <script src="https://unpkg.com/tinybase/lib/umd/tinybase.js"></script>
  </head>
  <body>
    ...
  </body>
</html>

Or install via npm:

npm install tinybase

If you are using TinyBase via CDN, we’ll need an additional event listener to check for when the TinyBase object is available. This would require us to update our previous example like below:

<html>
  <head>
    <title>TinyBase App</title>
    <script src="https://unpkg.com/tinybase/lib/umd/tinybase.js"></script>
    <script>
      addEventListener('load', () => {
        const { createStore } = TinyBase;
      });
    </script>
  </head>
  <body>
      ...
  </body>
</html>

And, assuming you installed the package with npm, we can use ES6 import to include its main function in our application:

import { createStore } from "tinybase";

Core concepts

Store

The store is TinyBase’s primary location for storing tabular data. Using the createStore() function, we can easily create one like below:

import { createStore } from "tinybase";
const store = createStore()

From here, we can define our table(s), add data change listeners, persist store data to browser storage, and so on.



Every TinyBase store has a simple hierarchical structure:

  • Each store has a defined number of tables
  • Each table has a set number of rows
  • Each row has a certain amount of cells

Tables

A table is used to organize data in the form of rows and cells and is used for both storing and displaying records in the structure format.

Apart from the table listeners, TinyBase lets us perform three basic operations (set, get, and delete) on a table.

Creating tables

TinyBase has two ways for creating tables: the setTable() method for creating a single table and the setTables() method for creating one or more tables:

const store = createStore();

// Create single table
store.setTable("users", {
  1: {
    name: "John Doe",
    age: 12,
    isVerified: true,
  },
});

// Create multiple tables

store.setTables({
  users: {
    1: {
      name: "John Doe",
      age: 12,
      isVerified: true,
    },
  },
  posts: {
    1: {
      title: "Hello World",
      body: "Hello World",
    },
  },
// ...
});

The example above shows how to utilize both the setTable() and setTables() methods. The first example involves the creation of a table called users, with a single row containing dummy user information. In the second example, two tables are created: users and posts.

Get tables

The getTable() and getTables() methods are used to access specific table information or all of the tables available in a store. The first would necessitate specifying the name of the table whose data we wish to retrieve:

// This function returns all tables.
console.log(store.getTables());

// Returns only the table 'users'.
console.log(store.getTable("users"));

Delete tables

TinyBase additionally has two ways of deleting tables, one for deleting a specific table and the other for deleting all tables in a store:

// Delete table 'posts'
store.delTable("posts");

// Delete all tables in the store.
store.delTables();

Rows

A row in this context represents a single, implicitly organized data item in a table, just as it does in a database setting. And with rows, we can do the following:

  • setRow() — This method accepts three parameters: the table identifier, the new row name, and an object containing the new row data. Additionally, if the table doesn’t already exist in the store, this method will create a new one:
    store.setRow("users", 2, {
      name: "Jane Doe",
      age: 15,
      isVerified: true,
    });
  • getRow() — Use this to obtain the object containing all of the data from a single row. This method takes two parameters, which are the table name from which the row should be retrieved and the row identifier:
    console.log(store.getRow("users", "1"));
    // returns - { name: 'John Doe', age: 12, isVerified: true }
  • delRow() — Used to delete a single row from a table, given the table and row id:
    store.delRow("users", 2);
    // Deletes row '2' from 'users' table

Cells

TinyBase has comparable functions for setting and retrieving cells:

  • setCell() — If the specified cell identifier already exists, this function will update it, else it will append the row with this new cell:
    // Will update table 'users' row '1' name with James Doe
    store.setCell("users", "1", "name", "James Doe");
    
    // Will append table 'users' row '1' with a new cell 'address'
    store.setCell("users", "1", "address", "North Pole");
  • getCell() — Given the table and row identifiers, this function returns an object containing the value of a single cell:
    store.getCell("users", "1", "address");
    // returns - North Pole
  • delCell() — Given its table, row, and cell identities, remove a single cell from a row:
    // Removes the address cell from row '1' in 'users' table store.
    delCell("users", "1", "address");

Listeners

TinyBase also provides the ability to add listeners to tables, rows, and cells. These listeners are used to detect data changes and take appropriate actions in response.


More great articles from LogRocket:


For example, to listen to data changes in a table, given the table id, we have:

const listenerId = store.addTableListener("users", () => {
  console.log("users table changed");
});

As a result, if data in this table changes, we’ll get the message “users table updated” in our console.

We can also add listeners to specific rows in a table:

const listenerId = store.addRowListener("users", "1", () => {
  console.log("Row '1' in table 'users' had changed");
});

There are over ten listener methods in the library, and going through them all one by one in this post would be tedious. For reference, all the methods can be found here.

Persist data

TinyBase also provides a persister module, which allows you to save and load store data to and from various locations, such as the browser’s localStorage and sessionStorage, so that these data can be saved between browser sessions or reloads.

To persist data to the browser’s storage, we have the createLocalPersister and createSessionPersister methods:

const { createStore, createLocalPersister } = TinyBase;
const store = createStore();

store.setTables({
  users: {
    1: {
      name: "John Doe",
      age: 12,
      isVerified: true,
    },
   // ...
  },
});

const persister = createLocalPersister(store, "users");
persister.save();

And we will be able to access and even save new data to our store via localStorage:

// Get store data from localStorage
console.log(localStorage.users)
// returns - {"users":{"1":{"name":"John Doe","age":12,...
// Add new data to store data directly from localStorage
localStorage.setItem("users", '{"users":{"3":{"name":"Random User"}}}');

Conclusion

TinyBase is still in its early stages, but it has a lot of amazing capabilities already. There are certain drawbacks.

For example, the way one or more functions can execute the same operation arbitrarily, like the way you can create a table or row using the setCell() method, but then, this is understandable.

Furthermore, there is still a lot of opportunity for expansion in the library. If you’re curious about what else TinyBase can do, check out its demo applications.

Full visibility into production React apps

Debugging React applications can be difficult, especially when users experience issues that are hard to reproduce. If you’re interested in monitoring and tracking Redux state, automatically surfacing JavaScript errors, and tracking slow network requests and component load time, try LogRocket.

LogRocket is like a DVR for web and mobile apps, recording literally everything that happens on your React app. Instead of guessing why problems happen, you can aggregate and report on what state your application was in when an issue occurred. LogRocket also monitors your app's performance, reporting with metrics like client CPU load, client memory usage, and more.

The LogRocket Redux middleware package adds an extra layer of visibility into your user sessions. LogRocket logs all actions and state from your Redux stores.

Modernize how you debug your React apps — .

Elijah Asaolu I am a programmer, I have a life.

Leave a Reply