Skip to main content

Introduction to Dexie.js

· 4 min read

Dexie.js is a minimalistic wrapper for IndexedDB, which is a low-level API for client-side storage of significant amounts of structured data, including files/blobs. This wrapper aims to provide a simpler and more concise API for working with IndexedDB, which is known for its complexity and verbosity.

Here are some key points about Dexie.js:

  • Size: Dexie.js is quite small, being only ~25k minified and gzipped.
  • Reactive: From version 3.2, Dexie integrates better with front-end frameworks, allowing you to query the database without boilerplate and let your components mirror the database in real time.
  • Ease of Learning: Dexie.js is designed to be straightforward and easy to learn, especially for those who have worked with native IndexedDB and appreciate a more concise API.
  • Documentation: The tool is well-documented, with examples to help developers get started.

Basic Examples

Here are some code examples provided on the Dexie.js website:

Declaring a Database

const db = new Dexie('MyDatabase');

// Declare tables, IDs, and indexes
db.version(1).stores({
friends: '++id, name, age'
});

Running Queries

// Find some old friends
const oldFriends = await db.friends
.where('age').above(75)
.toArray();

// Or make a new one
await db.friends.add({
name: 'Camilla',
age: 25,
street: 'East 13:th Street',
picture: await getBlob('camilla.png')
});

Live Queries in Different Frameworks

Dexie.js provides examples of how to use live queries with various front-end frameworks:

React

Here is a ReactJS example

import { useLiveQuery } from "dexie-react-hooks";
import { db } from "./db";

export function FriendList () {
const friends = useLiveQuery(async () => {
return await db.friends
.where("age")
.between(18, 65)
.toArray();
});

return (
<>
<h2>Friends</h2>
<ul>
{friends?.map(friend =>
<li key={friend.id}>
{friend.name}, {friend.age}
</li>
)}
</ul>
</>
);
}

Svelte

Here is a Svelte example:

<script>
import { liveQuery } from "dexie";
import { db } from "./db";

let friends = liveQuery(async () => {
return await db.friends
.where("age")
.between(18, 65)
.toArray();
});
</script>

<div>
<h2>Friends</h2>
<ul>
{#each ($friends || []) as friend (friend.id)}
<li>{friend.name}, {friend.age}</li>
{/each}
</ul>
</div>

Vue

<template>
<h2>Friends</h2>
<ul>
<li v-for="friend in friends" :key="friend.id">
{{ friend.name }}, {{ friend.age }}
</li>
</ul>
</template>
<script>
import { liveQuery } from "dexie";
import { db } from "../db";
import { useObservable } from "@vueuse/rxjs";

export default {
name: "FriendList",
setup() {
return {
friends: useObservable(
liveQuery(async () => {
return await db.friends
.where("age")
.between(18, 65)
.toArray();
})
)
};
}
};
</script>

Angular

Here is an Angular example:

import { Component } from '@angular/core';
import { liveQuery } from 'dexie';
import { db } from '../db';

@Component({
selector: 'friendlist',
template: `
<h2>Friends</h2>
<ul>
<li *ngFor="let friend of friends$ | async">
{{ friend.name }}, {{ friend.age }}
</li>
</ul>
`
})
export class FriendsComponent {
friends$ = liveQuery(() => listFriends());
}

async function listFriends() {
return await db.friends
.where("age")
.between(18, 65)
.toArray();
}

Syncing with the Cloud

Dexie.js also offers a way to sync your IndexedDB with the cloud:

// Create your db in the cloud
npx dexie-cloud create

// Whitelist your app origin(s)
npx dexie-cloud whitelist http://localhost:3000

// Add dexie-cloud-addon
npm install dexie-cloud-addon

// Update your DB declaration
import Dexie from "dexie";
import dexieCloud from "dexie-cloud-addon";

const db = new Dexie('MySyncedDB', {addons: [dexieCloud]});

db.version(1).stores({
friends: '@id, name, age'
});

db.cloud.configure({
databaseUrl: "https://<yourdatabase>.dexie.cloud",
requireAuth: true
});

For more detailed information and examples, you can check out the Dexie.js documentation at https://dexie.org/docs.