Skip to content

Getting Started

s edited this page Aug 3, 2026 · 3 revisions

Getting Started

This page assumes that your Supernote plugin already builds and runs. Supernote Module Generator does not create the plugin itself; it adds a native module to the plugin you already have.

Install the generator

Python 3.9 or newer is required.

python3 -m pip install supernote-module-generator

Confirm that the command is available:

supernote-module --version

The wiki follows the current default branch and may describe changes that are newer than the version you have installed. When something does not match, use the help included with your installed version:

supernote-module --help
supernote-module help add

Run it from the plugin root

Run the generator from the root of the existing plugin, not from android/ or another subdirectory.

The generator expects to find:

PluginConfig.json
package.json
android/
android/settings.gradle

android/settings.gradle.kts is also supported.

The generator does not search parent directories. If it says that the current directory is not a Supernote plugin, check where you are before changing anything else.

Choose a module type

The full explanation is on the Home page, but the practical choice is:

  • Choose Native Module when you want Kotlin or Java, need Android APIs, or want to use a Kotlin or Java library.
  • Choose Native JNI Module when you need C or C++ but still want a normal Promise-based JavaScript API and Android integration.
  • Choose JSI Module only when JavaScript genuinely needs a direct synchronous C++ API and you have confirmed that the target PluginHost can run it.

When you are unsure between JNI and JSI, choose JNI.

Run Doctor

Doctor checks the requirements for the module type you are about to generate without changing your plugin.

supernote-module doctor --type native
supernote-module doctor --type jni
supernote-module doctor --type jsi

A Native Module needs the normal Android and Java build environment. JNI and JSI additionally need CMake 3.22.1 or newer and an Android NDK whose Clang compiler supports the generated C23 and C++23 code for arm64-v8a.

Running Doctor without --type checks all three module types:

supernote-module doctor

That is useful when setting up a development machine, but it may report missing C/C++ tools even when you only intend to create a Native Module.

Doctor can check whether a JSI module can be generated and compiled. It cannot prove that the target PluginHost, firmware, linker namespace, and SELinux policy will allow the generated library to execute. That has to be tested on the actual target environment.

Generate a module

For the guided interface, run:

supernote-module

Choose Add module, then choose the module type.

The generator will ask for:

Question Example What it controls
Package name local-math Folder below local_modules/, dependency name, and JavaScript import string
Description Leave empty Optional package description
JavaScript name Math The object imported and called by JavaScript or TypeScript
Android namespace com.example.math Kotlin/Java namespace and generated Android paths
Package version 0.1.0 Version stored in the local package
Install now Yes Adds and installs the local file: dependency using npm or Yarn

The package name, JavaScript name, and Android namespace must be unique inside the plugin. They cannot be renamed later with Update, so choose names you are willing to keep.

For scripts or repeatable commands, the same module can be generated without the menu:

supernote-module add local-math --type native --yes

Use --type jni or --type jsi for the other module types.

If both package-lock.json and yarn.lock exist, the generator will not guess which package manager is correct. Specify one explicitly:

supernote-module add local-math --type native --package-manager npm --yes

What gets added

The generated package is placed below:

local_modules/<package-name>/

The generator also adds a local dependency to the plugin's package.json and creates the React Native and Android integration required for that module type.

The files you are meant to edit depend on the module type:

Module type Implementation files
Native Module android/src/main/java/<namespace-path>/
Native JNI Module android/src/main/cpp/
JSI Module android/src/main/cpp/

These paths are inside the generated package. The individual module pages explain which files are generated, which files are safe to edit, and how functions are exported.

Validate the module

After generation, or after changing exported functions, run:

supernote-module validate local-math --build

Without --build, Validate checks the generated files, metadata, package link, and exports. With --build, it also compiles the generated Android integration through the existing plugin project.

Add --verbose when a build fails:

supernote-module validate local-math --build --verbose

Validation can confirm that a JSI module compiles, but it still cannot guarantee that PluginHost will execute the resulting library.

Import the module

Every generated package has one default export. The import name is the package name and the object name is the JavaScript name selected during generation.

For Native and JNI modules:

import Math from 'local-math';

const total = await Math.add(20, 22);

For JSI modules:

import Math from 'local-math';

const total = Math.add(20, 22);

The module pages explain the supported function signatures and the difference between Promise-based and synchronous calls.

Update, validate, and remove

The main commands are:

supernote-module update local-math
supernote-module validate local-math --build
supernote-module remove local-math

Commit your plugin before running Update or Remove.

Update refreshes files owned by the generator while preserving the implementation roots described on the relevant module page. It does not provide a dry run or a file-by-file diff.

Remove deletes the complete generated package, including your implementation source. Interactive removal requires typing the exact package name.

If an operation is interrupted, run the generator again before manually deleting its recovery file. The generator will try to recover the previous transaction. Exit code 3 means that manual recovery is still required.

Continue with the module page