The preload script and contextBridge
A preload script is a file Electron runs in a window before the page loads. It has access to part of the Electron API, and with the contextBridge module it can put the functions the page needs onto the page's window object. This way the page gets exactly what it was allowed and nothing more.
Creating the script
Create preload.js in the project root:
// preload.js
const { contextBridge } = require('electron');
contextBridge.exposeInMainWorld('appInfo', {
electron: process.versions.electron,
chrome: process.versions.chrome,
node: process.versions.node,
});exposeInMainWorld takes a name and an object. On the page that object appears as window.appInfo.
Attaching it to the window
The script is set in the window's webPreferences in main.js:
// main.js
const { app, BrowserWindow } = require('electron');
const path = require('node:path');
function createWindow() {
const win = new BrowserWindow({
width: 900,
height: 600,
webPreferences: {
preload: path.join(__dirname, 'preload.js'),
},
});
win.loadFile('index.html');
}
app.whenReady().then(createWindow);Now the script runs before every page load in this window.
Using it on the page
Add a paragraph <p id="versions"></p> before the ul in index.html, and these lines to renderer.js:
// renderer.js
const versions = document.querySelector('#versions');
versions.textContent =
`Electron ${window.appInfo.electron}, Chromium ${window.appInfo.chrome}, Node.js ${window.appInfo.node}`;After npm start a line with versions appears under the heading. The page read data it does not have itself: process exists only in preload.
Functions, not modules
You can pass strings, numbers, objects and functions. The object is copied, so the page cannot change it inside preload. Usually the bridge carries wrapper functions around IPC — this is how the window.notes object will work in the next lessons:
// preload.js
const { contextBridge, ipcRenderer } = require('electron');
contextBridge.exposeInMainWorld('notes', {
load: () => ipcRenderer.invoke('notes:load'),
});The page calls window.notes.load() without knowing how it works inside.
What preload can use
By default preload runs in a sandbox and can load only:
| Module | What it contains |
|---|---|
electron | contextBridge, ipcRenderer, webFrame, webUtils, nativeImage and a few more |
events, timers, url | Part of the standard Node.js modules |
A limited process object is also available: versions and platform.
Common mistake
require('fs') in preload fails to load the module: the sandbox has no Node.js modules for files. Do not turn the sandbox off for this. The main process reads the file, and preload gives the page a function that asks it to do so over IPC.