The ElectronJS provides the power of the whole web portal in a single application. The Electron app embraces the Chromium browser for the UI and the NodeJS for the backend.
The app usually contains multiple resources: HTML, JS, styles, graphics. All these resources are packed into an ASAR archive. The Electron Main process (think “NodeJS backend”) serves them to the Renderer process(es) (think “frontend”).
🐞Bug
There is an issue of serving the audio and video content By default, it won’t be available in production builds whilst working fine on development environment.
The <audio>
/<video>
source URL calls return 200 😲 with no content!
How to fix it? — Long story short,
import * as E from "electron"
E.protocol.registerSchemesAsPrivileged([{
scheme: "app",
privileges: { secure: true, standard: true, stream: true }
// ^^^^^^^^^^^^
// this does the trick
}])
// Setup the app
// considering the resources URI to start with "app://"
const win = new BrowserWindow({ ... })
win.loadURL("app://./index.html")
// ^^^^^^
How it works?
The Main process creates a BrowserWindow
. The BW behaves as a regular web page therefore it uses HTTP communication respecting the URI scheme syntax.
We ask the Main process to register a custom scheme app://
with streaming privileges. The custom scheme does not allow streaming by default and this delivers no content to <audio>
and <video>
elements.
More on this in Electron process
docs.
Similarly, works it with BrowserView
-s (think BVs are the “tabs” of a BrowserWindow):
const win = new BrowserWindow({ ... })
const view = new BrowserView({ ... })
view.webContents.loadURL("app://./index.html")
Note on resource URI
Designing the web page, you don’t usually need full URI including the schema (with a very few exceptions). If a part on the left of the resource URI is omitted, it’s inherited from the caller page URI:
Page URI: app://admin/index.html
Images: <img src="forbidden.png" /> → "app://admin/forbidden.png"
<img src="/user.png" /> → "app:///forbidden.png"
In other words, if the resource path does not start with schema://
, you are safe 🙂 otherwise pay attention to the schema.