usePouchDB

usePouchDB

  • Docs
  • API
  • Help
  • GitHub

โ€บBasic Tutorial

Introduction

  • Quick Start
  • PouchDB and CouchDB

Basic Tutorial

  • Basic Tutorial: Intro
  • Setup
  • Add the Provider
  • Add Todos
  • List all Todos
  • Update docs
  • Syncing
  • Testing
  • More

API

  • Provider
  • usePouch
  • useDoc
  • useAllDocs
  • useFind
  • useView

Testing

Now that everything is working, let's make sure that it stays that way!

Packages to install

There are 3 packages I recommend you'll install:

  • pouchdb-adapter-memory
  • react-hooks-testing-library
  • React Testing Library (pre installed with Create-React-App)
npm
yarn
npm i -D pouchdb-adapter-memory @testing-library/react-hooks @testing-library/react
yarn add -D pouchdb-adapter-memory @testing-library/react-hooks @testing-library/react

pouchdb-adapter-memory

pouchdb-adapter-memory is a PouchDB Adapter. Adapters translate how your documents are stored and accessed. For example pouchdb-adapter-http (pre installed on most PouchDB setups) translates them into CouchDB's HTTP API.

But pouchdb-adapter-memory only stores them in memory. Perfect or testing!

react-hooks-testing-library

react-hooks-testing-library is a really good testing library, specialized in testing React Hooks.

The documentation for it can be found on https://react-hooks-testing-library.com/.

You can use it to test your own hooks. Be they extensions of hooks from usePouchDB or your own.

React Testing Library

React Testing Library comes pre-installed with create-react-app. It is a testing library that encourage you to test from the users perspective.

The documentation for it can be found at https://testing-library.com/docs/react-testing-library/intro.

Tests

Your tests should be closed systems. And no test before or after it should influence them. To achieve this I recommend that you create a new PouchDB database before each test. And that db should have the pouchdb-adapter-memory active.

// Using jest
import PouchDB from "pouchdb";
import memory from "pouchdb-adapter-memory";

// add the adapter to PouchDB
PouchDB.plugin(memory);

let myPouch = null;

beforeEach(() => {
  // before each test, create a new DB with the memory adapter.
  // nothing will be saved on disc!
  myPouch = new PouchDB("test", { adapter: "memory" });
});

afterEach(async () => {
  // Destroy the database after each test,
  // so that no data will be left from the previous test.
  await myPouch.destroy();
});

Also remember, that you must add all needed document before/during the test!

Components

All hooks must be in child components of <Provider />.

For React Testing Library you can warp your component with <Provider />:

import React from "react";
import { render } from "@testing-library/react";
import PouchDB from "pouchdb";
import memory from "pouchdb-adapter-memory";

import TodoList from "./TodoList";

PouchDB.plugin(memory);

let myPouch = null;

beforeEach(() => {
  myPouch = new PouchDB("test", { adapter: "memory" });
});

afterEach(async () => {
  await myPouch.destroy();
});

test("Test Component", async () => {
  // Add needed documents
  const putResult = await myPouch.bulkDocs([
    {
      _id: new Date(2020, 4, 30, 22, 03, 45, 0).toJSON(),
      type: "todo",
      text: "a todo",
      done: false,
    },
    {
      _id: new Date(2020, 4, 30, 21, 03, 45, 0).toJSON(),
      type: "todo",
      text: "moar todo",
      done: false,
    },
  ]);

  // Render the Component
  const { queryByByText } = render(
    <Provider pouchdb={db}>
      <TodoList />
    </Provider>,
  );

  const first = queryByByText("moar todo");
  expect(first).toBeTruthy();
  expect(first.nodeName).toBe("SPAN");
  expect(first.parentNode.nodeName).toBe("LI");
  expect(first.previousElementSibling.nodeName).toBe("INPUT");
  expect(first.previousElementSibling.nodeName.type).toBe("checkbox");

  const second = queryByByText("a todo");
  expect(second).toBeTruthy();
  expect(second.nodeName).toBe("SPAN");
  expect(second.parentNode.nodeName).toBe("LI");
  expect(second.previousElementSibling.nodeName).toBe("INPUT");
  expect(second.previousElementSibling.nodeName.type).toBe("checkbox");

  expect(second.parentNode.previousElementSibling).toBe(first.parentNode);
});

myPouch.bulkDocs is a method to create/update multiple docs in one go.

Hooks

To test hooks that depend on one of usePouchDB's hooks, you also must warp it in <Provider />.

react-hooks-testing-library's renderHook function can receive in the second argument a warper (documented here).

Let's test the addTodo from Add Todos extracted into a hook:

// hooks.js
import { useCallback } from "react";
import { usePouch } from "use-pouchdb";

// This hook returns a function, which we then call with the todo's text.
export function useAddDoc() {
  const db = usePouch();

  return useCallback(
    (text) => {
      const doc = {
        _id: new Date().toJSON(),
        type: "todo",
        text: text,
        done: false,
      };

      return db.put(doc);
    },
    [db],
  );
}
import React from "react";
import { renderHook } from "@testing-library/react-hooks";
import PouchDB from "pouchdb";
import memory from "pouchdb-adapter-memory";
import { Provider } from "use-pouchdb";

import { useAddDoc } from "./hooks";

PouchDB.plugin(memory);

let myPouch = null;

beforeEach(() => {
  myPouch = new PouchDB("test", { adapter: "memory" });
});

afterEach(async () => {
  await myPouch.destroy();
});

test("add document", async () => {
  const wrapper = ({ children }) => (
    <Provider pouchdb={myPouch}>{children}</Provider>
  );
  const { result } = renderHook(() => useAddDoc(), {
    wrapper,
  });

  expect(typeof result.current).toBe("function");

  await result.current("test todo");

  const { rows } = await myPouch.allDocs({ include_docs: true });
  expect(rows).toHaveLength(1);
  expect(rows[0]).toEqual({
    _id: expect.any(String),
    _rev: expect.any(String),
    type: "todo",
    text: "test todo",
    done: false,
  });
});

Now we are finished with our Todo example. All Todos are replicated, users can sign up and log in. I know, this was a long tutorial, but we did cover a lot!

Happy coding! ๐ŸŽ‰๐ŸŽŠ

โ† SyncingMore โ†’
  • Packages to install
    • pouchdb-adapter-memory
    • react-hooks-testing-library
    • React Testing Library
  • Tests
    • Components
    • Hooks
usePouchDB
Docs
Getting StartedAPI Reference
Contact
BlogGitHubStar
Impressum
Copyright ยฉ 2025 Christopher Astfalk