Electron: Why occurs 'Uncaught ReferenceError: require is no defined.'? - javascript

I have a problem problem in my program using Electron.
First, I was typing require() code in 'main.js'.
const { app, BrowserWindow, globalShortcut, Menu, ipcMain } = require('electron')
Above code does not show an error from console. And I have creating another source file func.js.
I was typing require() code in func.js.
const { ipcRenderer, remote } = require('electron')
But above code shows an error in the console.
So I don't know what is wrong. The ES6 script uses the import () statement, but I do not really know if there was an error in main.js, but I do not know why other files fail.

I got the same error & solved by adding the line bellow in main js file:
from:
win = new BrowserWindow({
})
to:
win = new BrowserWindow({
webPreferences: {nodeIntegration: true},
})

This occurs when you introduce a connecting JS code between html and corresponding Javascript file.

Related

"Uncaught ReferenceError: require is not defined" Electron

This seems like a simple error, but everywhere I look, I see people using Node.js in HTML somehow. I am using Electron and trying to make a simple replacement for the close button and everywhere I look at tutorials and questions about this, they tell you to use this code:
const {BrowserWindow} = require('electron').remote
document.getElementById("close-btn").addEventListener("click", (e) => {
var window = BrowserWindow.getFocusedWindow();
window.close();
});
But obviously this doesn't work because require is a Node.js function. I can't move it into my Node.js code because it can't access the buttons and won't create the listener.
I haven't seen anybody else have this issue and I am very new to Node.js and Electron.
Is there a way I can run a Node file by itself from JS and take the outputs into the normal JS.
So, this is a simple trick that lets you use require in your renderer process (window).
You just have to include the preload argument in webPreferences when creating the window:
In your main process (main.js), add webPreferences to your script:
mainWindow = new BrowserWindow({
webPreferences: {
preload: path.join(__dirname, "preload.js")
}
});
Create a file called preload.js in the same directory as your main.js file, and add this to it:
const { contextBridge } = require("electron");
contextBridge.exposeInMainWorld("versions", {
node: () => process.versions.node,
chrome: () => process.versions.chrome,
electron: () => process.versions.electron,
// We can also expose variables, not just functions
});
And for the require function:
contextBridge.exposeInMainWorld("require", require);
Now you should be able to use require in your HTML.
Learn more at https://www.electronjs.org/docs/latest/tutorial/tutorial-preload

Error with javascript: require('fs'). Why? [duplicate]

I am writing an application with the Node.js, Express.js, and Jade combination.
I have file client.js, which is loaded on the client. In that file I have code that calls functions from other JavaScript files. My attempt was to use
var m = require('./messages');
in order to load the contents of messages.js (just like I do on the server side) and later on call functions from that file. However, require is not defined on the client side, and it throws an error of the form Uncaught ReferenceError: require is not defined.
These other JavaScript files are also loaded at runtime at the client, because I place the links at the header of the webpage. So the client knows all the functions that are exported from these other files.
How do I call these functions from these other JavaScript files (such as messages.js) in the main client.js file that opens the socket to the server?
This is because require() does not exist in the browser/client-side JavaScript.
Now you're going to have to make some choices about your client-side JavaScript script management.
You have three options:
Use the <script> tag.
Use a CommonJS implementation. It has synchronous dependencies like Node.js
Use an asynchronous module definition (AMD) implementation.
CommonJS client side-implementations include (most of them require a build step before you deploy):
Browserify - You can use most Node.js modules in the browser. This is my personal favorite.
Webpack - Does everything (bundles JavaScript code, CSS, etc.). It was made popular by the surge of React, but it is notorious for its difficult learning curve.
Rollup - a new contender. It leverages ES6 modules and includes tree-shaking abilities (removes unused code).
You can read more about my comparison of Browserify vs (deprecated) Component.
AMD implementations include:
RequireJS - Very popular amongst client-side JavaScript developers. It is not my taste because of its asynchronous nature.
Note, in your search for choosing which one to go with, you'll read about Bower. Bower is only for package dependencies and is unopinionated on module definitions like CommonJS and AMD.
I am coming from an Electron environment, where I need IPC communication between a renderer process and the main process. The renderer process sits in an HTML file between script tags and generates the same error.
The line
const {ipcRenderer} = require('electron')
throws the Uncaught ReferenceError: require is not defined
I was able to work around that by specifying Node.js integration as true when the browser window (where this HTML file is embedded) was originally created in the main process.
function createAddItemWindow() {
// Create a new window
addItemWindown = new BrowserWindow({
width: 300,
height: 200,
title: 'Add Item',
// The lines below solved the issue
webPreferences: {
nodeIntegration: true,
contextIsolation: false
}
})}
That solved the issue for me. The solution was proposed here.
ES6: In HTML, include the main JavaScript file using attribute type="module" (browser support):
<script type="module" src="script.js"></script>
And in the script.js file, include another file like this:
import { hello } from './module.js';
...
// alert(hello());
Inside the included file (module.js), you must export the function/class that you will import:
export function hello() {
return "Hello World";
}
A working example is here. More information is here.
Replace all require statements with import statements. Example:
// Before:
const Web3 = require('web3');
// After:
import Web3 from 'web3';
It worked for me.
In my case I used another solution.
As the project doesn't require CommonJS and it must have ES3 compatibility (modules not supported) all you need is just remove all export and import statements from your code, because your tsconfig doesn't contain
"module": "commonjs"
But use import and export statements in your referenced files
import { Utils } from "./utils"
export interface Actions {}
Final generated code will always have(at least for TypeScript 3.0) such lines
"use strict";
exports.__esModule = true;
var utils_1 = require("./utils");
....
utils_1.Utils.doSomething();
This worked for me
Get the latest release from the RequireJS download page
It is the file for RequestJS which is what we will use.
Load it into your HTML content like this:
<script data-main="your-script.js" src="require.js"></script>
Notes!
Use require(['moudle-name']) in your-script.js,
not require('moudle-name')
Use const {ipcRenderer} = require(['electron']),
not const {ipcRenderer} = require('electron')
Even using this won't work. I think the best solution is Browserify:
module.exports = {
func1: function () {
console.log("I am function 1");
},
func2: function () {
console.log("I am function 2");
}
};
-getFunc1.js-
var common = require('./common');
common.func1();
window = new BrowserWindow({
webPreferences: {
nodeIntegration: true,
contextIsolation: false
}
});
I confirm. We must add:
webPreferences: {
nodeIntegration: true
}
For example:
mainWindow = new BrowserWindow({webPreferences: {
nodeIntegration: true
}});
For me, the problem has been resolved with that.
People are asking what is the script tag method. Here it is:
<script src='./local.js'></script>.
Or from network:
<script src='https://mycdn.com/myscript.js'></script>
You need plugin the right url for your script.
I was trying to build metronic using webpack. In my package.json I had to remove the "type": "module" section.

Uncaught ReferenceError: require not defined (electron)

I am trying to create a quote widget on electron. For renderer process, I created index.js and coded like below
console.log('from renderer');
var request = require('request');
const electron = require('electron');
var url ="https://quotesondesign.com/wp-json/wp/v2/posts/?orderby=rand&_="+rnd;
request(url, function(error, response, body) {
if(error)
{
document.getElementById("quote").innerHTML = 'Unable to fetch the quote plaese check the network connection';
return;
}
let bodyJSON = JSON.parse(body);
console.log(bodyJson);
let randomQuote = bodyJSON[0]["content"]["rendered"];
document.getElementById("quote").innerHTML = randomQuote;
});
And index.html has
<div id="quote">
</div>
<script src="index.js">
// require ('index.js');
</script>
If I use require ('index.js'); in script tag, it doesn't work. So I used src="index.js". Now renderer process works but on console, it shows "Uncaught ReferenceError: require is not defined at index.js:3"
My 1st query is why require ('index.js'); on script tag doesn't work on index.html
and 2nd query is how to fix the Uncaught ReferenceError problem on index.js
My electron version is v8.2.0 and node version is v12.16.1 and dependencies on package.json are as follows:
"dependencies": {
"request": "^2.88.2",
"require": "^2.4.20"
}
Anyone help me please. Thanks in advance.
Since Electron 5, Node integration in the renderer process is disabled by default. To get around that, you need to declare nodeIntegration: true when instantiating your BrowserWindow.
// In the main process.
const { BrowserWindow } = require('electron')
const mainWindow = new BrowserWindow({
width: 800,
height: 600,
webPreferences: {
nodeIntegration: true
}
})
Edit: As of Electron 12, you'll also need to define contextIsolation: false in order to do this, as the default value of the flag has changed.
https://www.electronjs.org/docs/breaking-changes#default-changed-contextisolation-defaults-to-true
The reason why require ('index.js'); doesn't work in the script tag is because require isn't defined for the browser. It is only defined for Node. The reason why you are getting the ReferenceError in index.js is because what <script src="index.js> is actually doing is running the code in index.js in the browser environment. So since it is being run in the browser require isn't defined here also.

using console.log() with electron

I have seen a lot of questions from people trying to console log from the rendering process, this is NOT my problem I have console.log littering my main code and I don't see anything in my console here is my code.
/* eslint-disable no-undef */
const { app, BrowserWindow, ipcMain } = require('electron');
const path = require('path');
const url = require('url');
/* eslint-enable */
let win;
console.log('console log test');
function createWindow() {
win = new BrowserWindow({
width: 800,
height: 800
});
win.loadURL(url.format({
pathname: path.join(__dirname, 'index.html'),
protocol: 'file:',
slashes: true
}));
win.on('close', () => {
win = null;
});
console.log('console log test');
}
app.on('ready', createWindow);
app.on('window-all-closed', () => {
if (process.platform !== 'darwin') {
app.quit();
}
});
app.on('activate', () => {
if (win == null) {
console.log('console log test');
createWindow();
console.log('console log test');
}
});
I don't see a single log other than the ones produced by electron itself
I've tried throwing errors and those work fine but anything console.* related doesn't work at all, I've tried running it in PowerShell and re-pulling from GitHub, my friend can see the console logs when he pulls the project though so it seems I'm isolated. I've also updated NPM and all modules associated with the project AND I've tried creating a new console and logging to that one but it doesn't seem to show up, am I missing something? I've put hours into this and am ready to give up.
On Windows, if you want to see a console with all your messages from console.log(), you must launch your app with the parameter --enable-logging, for example :
MyApp.exe --enable-logging
I feel your pain. I have this issue on one of my boxes (a Server2012 box). Nothing worked for me until I stumbled across this comment on one of the electron issues threads.
Typically when you install electron you will have a script in your package.json that looks like this.
"scripts": {
"start": "electron .",
}
I changed mine to
"scripts": {
"start": "C:/path/to/project/node_modules/electron-prebuilt/dist/electron.exe .",
}
And I started to get logging from the main electron process in powershell.
Note that if you are using newer versions of electron, you may need to change electron-prebuilt to electron.
How about logging directly into the browser console?
I have found this to be easier for my workflow.
So what I do is to set a listener on the ipcRenderer to the main process and anytime I needed to log a thing from the main, I just emit to the listerner on the renderer.
For instance, in the renderer.js, I set up like so:
pre.ipcRenderer.on("log", (event,log) => {
console.log(log)
});
and in the main, wherever I need to log a piece of code, I just insert this line of code:
window.webContents.send("log", [__dirname]);
My Assumptions with the codes above:
You have set nodeIntegration: false in your webPreference object. This is why codes like __dirname will be unavailable on the renderer process.
As a result of the above, you are using a preloader to load all your required node-specific files.
I defined all of them in my preload.js file and ship them into one giant object which I named window.pre
One of the preloaded modules in the pre object is ipcRenderer. This is why I consumed it as pre.ipcRenderer
All of these is to say that, if you are consuming your nodes directly from the renderer process, you wont need to be bothered by my pre. and if not, now you now why I used it.
Ciao.

Client on Node.js: Uncaught ReferenceError: require is not defined

I am writing an application with the Node.js, Express.js, and Jade combination.
I have file client.js, which is loaded on the client. In that file I have code that calls functions from other JavaScript files. My attempt was to use
var m = require('./messages');
in order to load the contents of messages.js (just like I do on the server side) and later on call functions from that file. However, require is not defined on the client side, and it throws an error of the form Uncaught ReferenceError: require is not defined.
These other JavaScript files are also loaded at runtime at the client, because I place the links at the header of the webpage. So the client knows all the functions that are exported from these other files.
How do I call these functions from these other JavaScript files (such as messages.js) in the main client.js file that opens the socket to the server?
This is because require() does not exist in the browser/client-side JavaScript.
Now you're going to have to make some choices about your client-side JavaScript script management.
You have three options:
Use the <script> tag.
Use a CommonJS implementation. It has synchronous dependencies like Node.js
Use an asynchronous module definition (AMD) implementation.
CommonJS client side-implementations include (most of them require a build step before you deploy):
Browserify - You can use most Node.js modules in the browser. This is my personal favorite.
Webpack - Does everything (bundles JavaScript code, CSS, etc.). It was made popular by the surge of React, but it is notorious for its difficult learning curve.
Rollup - a new contender. It leverages ES6 modules and includes tree-shaking abilities (removes unused code).
You can read more about my comparison of Browserify vs (deprecated) Component.
AMD implementations include:
RequireJS - Very popular amongst client-side JavaScript developers. It is not my taste because of its asynchronous nature.
Note, in your search for choosing which one to go with, you'll read about Bower. Bower is only for package dependencies and is unopinionated on module definitions like CommonJS and AMD.
I am coming from an Electron environment, where I need IPC communication between a renderer process and the main process. The renderer process sits in an HTML file between script tags and generates the same error.
The line
const {ipcRenderer} = require('electron')
throws the Uncaught ReferenceError: require is not defined
I was able to work around that by specifying Node.js integration as true when the browser window (where this HTML file is embedded) was originally created in the main process.
function createAddItemWindow() {
// Create a new window
addItemWindown = new BrowserWindow({
width: 300,
height: 200,
title: 'Add Item',
// The lines below solved the issue
webPreferences: {
nodeIntegration: true,
contextIsolation: false
}
})}
That solved the issue for me. The solution was proposed here.
ES6: In HTML, include the main JavaScript file using attribute type="module" (browser support):
<script type="module" src="script.js"></script>
And in the script.js file, include another file like this:
import { hello } from './module.js';
...
// alert(hello());
Inside the included file (module.js), you must export the function/class that you will import:
export function hello() {
return "Hello World";
}
A working example is here. More information is here.
Replace all require statements with import statements. Example:
// Before:
const Web3 = require('web3');
// After:
import Web3 from 'web3';
It worked for me.
In my case I used another solution.
As the project doesn't require CommonJS and it must have ES3 compatibility (modules not supported) all you need is just remove all export and import statements from your code, because your tsconfig doesn't contain
"module": "commonjs"
But use import and export statements in your referenced files
import { Utils } from "./utils"
export interface Actions {}
Final generated code will always have(at least for TypeScript 3.0) such lines
"use strict";
exports.__esModule = true;
var utils_1 = require("./utils");
....
utils_1.Utils.doSomething();
This worked for me
Get the latest release from the RequireJS download page
It is the file for RequestJS which is what we will use.
Load it into your HTML content like this:
<script data-main="your-script.js" src="require.js"></script>
Notes!
Use require(['moudle-name']) in your-script.js,
not require('moudle-name')
Use const {ipcRenderer} = require(['electron']),
not const {ipcRenderer} = require('electron')
Even using this won't work. I think the best solution is Browserify:
module.exports = {
func1: function () {
console.log("I am function 1");
},
func2: function () {
console.log("I am function 2");
}
};
-getFunc1.js-
var common = require('./common');
common.func1();
window = new BrowserWindow({
webPreferences: {
nodeIntegration: true,
contextIsolation: false
}
});
I confirm. We must add:
webPreferences: {
nodeIntegration: true
}
For example:
mainWindow = new BrowserWindow({webPreferences: {
nodeIntegration: true
}});
For me, the problem has been resolved with that.
People are asking what is the script tag method. Here it is:
<script src='./local.js'></script>.
Or from network:
<script src='https://mycdn.com/myscript.js'></script>
You need plugin the right url for your script.
I was trying to build metronic using webpack. In my package.json I had to remove the "type": "module" section.

Categories