Dependency issues with Webpack

I noticed that my webpack project broke when integrating Moralis. To narrow down the problem I cloned a webpack starter project (https://github.com/wbkd/webpack-starter), npm i moralis, added this code below, and reproduced those errors.

import Moralis from 'moralis';
// ...
Moralis.initialize(MORALIS_APP_ID);
Moralis.serverURL = MORALIS_SERVER_URL;

I added this config to webpack.common.js regarding the polyfill errors (though I’m not sure if this how you intend we handle these module dependencies).

resolve: {
   // ...
   fallback: {
      'crypto': false,
      'stream': false,
      'assert': false,
      'http': false,
      'https': false,
      'os': false
    }
}

The last error remaining is:

WARNING in ./node_modules/moralis/lib/browser/MoralisWalletConnectProvider.js 63:44-83
Module not found: Error: Can't resolve '@walletconnect/web3-provider' in '/path/to/project/node_modules/moralis/lib/browser'
 @ ./node_modules/moralis/lib/browser/MoralisWeb3.js 49:59-100
 @ ./node_modules/moralis/lib/browser/Parse.js 37:42-66
 @ ./node_modules/moralis/index.js 1:0-50
 @ ./src/scripts/index.js 2:0-30 9:0-18 10:0-17

What can I do to make Moralis work with a Webpack project?

Hey @makuziker

I see the error message Can't resolve '@walletconnect/web3-provider', do you use walletconnect provider functions inside the project?

Hello,

No, I do not use walletconnect provider functions in the project.

Install npm install @walletconnect/web3-provider

It seems that there is an issue on Moralis SDK side. By default, you don’t need to install it. But I think this will solve your problem.

Ah yes that does remove that error.

There’s one more error actually on this webpack-starter. It occurs on the browser-side.

When I comment out the three lines of Moralis code, the browser index.js code runs as expected. When I uncomment the Moralis code, the browser throws this error (and no index.js code runs):

Uncaught ReferenceError: process is not defined
    at eval (util.js?3022:109)
    at Object../node_modules/util/util.js (vendors-node_modules_css-loader_dist_runtime_api_js-node_modules_css-loader_dist_runtime_cssW-3d8c02.js:11630)
    at __webpack_require__ (app.js:383)
    at fn (app.js:631)
    at eval (index.js?166e:20)
    at Object../node_modules/web3-core-requestmanager/lib/index.js (vendors-node_modules_css-loader_dist_runtime_api_js-node_modules_css-loader_dist_runtime_cssW-3d8c02.js:11810)
    at __webpack_require__ (app.js:383)
    at fn (app.js:631)
    at eval (index.js?c063:22)
    at Object../node_modules/web3-core/lib/index.js (vendors-node_modules_css-loader_dist_runtime_api_js-node_modules_css-loader_dist_runtime_cssW-3d8c02.js:11875)

Could you show us the package.json to see what version of moralis you’re using? Do you have react-moralis installed as well?

Sure thing. This project doesn’t have react-moralis installed.

{
  "name": "webpack-starter",
  "version": "1.0.0",
  "description": "A light foundation for your next frontend project based on webpack.",
  "scripts": {
    "lint": "npm run lint:styles; npm run lint:scripts",
    "lint:styles": "stylelint src",
    "lint:scripts": "eslint src",
    "build": "cross-env NODE_ENV=production webpack --config webpack/webpack.config.prod.js",
    "start": "webpack serve --config webpack/webpack.config.dev.js"
  },
  "repository": {
    "type": "git",
    "url": "git+https://github.com/wbkd/webpack-starter.git"
  },
  "keywords": [
    "webpack",
    "startkit",
    "frontend",
    "es6",
    "javascript",
    "webdev"
  ],
  "author": "webkid.io",
  "license": "MIT",
  "bugs": {
    "url": "https://github.com/wbkd/webpack-starter/issues"
  },
  "devDependencies": {
    "@babel/core": "^7.15.0",
    "@babel/plugin-proposal-class-properties": "^7.14.5",
    "@babel/plugin-syntax-dynamic-import": "^7.8.3",
    "@babel/preset-env": "^7.15.0",
    "babel-eslint": "^10.1.0",
    "babel-loader": "^8.2.2",
    "clean-webpack-plugin": "^3.0.0",
    "copy-webpack-plugin": "^9.0.1",
    "cross-env": "^7.0.3",
    "css-loader": "^6.2.0",
    "eslint": "^7.32.0",
    "eslint-webpack-plugin": "^3.0.1",
    "file-loader": "^6.2.0",
    "html-loader": "^2.1.2",
    "html-webpack-plugin": "^5.3.2",
    "mini-css-extract-plugin": "^2.2.0",
    "node-sass": "^6.0.1",
    "postcss-loader": "^6.1.1",
    "postcss-preset-env": "^6.7.0",
    "sass-loader": "^12.1.0",
    "style-loader": "^3.2.1",
    "stylelint": "^13.13.1",
    "stylelint-config-standard": "^22.0.0",
    "stylelint-webpack-plugin": "^3.0.1",
    "webpack": "^5.50.0",
    "webpack-cli": "^4.7.2",
    "webpack-dev-server": "^3.11.2",
    "webpack-merge": "^5.8.0"
  },
  "dependencies": {
    "@babel/polyfill": "^7.12.1",
    "@walletconnect/web3-provider": "^1.6.5",
    "core-js": "^3.16.1",
    "d3": "^7.0.0",
    "moralis": "^0.0.39"
  }
}

@Yomoo / @malik I’ll ask something a little different.
Is there a working example of a vanilla JS frontend project where Moralis is installed via package.json / npm i moralis?
Or, do your use cases only cover installing Moralis via a <script> tag in the html for vanilla JS frontends?

Hello again. I found a solution to my problems. Here’s my code. Just a note that my webpack knowledge is rather beginner.

The highlights here is that I installed npm i moralis @walletconnect/web3-provider process, defined process and Buffer in the plugins, and defined empty fallback modules for crypto stream assert http https os

With this code I verified I can build the dev bundle, initialize Moralis, and login with metamask without throwing an error.

package.json

{
  "name": "webpack-starter",
  "version": "1.0.0",
  "description": "A light foundation for your next frontend project based on webpack.",
  "scripts": {
    "lint": "npm run lint:styles; npm run lint:scripts",
    "lint:styles": "stylelint src",
    "lint:scripts": "eslint src",
    "build": "cross-env NODE_ENV=production webpack --config webpack/webpack.config.prod.js",
    "start": "webpack serve --config webpack/webpack.config.dev.js"
  },
  "repository": {
    "type": "git",
    "url": "git+https://github.com/wbkd/webpack-starter.git"
  },
  "keywords": [
    "webpack",
    "startkit",
    "frontend",
    "es6",
    "javascript",
    "webdev"
  ],
  "author": "webkid.io",
  "license": "MIT",
  "bugs": {
    "url": "https://github.com/wbkd/webpack-starter/issues"
  },
  "devDependencies": {
    "@babel/core": "^7.15.0",
    "@babel/plugin-proposal-class-properties": "^7.14.5",
    "@babel/plugin-syntax-dynamic-import": "^7.8.3",
    "@babel/preset-env": "^7.15.0",
    "babel-eslint": "^10.1.0",
    "babel-loader": "^8.2.2",
    "clean-webpack-plugin": "^3.0.0",
    "copy-webpack-plugin": "^9.0.1",
    "cross-env": "^7.0.3",
    "css-loader": "^6.2.0",
    "eslint": "^7.32.0",
    "eslint-webpack-plugin": "^3.0.1",
    "file-loader": "^6.2.0",
    "html-loader": "^2.1.2",
    "html-webpack-plugin": "^5.3.2",
    "mini-css-extract-plugin": "^2.2.0",
    "node-sass": "^6.0.1",
    "postcss-loader": "^6.1.1",
    "postcss-preset-env": "^6.7.0",
    "sass-loader": "^12.1.0",
    "style-loader": "^3.2.1",
    "stylelint": "^13.13.1",
    "stylelint-config-standard": "^22.0.0",
    "stylelint-webpack-plugin": "^3.0.1",
    "webpack": "^5.50.0",
    "webpack-cli": "^4.7.2",
    "webpack-dev-server": "^3.11.2",
    "webpack-merge": "^5.8.0"
  },
  "dependencies": {
    "@babel/polyfill": "^7.12.1",
    "@walletconnect/web3-provider": "^1.6.5",
    "core-js": "^3.16.1",
    "d3": "^7.0.0",
    "moralis": "^0.0.39",
    "process": "^0.11.10"
  }
}

webpack.common.js

const Path = require('path');
const { CleanWebpackPlugin } = require('clean-webpack-plugin');
const CopyWebpackPlugin = require('copy-webpack-plugin');
const HtmlWebpackPlugin = require('html-webpack-plugin');
const webpack = require('webpack');

module.exports = {
  entry: {
    app: Path.resolve(__dirname, '../src/scripts/index.js'),
  },
  output: {
    path: Path.join(__dirname, '../build'),
    filename: 'js/[name].js',
  },
  optimization: {
    splitChunks: {
      chunks: 'all',
      name: false,
    },
  },
  plugins: [
    new CleanWebpackPlugin(),
    new CopyWebpackPlugin({
      patterns: [{ from: Path.resolve(__dirname, '../public'), to: 'public' }]
    }),
    new HtmlWebpackPlugin({
      template: Path.resolve(__dirname, '../src/index.html'),
    }),
    new webpack.ProvidePlugin({ process: 'process/browser' }),
    new webpack.ProvidePlugin({ Buffer: ['buffer', 'Buffer'] })
  ],
  resolve: {
    alias: {
      '~': Path.resolve(__dirname, '../src'),
    },
    fallback: {
      'crypto': false,
      'stream': false,
      'assert': false,
      'http': false,
      'https': false,
      'os': false
    }
  },
  module: {
    rules: [
      {
        test: /\.mjs$/,
        include: /node_modules/,
        type: 'javascript/auto',
      },
      {
        test: /\.(ico|jpg|jpeg|png|gif|eot|otf|webp|svg|ttf|woff|woff2)(\?.*)?$/,
        use: {
          loader: 'file-loader',
          options: {
            name: '[path][name].[ext]',
          },
        },
      },
    ],
  },
};

src/index.js

import '../styles/index.scss';
import Moralis from 'moralis';

if (process.env.NODE_ENV === 'development') {
  require('../index.html');
}

Moralis.initialize(INSERT_APP_ID);
Moralis.serverURL = INSERT_SERVER_URL;

async function login() {
  let user = Moralis.User.current();
  if (!user) {
    user = await Moralis.Web3.authenticate();
  }
  console.log('logged in user:', user?.get('ethAddress'));
}

async function logout() {
  await Moralis.User.logOut();
  window.location.reload();
}

document.getElementById("btn-login").onclick = login;
document.getElementById("btn-logout").onclick = logout;

Great job @makuziker

Thank you for sharing the solution to the problem with the community :man_mechanic:

We appreciate that :raised_hands:

Latest version of Moralis is 0.0.42