Uncaught TypeError: promisify is not a function (Electron-Vite & React)
Error displays when running my app (browser & desktop). I've seen this error be asked about before and it doesn't seem to be an issue with better-sqlite3, though I still don't have a solution. I want to create a local database for handling users.
Node: v22.20.0 OS: Debian GNU/Linux 13 (trixie)
package.json
{
"name": "amas-monitor",
"version": "1.0.0",
"type": "module",
"description": "",
"main": "./out/main/index.js",
"author": "",
"homepage": "",
"scripts": {
"format": "prettier --write .",
"lint": "eslint --cache .",
"start": "electron-vite preview",
"dev": "electron-vite dev",
"build": "electron-vite build",
"rebuild": "electron-rebuild -f -w better-sqlite3",
"postinstall": "electron-builder install-app-deps",
"build:unpack": "npm run build && electron-builder --dir",
"build:win": "npm run build && electron-builder --win",
"build:mac": "npm run build && electron-builder --mac",
"build:linux": "npm run build && electron-builder --linux"
},
"dependencies": {
"@electron-toolkit/preload": "^3.0.2",
"@electron-toolkit/utils": "^4.0.0",
"@influxdata/influxdb-client": "^1.35.0",
"@vnedyalk0v/react19-simple-maps": "^1.2.0",
"argon2": "^0.44.0",
"better-sqlite3": "^12.4.1",
"chart.js": "^4.5.1",
"chartjs-adapter-date-fns": "^3.0.0",
"chartjs-plugin-datalabels": "^2.2.0",
"cors": "^2.8.5",
"electron-updater": "^6.3.9",
"express": "^5.1.0",
"ffmpeg": "^0.0.4",
"leaflet": "^1.9.4",
"prop-types": "^15.8.1",
"react-chartjs-2": "^5.3.0",
"react-icons": "^5.5.0",
"react-leaflet": "^5.0.0",
"react-notifications": "^1.7.4",
"react-router-dom": "^7.9.5",
"sqlite3": "^5.1.7"
},
"devDependencies": {
"@electron-toolkit/eslint-config": "^2.1.0",
"@electron-toolkit/eslint-config-prettier": "^3.0.0",
"@vitejs/plugin-react": "^5.0.3",
"electron": "^38.4.0",
"electron-builder": "^25.1.8",
"electron-rebuild": "^3.2.9",
"electron-vite": "^4.0.1",
"eslint": "^9.36.0",
"eslint-plugin-react": "^7.37.5",
"eslint-plugin-react-hooks": "^5.2.0",
"eslint-plugin-react-refresh": "^0.4.20",
"prettier": "^3.6.2",
"react": "^19.2.0",
"react-dom": "^19.1.1",
"vite": "^7.1.10"
}
}
users.js
import Database from 'better-sqlite3'
import argon2 from 'argon2'
const db = new Database('users.db')
db.pragma('journal_mode = WAL')
export const seedUsers = [
{
email: '[email protected]',
password: 'admin',
role: 'admin'
},
{
email: '[email protected]',
password: 'technician',
role: 'technician'
},
{
email: '[email protected]',
password: 'operator',
role: 'operator'
}
]
export async function initUserDatabase() {
db.exec(`
CREATE TABLE IF NOT EXISTS users (
id INTEGER PRIMARY KEY,
email TEXT UNIQUE NOT NULL,
password_hash TEXT NOT NULL,
role TEXT NOT NULL
);
`)
const count = db.prepare('SELECT COUNT(*) as n FROM users').get().n
if (count === 0) {
console.log('[db] seeding default users…')
const insert = db.prepare(`
INSERT INTO users (email, password_hash, role)
VALUES (@email, @password_hash, @role)
`)
for (const u of seedUsers) {
const hash = await argon2.hash(u.password)
insert.run({
email: u.email,
password_hash: hash,
role: u.role
})
}
}
console.log('[db] users ready')
}
console error
There might be some issue with the bundling.
The only part, where promisify is used, is the import within backup.js: https://github.com/WiseLibs/better-sqlite3/blob/ea0d8c73615ce2b6133df67da10c7e6452115d73/lib/methods/backup.js#L3-L5
Maybe this should be switched to explicitly import node:util instead. You could either try that within your project, or declare better-sqlite3 as a external module to exclude it from the bundling process and load it as "normal" module instead.
Do you try to use better-sqlite3 in the browser/frontend side? i guess it is meant to be used in node or compatible contexts only
checkout electron setup, how to use node stuff in render processes,
e.g. enable node integration for that windows (not recommended), or better create preload scripts where you define explicit functions exposing to the render process.
in your example i would create start and seed the db somewhere on app startup in the main process world. And providing render proccesses an "api" to just do the things it is allowed to do via preload scripts.
something like business logic abstraction for better test-ability. Just add some small fast unit tests for node/sql stuff. :)
If you are bundling with electron-builder the native apps, keep in mind to add those binary/native dependencies to asarUnpack.
electron-builder.cjs
{
...,
asarUnpack: [
'node_modules/better-sqlite3/**/*'
],
...
}
I'm going ahead and close this. The "React" in the title is a giveaway that you are likely trying to run better-sqlite3 in a browser.