Custom RPC node with web3Auth x Moralis

Iā€™m not sure I did exacly what you are saying, I just installed Moralis, took the prebuilt version (with lib and dist) and created my own repo from that, then added that as a package dependency. Works so far.

Installing it using npm wonā€™t install the fix you made there. You should make the fix locally in the node modules or try it out the way I explained. You need a little understanding of how npm works locally to fix that though

Iā€™m so confused, I canā€™t seem to make changes in node_modules\moralis\lib\browser\Web3Connector\Web3AuthConnector.js and have them impact the site.

This is the original moralis 1.8.0 and editing directly in the node_modules on my local enviroment.

Even COMMENTING OUT the entire Web3AuthConnector.js, it still opens up the login and launches web3authā€™s pop up. Huh??

However, if I delete the Web3AuthConnector.js it says thereā€™s missing required stuff.

I have tried reseting VS Code and the browser and still the same issue.

Have you restarted your app server?

The local next server is being restarted. Iā€™m gonna take a shot at deploying it on vercel and see what happens in a totally different enviroment.

When I deployed production (vercel) using my custom fork I still get the same issue. This is the file (the console.logs dontā€™ appear in my consoleā€¦)

"use strict";

var _Reflect$construct = require("@babel/runtime-corejs3/core-js-stable/reflect/construct");

var _Object$defineProperty = require("@babel/runtime-corejs3/core-js-stable/object/define-property");

var _interopRequireDefault = require("@babel/runtime-corejs3/helpers/interopRequireDefault");

_Object$defineProperty(exports, "__esModule", {

  value: true

});

exports.Web3Auth = void 0;

var _regenerator = _interopRequireDefault(require("@babel/runtime-corejs3/regenerator"));

var _concat = _interopRequireDefault(require("@babel/runtime-corejs3/core-js-stable/instance/concat"));

var _promise = _interopRequireDefault(require("@babel/runtime-corejs3/core-js-stable/promise"));

var _asyncToGenerator2 = _interopRequireDefault(require("@babel/runtime-corejs3/helpers/asyncToGenerator"));

var _createClass2 = _interopRequireDefault(require("@babel/runtime-corejs3/helpers/createClass"));

var _classCallCheck2 = _interopRequireDefault(require("@babel/runtime-corejs3/helpers/classCallCheck"));

var _assertThisInitialized2 = _interopRequireDefault(require("@babel/runtime-corejs3/helpers/assertThisInitialized"));

var _inherits2 = _interopRequireDefault(require("@babel/runtime-corejs3/helpers/inherits"));

var _possibleConstructorReturn2 = _interopRequireDefault(require("@babel/runtime-corejs3/helpers/possibleConstructorReturn"));

var _getPrototypeOf2 = _interopRequireDefault(require("@babel/runtime-corejs3/helpers/getPrototypeOf"));

var _defineProperty2 = _interopRequireDefault(require("@babel/runtime-corejs3/helpers/defineProperty"));

var _ethers = require("ethers");

var _verifyChainId = _interopRequireDefault(require("../utils/verifyChainId"));

var _AbstractWeb3Connector = _interopRequireDefault(require("./AbstractWeb3Connector"));

function _createSuper(Derived) {

  var hasNativeReflectConstruct = _isNativeReflectConstruct();

  return function () {

    var Super = (0, _getPrototypeOf2.default)(Derived),

        result;

    if (hasNativeReflectConstruct) {

      var NewTarget = (0, _getPrototypeOf2.default)(this).constructor;

      result = _Reflect$construct(Super, arguments, NewTarget);

    } else {

      result = Super.apply(this, arguments);

    }

    return (0, _possibleConstructorReturn2.default)(this, result);

  };

}

function _isNativeReflectConstruct() {

  if (typeof Reflect === "undefined" || !_Reflect$construct) return false;

  if (_Reflect$construct.sham) return false;

  if (typeof Proxy === "function") return true;

  try {

    Boolean.prototype.valueOf.call(_Reflect$construct(Boolean, [], function () {}));

    return true;

  } catch (e) {

    return false;

  }

}

var Web3Auth = /*#__PURE__*/function (_AbstractWeb3Connecto) {

  (0, _inherits2.default)(Web3Auth, _AbstractWeb3Connecto);

  var _super = _createSuper(Web3Auth);

  function Web3Auth() {

    var _context;

    var _this;

    (0, _classCallCheck2.default)(this, Web3Auth);

    for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {

      args[_key] = arguments[_key];

    }

    _this = _super.call.apply(_super, (0, _concat.default)(_context = [this]).call(_context, args));

    (0, _defineProperty2.default)((0, _assertThisInitialized2.default)(_this), "type", 'web3Auth');

    (0, _defineProperty2.default)((0, _assertThisInitialized2.default)(_this), "connect", function (web3auth) {

      return new _promise.default(function (resolve, reject) {

        (function (web3auth) {

          web3auth.loginModal.on('MODAL_VISIBILITY', /*#__PURE__*/function () {

            var _ref = (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee(visibility) {

              return _regenerator.default.wrap(function (_context2) {

                while (1) {

                  switch (_context2.prev = _context2.next) {

                    case 0:

                      if (!visibility) {

                        reject(new Error('Web3Auth: User closed login modal.'));

                      }

                    case 1:

                    case "end":

                      return _context2.stop();

                  }

                }

              }, _callee);

            }));

            return function () {

              return _ref.apply(this, arguments);

            };

          }());

        })(web3auth);

        web3auth.connect().then(resolve).catch(reject);

      });

    });

    (0, _defineProperty2.default)((0, _assertThisInitialized2.default)(_this), "activate", /*#__PURE__*/(0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee2() {

      var _ref3,

          _ref3$chainId,

          chainId,

          clientId,

          theme,

          appLogo,

          loginMethodsOrder,

          _Web3Auth,

          _require,

          _window,

          _window$Web3auth,

          ethChainConfig,

          web3auth,

          provider,

          _web3auth,

          _web3auth2,

          _web3auth3,

          isSocialLogin,

          ether,

          signer,

          values,

          providerChainId,

          _args2 = arguments;

      return _regenerator.default.wrap(function (_context3) {

        console.log('148', chainId)

        while (1) {

          switch (_context3.prev = _context3.next) {

            case 0:

              _ref3 = _args2.length > 0 && _args2[0] !== undefined ? _args2[0] : {}, _ref3$chainId = _ref3.chainId, chainId = _ref3$chainId === void 0 ? '0x1' : _ref3$chainId, clientId = _ref3.clientId, theme = _ref3.theme, appLogo = _ref3.appLogo, loginMethodsOrder = _ref3.loginMethodsOrder;

              if (clientId) {

                _context3.next = 3;

                break;

              }

              throw new Error('"clientId" not provided, please provide clientId');

            case 3:

              try {

                _Web3Auth = (_require = require('@web3auth/web3auth')) === null || _require === void 0 ? void 0 : _require.Web3Auth;

              } catch (_unused) {// Do Nothing Individual Checks are done below

              } // Check if user is using CDN to import

              if (!_Web3Auth) {

                _Web3Auth = (_window = window) === null || _window === void 0 ? void 0 : (_window$Web3auth = _window.Web3auth) === null || _window$Web3auth === void 0 ? void 0 : _window$Web3auth.Web3Auth;

              } // Error checking for if library is not installed

              if (_Web3Auth) {

                _context3.next = 7;

                break;

              }

              throw new Error('"@web3auth/web3auth" not installed, please install');

            case 7:

              // change chainId and RPC for your chain

              if (chainId === '0x1') {

                console.log('182', chainId)

                ethChainConfig = {

                  chainNamespace: 'eip155',

                  chainId: (0, _verifyChainId.default)(chainId),

                  rpcTarget: 'https://speedy-nodes-nyc.moralis.io/9e***********d1/eth/mainnet'

                }; // Build Web3Auth

              } else {

                console.log('190', chainId)

                ethChainConfig = {

                  chainNamespace: 'eip155',

                  chainId: (0, _verifyChainId.default)(chainId),

                }; // Build Web3Auth

              }

              try {

                web3auth = new _Web3Auth({

                  chainConfig: ethChainConfig,

                  uiConfig: {

                    theme: theme !== null && theme !== void 0 ? theme : 'dark',

                    appLogo: appLogo !== null && appLogo !== void 0 ? appLogo : 'https://moralis.io/wp-content/uploads/2021/05/moralisWhiteLogo.svg',

                    loginMethodsOrder: loginMethodsOrder

                  },

                  clientId: clientId

                });

              } catch (_unused2) {// Do Nothing error checked below

              }

              if (web3auth) {

                _context3.next = 11;

                break;

              }

              throw new Error('Could not connect via Web3Auth, error during initializing Web3Auth');

            case 11:

              _context3.next = 13;

              return web3auth.initModal();

            case 13:

              provider = null;

              _context3.next = 16;

              return _this.connect(web3auth);

            case 16:

              provider = _context3.sent;

              if (provider) {

                _context3.next = 19;

                break;

              }

              throw new Error('Could not connect via Web3Auth, error in connecting to provider');

            case 19:

              _context3.prev = 19;

              isSocialLogin = (_web3auth = web3auth) !== null && _web3auth !== void 0 && _web3auth.provider ? false : true;

              ether = new _ethers.ethers.providers.Web3Provider((_web3auth2 = web3auth) !== null && _web3auth2 !== void 0 && _web3auth2.provider ? web3auth.provider : web3auth);

              signer = ether.getSigner();

              _context3.next = 25;

              return _promise.default.all([ether.getNetwork(), signer.getAddress()]);

            case 25:

              values = _context3.sent;

              providerChainId = values[0].chainId;

              _this.account = values[1].toLocaleLowerCase();

              _this.chainId = "0x".concat(providerChainId.toString(16));

              _this.provider = isSocialLogin ? ether : (_web3auth3 = web3auth) === null || _web3auth3 === void 0 ? void 0 : _web3auth3.provider;

              _this.web3Instance = web3auth;

              _this.subscribeToEvents(_this.provider);

              return _context3.abrupt("return", {

                chainId: _this.chainId,

                account: _this.account,

                provider: _this.provider

              });

            case 35:

              _context3.prev = 35;

              _context3.t0 = _context3["catch"](19);

              throw new Error('Could not connect via Web3Auth, error while authenticating');

            case 38:

            case "end":

              return _context3.stop();

          }

        }

      }, _callee2, null, [[19, 35]]);

    })));

    (0, _defineProperty2.default)((0, _assertThisInitialized2.default)(_this), "deactivate", /*#__PURE__*/(0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee3() {

      return _regenerator.default.wrap(function (_context4) {

        while (1) {

          switch (_context4.prev = _context4.next) {

            case 0:

              _this.unsubscribeToEvents(_this.provider);

              if (!_this.web3Instance) {

                _context4.next = 4;

                break;

              }

              _context4.next = 4;

              return _this.web3Instance.logout();

            case 4:

              _this.account = null;

              _this.chainId = null;

              _this.provider = null;

            case 7:

            case "end":

              return _context4.stop();

          }

        }

      }, _callee3);

    })));

    return _this;

  }

  return (0, _createClass2.default)(Web3Auth);

}(_AbstractWeb3Connector.default);

exports.Web3Auth = Web3Auth;

OH NEVERMIND, they are appearing in my console. The chainId should be 1 (number), not the string (your code has a bug)

Okay, so going back to the issues with the package not being updated when editing code, it has something to do with package-lock.json and the versions stored there. I even had to update the version of my fork for my production enviroment to realize it should look for changesā€¦Iā€™m now the first running the newest version of Moralis 1.8.1.

BUT BACK TO THE ORIGINAL ISSUE:
It appears to be using my custom rpc but now Iā€™m getting error 403, not authorized https://f*******w.usemoralis.com:2053/server/users 403

Whatā€™s the deal?

Okay, I switched servers, and now it works.

Wow, thatā€™s a lot of work to jump through to put in a custom RPC which is REQUIRED for web3auth. I hope someone at Moralis is taking notes and implements this feature. There is really no point to offer intergration with web3auth if you have to use their crappy rpcs (they say in their documentation that you need to switch it)

Hi Mikiekwoods,

Actually I passed the rpcTarget directly at the top level of the config and it works:

await authenticate({
provider: ā€œweb3Authā€,
clientId: ā€œā€¦ā€,
chainId: ā€œ0x5ā€,
rpcTarget: ā€œhttps://rpc.ankr.com/ethā€
})

my only question is that I thought Moralis would provide an rpc Targetā€¦ what am I supposed to put there as a valid target ?

you should put there a public RPC url, if you put your speedy node url then anyone can see it and use it

1 Like

pe_chaut, are you using typescript? When I try to pass rpcTarget I get:

ā€œArgument of type ā€˜{ provider: ā€œweb3Authā€; clientId: string; chainId: number; rpcTarget: string; theme: string; loginMethodsOrder: string[]; }ā€™ is not assignable to parameter of type ā€˜AuthenticateOptions | undefinedā€™.
Object literal may only specify known properties, and ā€˜rpcTargetā€™ does not exist in type ā€˜AuthenticateOptionsā€™.ā€

Not working even with ts ignore.

You have latest version of the sdk?

Yes I did 1.8.0 . I even just reinstalled all my packages again and restarted VS Code to be sure.

    await authenticate({
        provider: "web3Auth",
        clientId: process.env.NEXT_PUBLIC_WEB3AUTH_ID!,
        chainId,
        //@ts-ignore
        rpcTarget: "https://rpc.ankr.com/eth",
        theme: "light", //or "dark"
        loginMethodsOrder: ["google", "facebook", "twitter", "discord", "reddit", "apple", "line", "github", "kakao", "linkedin", "weibo", "wechat", "email_passwordless"]
    })

Still requires to ts ignore the type error and still doesnā€™t work (console shows the default quicknode RPC is failing)

What if you add that ts-ignore on the authenticate function?

There is still an error

Cryptokid, do you know that rpcTarget is supposed to be accepted a parameter on the latest 1.8.0 or are you basing it off of pe_chaunt? It is not present in the documentation https://docs.moralis.io/moralis-dapp/users/web3-login/web3auth

Also the chainId types indicate it is suppose to be a number, which differs from the documentation.

Note: I already solved this issue by forking Moralis, but if it is indeed a feature already, then that is a far better solution.

OH NEVERMIND, they are appearing in my console. The chainId should be 1 (number), not the string (your code has a bug)

That string in hex form works for Mumbai (it was example code for someone else). Were you using "1"?

Also the chainId types indicate it is suppose to be a number, which differs from the documentation.

Which one, the chainId parameter for authenticate or for the web3auth config? You can submit an issue on the relevant GitHub repo.

I am not sure how @pe_chaut is using rpcTarget directly where it changes the URL (he isnā€™t using TypeScript), rpcTarget is not set at all in the Web3Auth connector.

@pe_chaut Can you verify that it is actually being used?