Deploying Svelte App to Heroku / Dokku fails because modules cannot be found - node.js

I am having problems deploying my svelte web3 App to my VPS running Dokku.
The structure of the folder is as follows:
root
|-->svelte
|--> ...
I found some solutions to work with the two folders needing npm install around here. So I put:
"heroku-postbuild": "cd ./svelte && npm install && npm run build" and "cacheDirectories": ["./node_modules", "./svelte/node_modules"] in the root package.json.
But when the process comes to this point it fails with the following error:
remote: [!] Error: Cannot find module '#rollup/plugin-node-resolve'
remote: Require stack:
remote: - /tmp/build/svelte/rollup.config.js
remote: - /tmp/build/svelte/node_modules/rollup/dist/shared/loadConfigFile.js
remote: - /tmp/build/svelte/node_modules/rollup/dist/bin/rollup
I've tried changing the import to include the full paths etc. but nothing has worked so far. I have also changed the order of the imports, but the process fails with the first import in the rollup.config.
Any ideas?
package.json root:
"scripts": {
"heroku-postbuild": "cd ./svelte && npm install && npm run build"
},
"dependencies": {
"#openzeppelin/contracts": "^4.6.0",
"#truffle/hdwallet-provider": "^2.0.8",
"babel-polyfill": "^6.26.0",
"babel-register": "^6.26.0",
"dotenv": "^16.0.0",
"web3": "^1.7.3"
},
"cacheDirectories": ["./node_modules", "./svelte/node_modules"],
"engines": {
"node": "16.14",
"npm": "8.7.x"
}
}
package.json svelte (added all the dev dependencies again just in case)
{
"name": "app",
"version": "1.0.0",
"private": true,
"scripts": {
"build": "rollup -c",
"dev": "rollup -c -w",
"start": "sirv public --no-clear"
},
"devDependencies": {
"#rollup/plugin-commonjs": "^17.0.0",
"#rollup/plugin-node-resolve": "^11.0.0",
"rollup": "^2.3.4",
"rollup-plugin-css-only": "^3.1.0",
"rollup-plugin-livereload": "^2.0.0",
"rollup-plugin-svelte": "^7.0.0",
"rollup-plugin-terser": "^7.0.0",
"svelte": "^3.0.0"
},
"dependencies": {
"rollup-plugin-terser": "^7.0.0",
"svelte": "^3.0.0",
"#rollup/plugin-commonjs": "^17.0.0",
"#rollup/plugin-node-resolve": "^11.0.0",
"rollup-plugin-css-only": "^3.1.0",
"rollup": "^2.3.4",
"rollup-plugin-svelte": "^7.0.0",
"#rollup/plugin-json": "^4.1.0",
"apexcharts": "^3.35.0",
"bootstrap": "^5.1.3",
"moment": "^2.29.2",
"rollup-plugin-copy": "^3.4.0",
"sirv-cli": "^2.0.0",
"svelte-web3": "^3.4.0"
}
}
rollup.config.js
import resolve from '#rollup/plugin-node-resolve';
import { nodeResolve } from '#rollup/plugin-node-resolve';
import svelte from 'node_modules/rollup-plugin-svelte';
import commonjs from 'node_modules/#rollup/plugin-commonjs';
import livereload from 'node_modules/rollup-plugin-livereload';
import { terser } from 'node_modules/rollup-plugin-terser';
import css from 'node_modules/rollup-plugin-css-only';
import json from 'node_modules/#rollup/plugin-json';
import copy from 'node_modules/rollup-plugin-copy'
const production = !process.env.ROLLUP_WATCH;
function serve() {
let server;
function toExit() {
if (server) server.kill(0);
}
return {
writeBundle() {
if (server) return;
server = require('child_process').spawn('npm', ['run', 'start', '--', '--dev'], {
stdio: ['ignore', 'inherit', 'inherit'],
shell: true
});
process.on('SIGTERM', toExit);
process.on('exit', toExit);
}
};
}
export default {
input: 'src/main.js',
output: {
sourcemap: true,
format: 'iife',
name: 'app',
file: 'public/build/bundle.js'
},
plugins: [
svelte({
compilerOptions: {
// enable run-time checks when not in production
dev: !production
}
}),
// we'll extract any component CSS out into
// a separate file - better for performance
css({ output: 'bundle.css' }),
// If you have external dependencies installed from
// npm, you'll most likely need these plugins. In
// some cases you'll need additional configuration -
// consult the documentation for details:
// https://github.com/rollup/plugins/tree/master/packages/commonjs
resolve({
browser: true,
dedupe: ['svelte']
}),
commonjs(),
json(),
nodeResolve(),
copy({
targets: [{
src: './node_modules/bootstrap/dist/**/*',
dest: 'public/vendor/bootstrap'
}]
}),
// In dev mode, call `npm run start` once
// the bundle has been generated
!production && serve(),
// Watch the `public` directory and refresh the
// browser on changes when not in production
!production && livereload('public'),
// If we're building for production (npm run build
// instead of npm run dev), minify
production && terser()
],
watch: {
clearScreen: false
}
};
```

Related

NPM / Vite problem: Could not resolve "vue" in Framework7 project

I'm having an unusual problem running a basic Framework7 project with vue.
Once created a Framework7 Vue project with the command: framework7 create --ui and installed the dependencies with npm i get the following problem: Could not resolve "vue"
in all packages because the script is looking for vue inside a esm folder like: ../../../node_modules/swiper/esm/vue/swiper.js:1:79 and it's quite strange because esm folder is never existed.
The strange thing is that the same project, with the same package.json works perfectly in another pc with the same version of node (v16.14.2) and npm (8.7.0)
So the problem must be in my pc. I thought about some cache problem, but despite forcing a cache cleanup the problem remains.
For completeness I leave the json package, which is the same that framework7 create --ui command creates for a Vue project.
Has anyone ever had a similar problem or know what the cause might be?
I guess the problem could be related to npm or vite.
{
"name": "my-app",
"private": true,
"version": "1.0.0",
"description": "My App",
"repository": "",
"license": "UNLICENSED",
"scripts": {
"start": "npm run dev",
"dev": "cross-env NODE_ENV=development vite",
"build": "cross-env NODE_ENV=production vite build && npx workbox generateSW workbox-config.js",
"build-capacitor-ios": "cross-env NODE_ENV=production vite build && npx cap copy ios",
"build-capacitor-android": "cross-env NODE_ENV=production vite build && npx cap copy android",
"postinstall": "cpy --flat ./node_modules/framework7-icons/fonts/*.* ./src/fonts/ && cpy --flat ./node_modules/material-icons/iconfont/*.* ./src/fonts/"
},
"browserslist": [
"IOS >= 13",
"Safari >= 13",
"last 5 Chrome versions",
"last 5 Firefox versions",
"Samsung >= 12"
],
"dependencies": {
"#capacitor/android": "^3.4.3",
"#capacitor/app": "^1.1.1",
"#capacitor/browser": "^1.0.7",
"#capacitor/core": "^3.4.3",
"#capacitor/ios": "^3.4.3",
"#capacitor/keyboard": "^1.2.2",
"#capacitor/splash-screen": "^1.2.2",
"#capacitor/status-bar": "^1.0.8",
"dom7": "^4.0.4",
"framework7": "^7.0.1",
"framework7-icons": "^5.0.5",
"framework7-vue": "^7.0.1",
"material-icons": "^1.10.8",
"skeleton-elements": "^4.0.0",
"swiper": "^8.1.1",
"vue": "^3.2.33"
},
"devDependencies": {
"#capacitor/cli": "^3.4.3",
"#vitejs/plugin-vue": "^2.3.1",
"#vue/compiler-sfc": "^3.2.33",
"cordova-res": "^0.15.4",
"cpy-cli": "^4.1.0",
"cross-env": "^7.0.3",
"postcss-preset-env": "^7.4.3",
"vite": "^2.9.5",
"workbox-cli": "^6.5.3"
}
}
Changing in vite.config.js works for me. I have used the node_modules path for all the external bundle related errors
You can mark the path "vue" as external to exclude it from the bundle, which will remove this error.
import path from 'path';
import vue from '#vitejs/plugin-vue';
const SRC_DIR = path.resolve(__dirname, './src');
const PUBLIC_DIR = path.resolve(__dirname, './public');
const BUILD_DIR = path.resolve(__dirname, './www',);
function getPath(new_path) {
return path.resolve(__dirname, 'node_modules/' + new_path);
}
export default {
plugins: [
vue(),
],
root: SRC_DIR,
base: '',
publicDir: PUBLIC_DIR,
build: {
outDir: BUILD_DIR,
assetsInlineLimit: 0,
emptyOutDir: true,
rollupOptions: {
treeshake: false,
},
},
resolve: {
alias: {
'#': SRC_DIR,
"vue": getPath('vue/dist/vue.runtime.esm-browser.js'),
"framework7/lite-bundle": getPath('framework7/framework7-lite-bundle.esm.js'),
"framework7-vue/bundle": getPath('framework7-vue/framework7-vue-bundle.js'),
"swiper/vue": getPath('swiper/vue/swiper-vue.js'),
"skeleton-elements/vue": getPath('skeleton-elements/vue/index.js'),
},
},
server: {
host: true,
},
};

Nuxt Build on heroku does not work but runs locally

i have a nuxt application which i need to deploy on heroku. locally everything works fine. when i install dependencies (locally) there are a lot of unmet dependencies but like i said it works perfectly even when i run build scripts. however when i push to heroku it says build succeded but the app does not work. then i tried building the app on heroku manually by using bash commands on heroku. when i run build script it fails to build with this error :
│ ✖ Nuxt Fatal Error │
Error: Cannot find module '#nuxt/typescript-build' │
│ Require stack: │
│ - /app/node_modules/#nuxt/core/dist/core.js │
│ - /app/node_modules/#nuxt/cli/dist/cli-index.js │
│ - /app/node_modules/#nuxt/cli/dist/cli.js │
│ - /app/node_modules/nuxt/bin/nuxt.js
when i checked '#nuxt/typescript-build' in package.json file it is mentionned under devDependencies (i ran yarn install before building app)
the contents of package.json as well as nuxt.config.js and Procfile are in the following gist
My nuxt.config.js
import colors from "vuetify/es5/util/colors";
import i18n from "./i18n";
export default {
mode: "spa",
/*
** Headers of the page
*/
head: {
titleTemplate: "%s - " + process.env.npm_package_name,
title: process.env.npm_package_name || "",
meta: [
{ charset: "utf-8" },
{ name: "viewport", content: "width=device-width, initial-scale=1" },
{
hid: "description",
name: "description",
content: process.env.npm_package_description || "",
},
],
script: [{ src: "https://use.fontawesome.com/releases/v5.0.6/js/all.js" }],
link: [
{ rel: "icon", type: "image/x-icon", href: "/favicon.ico" },
{
rel: "stylesheet",
href: "https://fonts.googleapis.com/css2?family=Monoton&display=swap",
},
{
rel: "stylesheet",
href:
"https://fonts.googleapis.com/css?family=Roboto:300,400,500,700|Material+Icons",
},
],
},
server: {
host: "0.0.0.0", // default: localhost
},
env: {
BASE_URL: process.env.BASE_URL,
},
/*
** Customize the progress-bar color
*/
loading: { color: "#fff" },
/*
** Global CSS
*/
css: [],
/*
** Plugins to load before mounting the App
*/
plugins: [
{ src: "~/plugins/vuex-persist", ssr: false },
"~/plugins/filters.js",
"~/plugins/vue-youtube.js",
"~/plugins/vue-shortkey.js",
"~/plugins/services.ts",
"~/plugins/color.ts",
"~/plugins/role.ts",
],
/*
** Nuxt.js modules
*/
modules: [
["nuxt-i18n", i18n],
"#nuxtjs/vuetify",
// Doc: https://axios.nuxtjs.org/usage
"#nuxtjs/axios",
"#nuxtjs/eslint-module",
],
buildModules: [
"#nuxt/typescript-build",
"#nuxtjs/composition-api/module",
[
"#nuxtjs/google-analytics",
{
id: process.env.GOOGLE_TRACKING_ID,
},
],
],
/*
** Axios module configuration
** See https://axios.nuxtjs.org/options
*/
axios: {
proxy: false,
},
/*
** vuetify module configuration
** https://github.com/nuxt-community/vuetify-module
*/
vuetify: {
theme: {
primary: colors.blue.darken2,
accent: colors.grey.darken3,
secondary: colors.amber.darken3,
info: colors.teal.lighten1,
warning: colors.amber.base,
error: colors.deepOrange.accent4,
success: colors.green.accent3,
themes: {
dark: {
primary: "#21CFF3",
accent: "#FF4081",
secondary: "#ffe18d",
success: "#4CAF50",
info: "#2196F3",
warning: "#FB8C00",
error: "#FF5252",
},
light: {
primary: "#1976D2",
accent: "#e91e63",
secondary: "#30b1dc",
success: "#4CAF50",
info: "#2196F3",
warning: "#FB8C00",
error: "#FF5252",
},
},
},
},
/*
** Build configuration
*/
build: {
/*
** You can extend webpack config here
*/
publicPath: process.env.PUBLIC_PATH || "/_nuxt/",
extend(config, ctx) {
// config.module.rules.push({
// test: /\.(txt|csv|conll|jsonl)$/i,
// loader: 'file-loader',
// options: {
// name: '[path][name].[ext]'
// }
// })
config.module.rules.push({
enforce: "pre",
test: /\.(txt|csv|json|jsonl)$/,
loader: "raw-loader",
exclude: /(node_modules)/,
});
config.module.rules.push({
test: /\.(ogg|mp3|wav|mpe?g)$/i,
loader: "file-loader",
options: {
name: "[path][name].[ext]",
},
});
},
},
};
My package.json
{
"name": "doccano",
"version": "1.0.0",
"description": "doccano is an open source annotation tools for machine learning practitioner.",
"author": "Hironsan",
"private": true,
"scripts": {
"lint": "eslint --ext .ts,.js,.vue --ignore-path .gitignore .",
"lintfix": "eslint --fix --ext .ts,.js,.vue --ignore-path .gitignore .",
"precommit": "yarn lint",
"test": "jest",
"dev": "nuxt",
"build": "nuxt build",
"start": "nuxt start",
"generate": "nuxt generate"
},
"dependencies": {
"#nuxtjs/axios": "^5.12.0",
"#nuxtjs/composition-api": "^0.23.4",
"#nuxtjs/proxy": "^2.0.1",
"#nuxtjs/vuetify": "^1.11.2",
"#toast-ui/vue-editor": "^1.1.1",
"#vuejs-community/vue-filter-date-format": "^1.6.3",
"#vuejs-community/vue-filter-date-parse": "^1.1.6",
"chart.js": "^2.9.3",
"codemirror": "^5.55.0",
"filepond": "^4.26.1",
"filepond-plugin-file-validate-type": "^1.2.6",
"js-cookie": "^2.2.1",
"lodash": "^4.17.21",
"nuxt": "^2.11.0",
"nuxt-i18n": "^6.13.12",
"papaparse": "^5.2.0",
"sweetalert": "^2.1.2",
"sweetalert2": "^11.1.7",
"tui-editor": "^1.4.10",
"vue-chartjs": "^3.5.0",
"vue-filepond": "^6.0.0",
"vue-shortkey": "^3.1.7",
"vue-youtube": "^1.4.0",
"vuetify": "^2.3.4",
"vuex-persist": "^3.1.3",
"wavesurfer.js": "^5.0.1",
"yarn": "^1.22.4"
},
"devDependencies": {
"#nuxt/types": "^2.14.12",
"#nuxt/typescript-build": "^2.0.4",
"#nuxtjs/eslint-config": "^3.0.0",
"#nuxtjs/eslint-config-typescript": "^5.0.0",
"#nuxtjs/eslint-module": "^2.0.0",
"#nuxtjs/google-analytics": "^2.3.0",
"#nuxtjs/google-fonts": "^1.3.0",
"#types/lodash": "^4.14.168",
"#types/wavesurfer.js": "^5.0.1",
"#vue/test-utils": "^1.0.3",
"axios-mock-adapter": "^1.18.1",
"babel-core": "7.0.0-bridge.0",
"babel-eslint": "^10.1.0",
"babel-jest": "^26.1.0",
"eslint": "^7.19.0",
"eslint-config-prettier": "^7.2.0",
"eslint-config-standard": ">=14.1.1",
"eslint-plugin-import": ">=2.22.0",
"eslint-plugin-jest": ">=23.18.0",
"eslint-plugin-node": ">=11.1.0",
"eslint-plugin-nuxt": "^1.0.0",
"eslint-plugin-promise": ">=4.0.1",
"eslint-plugin-standard": ">=4.0.1",
"eslint-plugin-vue": "^6.2.2",
"jest": "^26.1.0",
"nodemon": "^2.0.4",
"prettier": "^2.2.1",
"raw-loader": "^4.0.2",
"stylus": "^0.54.7",
"stylus-loader": "^3.0.2",
"vue-jest": "^3.0.6"
}
}
I would make sure the devDependencies are being installed:
You have "#nuxt/typescript-build": "^2.0.4", as a dev dependency...
Make sure your have this config value set:
NPM_CONFIG_PRODUCTION=false
so that the devDependencies get installed!
You can do that online in the app settings "Config Vars" section,
or with Heroki cli:
heroku config:set NPM_CONFIG_PRODUCTION=false
mode is obsolete as you can see here: https://nuxtjs.org/docs/configuration-glossary/configuration-mode#the-mode-property
I don't even know why I asked if you wanted a target: 'server' here since it's not even logic.
Since you want to have an SPA only (not the most beneficial with Nuxt tho), you should set the following in your nuxt.config.js file
ssr: false,
target: 'static',
Then, you can yarn generate and yarn start to double check that everything works locally. If it does, you can upload your generated dist directory on https://app.netlify.com/drop for debugging purposes.
If it works there (it should), you can then just plug some CI with a few clicks and it will enable you to simply push to your github repo for a new project generation!
It was because of missing Vue module declaration, create vue-shim.d.ts file in the root directory and add the below content inside it
declare module '*.vue' {
import Vue from 'vue'
export default Vue
}
Reference documentation: https://typescript.nuxtjs.org/guide/setup.html
And as mentioned here: https://github.com/nuxt/typescript/issues/153#issuecomment-543010838

Why is contextBridge not being imported in my Electron app?

I'm writing an Electron app with React and Typescript, using Webpack, Babel and ESLint but I'm having trouble setting:
mainWindow = new BrowserWindow({
title: "Biomech",
webPreferences: {
nodeIntegration: false,
contextIsolation: true,
enableRemoteModule: false,
sandbox: true,
preload: path.join(__dirname, "./preload.js"),
nativeWindowOpen: true,
},
});
which I want as a security measure.
The reason being that, if I set the webPreferences as specified above, I need to use contextBridge and a preload script that binds the functions that are using IPC to the window. And the problem is that contextBridge is not being properly imported in my preload.ts:
import { contextBridge, ipcRenderer } from "electron";
import { readFileSync } from 'fs';
import { History } from 'history';
import { LIST_DRIVE_FILES_CHANNEL, LOAD_PREV_TEST_RESULTS_CHANNEL, OAUTH2_ACCESS_TOKEN_REQUEST_CHANNEL } from "../src/constants/ipcChannels";
import { VISUALIZE_RESULTS_PATH } from "../src/constants/urls";
// Expose protected methods that allow the renderer process to use
// the ipcRenderer without exposing the entire object
contextBridge.exposeInMainWorld(
"api", {
exchangeCodeForAccessToken: (code: string) => {
ipcRenderer.invoke(OAUTH2_ACCESS_TOKEN_REQUEST_CHANNEL, code);
},
listDriveFiles: (accessToken: string) => {
ipcRenderer.invoke(LIST_DRIVE_FILES_CHANNEL, accessToken);
},
openDirectoryDialog: (history: History) => {
ipcRenderer.invoke(LOAD_PREV_TEST_RESULTS_CHANNEL).then((dialog: any) => {
if (dialog.canceled) { // canceled with one l is correct
return;
} else {
const selectedDirectory = dialog.filePaths[0];
console.log(readFileSync(selectedDirectory + "/README.md", 'utf-8'));
history.push(VISUALIZE_RESULTS_PATH);
}
})
}
}
);
The way I see it it's properly used like the examples I've seen here in SO, or in the Electron docs. But when I run my main process script: npm run dev:electron which is specified in my package.json:
{
"name": "electron-react-ts-app",
"version": "1.0.0",
"description": "Electron + React + Typescript",
"main": "./dist/main.js",
"preload": "./dist/preload.js",
"scripts": {
"dev": "concurrently --success first \"npm run dev:electron\" \"npm run dev:react\" -k",
"dev:electron": "NODE_ENV=development webpack --config webpack.electron.config.js --mode development && electron .",
"dev:react": "NODE_ENV=development webpack serve --config webpack.react.config.js --mode development",
"build:electron": "NODE_ENV=production webpack --config webpack.electron.config.js --mode production",
"build:react": "NODE_ENV=production webpack --config webpack.react.config.js --mode production",
"build": "npm run build:electron && npm run build:react",
"pack": "electron-builder --dir",
"dist": "electron-builder",
"lint": "eslint .",
"format": "prettier --write \"**/*.+(js|jsx|json|yml|yaml|css|md|vue)\""
},
"keywords": [],
"license": "MIT",
"build": {
"files": [
"dist/",
"node_modules/",
"package.json"
],
"productName": "Example",
"appId": "com.example.app",
"directories": {
"output": "dist"
}
},
"devDependencies": {
"#babel/preset-env": "^7.9.5",
"#babel/preset-react": "^7.9.4",
"#babel/preset-typescript": "^7.9.0",
"#types/electron-devtools-installer": "^2.2.0",
"#types/react-router-dom": "^5.1.7",
"#types/regenerator-runtime": "^0.13.0",
"dpdm": "^3.6.0",
"electron": "^11.2.1",
"electron-builder": "^22.7.0",
"electron-devtools-installer": "^3.1.1",
"eslint": "^7.18.0",
"file-loader": "^6.2.0",
"html-webpack-plugin": "^4.5.1",
"husky": "^4.3.8",
"lint-staged": "^10.5.3",
"prettier": "^2.2.1",
"react-router-dom": "^5.2.0",
"webpack": "^5.11.1",
"webpack-cli": "^4.3.1",
"webpack-dev-server": "^3.11.1"
},
"dependencies": {
"#babel/core": "^7.12.10",
"#popperjs/core": "^2.6.0",
"#types/node": "^14.14.22",
"#types/react": "^17.0.0",
"#types/react-dom": "^17.0.0",
"axios": "^0.21.1",
"babel-loader": "^8.2.2",
"bootstrap": "^4.5.3",
"chokidar": "^3.5.1",
"core-js": "^3.8.3",
"css-loader": "^5.0.1",
"electron-fetch": "^1.7.3",
"fsevents": "^2.3.1",
"ini": "^2.0.0",
"jquery": "^3.5.1",
"react": "^17.0.1",
"react-bootstrap": "^1.4.0",
"react-dom": "^17.0.1",
"react-google-login": "^5.2.2",
"style-loader": "^2.0.0"
},
"husky": {
"hooks": {
"pre-commit": "npm run lint && npm run format"
}
},
"lint-staged": {
"*.+(js|jsx)": "eslint --fix",
"*.+(json|css|md)": "prettier --write"
}
}
I get the following error: Cannot read property 'exposeInMainWorld' of undefined
webpack 5.19.0 compiled successfully in 1793 ms
App threw an error during load
TypeError: Cannot read property 'exposeInMainWorld' of undefined
at Object../electron/preload.ts (/Users/lucas_sg/Documents/ITBA/PF/pf-biomech/dist/preload.js:24:53)
at __webpack_require__ (/Users/lucas_sg/Documents/ITBA/PF/pf-biomech/dist/preload.js:128:41)
at /Users/lucas_sg/Documents/ITBA/PF/pf-biomech/dist/preload.js:252:11
at Object.<anonymous> (/Users/lucas_sg/Documents/ITBA/PF/pf-biomech/dist/preload.js:254:12)
at Module._compile (internal/modules/cjs/loader.js:1152:30)
at Object.Module._extensions..js (internal/modules/cjs/loader.js:1173:10)
at Module.load (internal/modules/cjs/loader.js:992:32)
at Module._load (internal/modules/cjs/loader.js:885:14)
at Function.f._load (electron/js2c/asar_bundle.js:5:12738)
at Module.require (internal/modules/cjs/loader.js:1032:19)
I've checked out this repo regarding Electron security and it doesn't look like he's doing things too different, at least at first glance, but I'm clearly messing something up.
Here's my webpack config (webpack.electron.config.js) in case it's useful:
const path = require("path");
module.exports = [
{
resolve: {
extensions: [".tsx", ".ts", ".js"],
},
devtool: "source-map",
entry: {
main: {
import: "./electron/main.ts",
dependOn: "preload"
},
preload: "./electron/preload.ts"
},
output: {
path: path.resolve(__dirname, "dist"),
filename: "[name].js",
},
target: "electron-main",
module: {
rules: [
{
test: /\.(js|ts|tsx)$/,
exclude: /node_modules/,
use: {
loader: "babel-loader",
},
},
{
test: /\.css$/,
use: ["style-loader", "css-loader"],
},
],
},
node: {
__dirname: false,
},
},
];
I think the issue resides in you webpack.config file:
entry: {
main: {
import: "./electron/main.ts",
dependOn: "preload"
},
preload: "./electron/preload.ts"
},
Might be that webpack tries to resolve all "preload.ts" dependency at compile time, plus tries to bundle it together with main.ts file. And in such case it will never get access to contextBridge. The preload.js file should only be run in a separate "context" - "Isolated World" as they refer in the docs.
What I would try is:
remove the dependOn: and preload: lines from you webpack config.
convert preload.ts file to JS (ie. to CommonJS format) - try doing that with TS CLI for now
Your preload.js file should look more or less like this:
const { contextBridge, ipcRenderer } = require('electron')
contextBridge.exposeInMainWorld(
'electron',
{
doThing: () => ipcRenderer.send('do-a-thing')
}
)
copy preload.js to a __dirname (in my case it was /dist)
run electron again
That was the only way I could access "contextBridge" object.

Missing Script: webpack in npm

I'm trying to re-build a react app and bundle it using webpack. Whenever I try to run npm run-script build it would always show a npm ERR! missing script: webpack
Things that I've tried:
Deleted the node_modules folder the doing a npm install (again)
installed the webpack globally
installed the webpack-cli
You may notice that I am using old version of some modules. This is because this is a legacy app built before I was employed and now I am trying to integrate the app that I built into this app but before that I would like to understand how the whole thing works as vanilla.
Below is my package.json file
{
"name": "storyline-feedback-tool",
"version": "1.1.2",
"description": "",
"main": "index.js",
"scripts": {
"build": "webpack",
"start-hot": "node server.js",
"start": "webpack-dev-server --content-base public/ --inline --port 3001"
},
"keywords": [],
"author": "",
"license": "ISC",
"dependencies": {
"babel-polyfill": "^6.13.0",
"classnames": "^2.2.5",
"g": "^2.0.1",
"lodash": "^4.15.0",
"react": "^15.3.1",
"react-dom": "^15.3.1",
"react-spin": "^0.6.2",
"webpack": "^1.15.0",
"webpack-cli": "^3.2.3"
},
"devDependencies": {
"autoprefixer": "^6.4.0",
"babel-core": "^6.14.0",
"babel-eslint": "^6.1.2",
"babel-loader": "^6.2.5",
"babel-preset-es2015": "^6.14.0",
"babel-preset-react": "^6.11.1",
"babel-preset-react-hmre": "^1.1.1",
"css-loader": "^0.24.0",
"eslint": "^3.3.1",
"eslint-config-airbnb": "^10.0.1",
"eslint-plugin-import": "^1.14.0",
"eslint-plugin-jsx-a11y": "^2.2.0",
"eslint-plugin-react": "^6.1.2",
"less": "^2.7.1",
"less-loader": "^2.2.3",
"postcss-loader": "^0.11.0",
"postcss-pxtorem": "^3.3.1",
"react-hot-loader": "^1.3.0",
"style-loader": "^0.13.1",
"webpack-dev-server": "^1.15.1"
}
}
Here is my webpack.config.js
var webpack = require('webpack');
var path = require('path');
var autoprefixer = require('autoprefixer');
var postcssPxtorem = require('postcss-pxtorem');
var config = {
name: 'feedback-tool',
entry: {
'feedback-main': './src/index-main.js',
'feedback-form': './src/index-form.js',
},
output: {
path: path.resolve(__dirname, 'public/feedback'),
publicPath: '/feedback/',
filename: '[name].js'
}
};
config.module = {
loaders: [
{
test: /\.js$/,
include: path.resolve(__dirname, 'src'),
exclude: /(node_modules)/,
loader: 'babel',
},
{
test: /\.less$/,
loader: "style-loader!css-loader!postcss-loader!less-loader"
},
{
test: /\.css$/,
loader: "style-loader!css-loader!postcss-loader"
}
]
};
config.postcss = function () {
return [
autoprefixer({
browsers: [
'last 2 version',
'ie > 8']
}),
postcssPxtorem({
propWhiteList: []
})]
};
config.plugins = [
new webpack.optimize.UglifyJsPlugin({
compress: {
warnings: false,
},
output: {
comments: false,
},
}),
new webpack.DefinePlugin({
'process.env': {
'NODE_ENV': '"production"'
}
}),
];
module.exports = config;
Any help would be appreciated.
in my case I just add to node "Scripts" the key "webpack":"webpack". and that worked for me.
{
"name": "reactdemo",
"version": "1.0.0",
"description": "lmora demo",
"main": "app.js",
"scripts": {
"webpack": "webpack",
"test": "echo \"Error: no test specified\" && exit 1"
},
The error message of: npm ERR! missing script: webpack makes me believe your webpack installation screwed up somewhere down the line or having webpack installed globally is causing issues due to the legacy nature of this project. Could you try the following and see if this resolves your issue:
Ensure that your version of node is compatible with webpack. The documentation recommends using the LTS version of Node: 10.15.1 LTS. Directly from webpack's documentation:
"Before we begin, make sure you have a fresh version of Node.js installed. The current Long Term Support (LTS) release is an ideal starting point. You may run into a variety of issues with the older versions as they may be missing functionality webpack and/or its related packages require."
Uninstall Webpack and the CLI:
npm uninstall -g webpack
npm uninstall webpack-cli
Re-Install webpack and the cli locally since installing webpack globally may cause issues:
"Note that this is not a recommended practice. Installing globally locks you down to a specific version of webpack and could fail in projects that use a different version."
npm install --save-dev webpack
npm install --save-dev webpack-cli
Update your custom build command to include the path to your webpack.config.js file.
"scripts": {
"build": "webpack --config <path_to_webpack_config>/webpack.config.js",
"start-hot": "node server.js",
"start": "webpack-dev-server --content-base public/ --inline --port 3001"
},
Try running your build script again:
npm run build
Hopefully that helps!

Why won't `electron-packager` bundle node modules that are listed in `package.json` as dependencies?

I've been struggling with this for a week now so I thought I'd reach out to the amazing SO community for help. I've got an Electron project that needs to produce an OS X application (and Windows eventually). Initially we were using webpack to bundle everything (electron and front-end code) but, with the addition of some features that utilize ffi, this was no longer an option. After switching to using gulp to transpile and uglify the electron code, the app was working in development.
The problem I'm having is, when using electron-packager, none of my node_modules are being bundled during the build. According to the docs, electron-packager should bundle anything listed in the dependencies section of package.json. I built a simple proof-of-concept app to simplify things and modules still aren't being bundled for the electron code. This new, simplified project is just trying to include bunyan (this also fails for ffi) but, after building, the app complains that the bunyan module cannot be found. Can someone help? Am I missing something small but important? Here's some detail to the project:
Environment Details
OSX Version: 10.11.6 (15G1108)
Node Version: 5.2.0 (using nvm)
npm version: 3.3.12
package.json
{
"name": "build-with-native-modules",
"version": "1.0.0",
"description": "A test for Electron packages with native Node modules.",
"main": "el/main.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1",
"clean": "./node_modules/.bin/rimraf build",
"start": "npm run clean && gulp && ./node_modules/.bin/electron ./build/dist/el/main.js",
"electron:rebuild": "./node_modules/.bin/electron-rebuild",
"build:osx": "gulp build:osx",
"cinstall": "rm -Rf ./node_modules && npm cache clean && npm i && npm run electron:rebuild"
},
"postinstall": "install-app-deps",
"author": "Zachary Abresch <zachary.abresch#gmail.com>",
"license": "MIT",
"dependencies": {
"bunyan": "^1.8.4",
"jquery": "^3.1.1"
},
"devDependencies": {
"babel-cli": "^6.18.0",
"babel-core": "^6.18.2",
"babel-eslint": "^7.1.0",
"babel-loader": "^6.2.7",
"babel-preset-es2015": "^6.18.0",
"babel-preset-stage-0": "^6.16.0",
"babel-register": "^6.18.0",
"electron": "1.4.6",
"electron-packager": "^8.2.0",
"electron-rebuild": "^1.3.0",
"eslint": "^3.9.1",
"eslint-config-airbnb": "^13.0.0",
"eslint-plugin-import": "^2.2.0",
"eslint-plugin-jsx-a11y": "^2.2.3",
"eslint-plugin-react": "^6.6.0",
"gulp": "^3.9.1",
"gulp-babel": "^6.1.2",
"gulp-util": "^3.0.7",
"rimraf": "^2.5.4",
"webpack": "^1.13.3",
"webpack-dev-server": "^1.16.2"
}
}
gulpfile.babel.js
import gulp from 'gulp';
import babel from 'gulp-babel';
import gutil from 'gulp-util';
import webpack from 'webpack';
import packager from 'electron-packager';
import webpackConfig from './webpack.config.babel';
import pack from './package.json';
gulp.task('electron:babel', () => {
gulp.src('src/el/**/*.js', { base: 'src' })
.pipe(babel())
.pipe(gulp.dest('build/dist'));
});
gulp.task('move:html', () => {
gulp.src('src/ui/**/*.html', { base: 'src' })
.pipe(gulp.dest('build/dist'));
});
gulp.task('move:package', () => {
gulp.src('package.json', { base: './' })
.pipe(gulp.dest('build/dist'));
});
gulp.task('ui:webpack', (done) => {
const myConfig = Object.create(webpackConfig);
webpack(myConfig, (err, stats) => {
if (err) throw new gutil.PluginError('ui:webpack', err);
gutil.log('[ui:webpack]', stats.toString({ colors: true }));
done();
});
});
const osxBuildOptions = {
arch: 'x64',
'app-copyright': '8x8, Inc.',
'app-version': '1.0.0',
'build-version': '1.0.0',
dir: './build/dist',
name: pack.name,
out: './build/bundle',
overwrite: true,
version: pack.devDependencies.electron,
};
gulp.task('build:osx',
['move:package', 'electron:babel', 'ui:webpack', 'move:html'],
(done) => {
packager(osxBuildOptions, (err, appPath) => {
if (err) throw new gutil.PluginError('electron-packager', err);
gutil.log(`[build:osx] App built in: ${appPath}`);
done();
});
});
gulp.task('default', ['electron:babel', 'ui:webpack', 'move:html']);
webpack.config.babel.js
import path from 'path';
module.exports = {
target: 'electron',
entry: './src/ui/renderer.js',
output: {
path: path.resolve(__dirname, 'build/dist/ui'),
filename: 'ui.bundle.js',
},
module: {
loaders: [
{
loader: 'babel-loader',
include: [
path.resolve(__dirname, 'src/ui'),
],
test: /\.js/,
},
],
},
};
I'm considering trying out electron-builder but I really feel like this should be working. If anyone has any info or insight I'd greatly appreciate it. If you need any additional information, please let me know in the comments. Thanks!

Resources