Moralis 2.0 Parse Auth Upgrade

Rewrite: I am trying to hook up the new moralis.auth with my existing parse db here is my auth code

async loginv2 (authData: any): Promise<any> {
    const { message, signature } = authData

    try {
      const results = await Moralis.Auth.verify({
        message, signature, network: 'evm'
      })

      const data = results.toJSON()

      authData.chainId = data.chain
      authData.nonce = data.nonce
      authData.address = data.address
      authData.version = data.version
      authData.domain = data.domain
      authData.expirationTime = data.expirationTime
      authData.notBefore = data.notBefore
      authData.resources = data.resources
      authData.statement = data.statement
      authData.uri = data.uri
    } catch (e) {
      this.logger.error(e)
    }

    const data = await this.createSigningData(message)

    this.logger.debug({ authData: { ...authData } })

    const user = await Parse.User.logInWith('moralisEth', { authData: { id: authData.address, signature, data } }).catch((e) => {
      this.logger.error(e)
    })
    if (!user) throw new Error('Could not get user')

    await user.setACL(new Parse.ACL(user))
    user.addAllUnique('accounts', [authData.address])
    user.set('ethAddress', authData.address)
    await user.save(null)
    const accessToken = this.jwtService.sign(user, { expiresIn: '7d' })
    this.logger.debug(accessToken)
    return { user, accessToken }
  }

My code at Parse.User.logInWith returns an error ParseError: 101 Eth address not verified. any ideas?

For reference authdata looks like

"authData": {
    "message": "pets.love wants you to sign in with your Ethereum account:\n0x30070B0A885A0c774780Dfe68B5932643eC511fE\n\nPlease sign this message to confirm your identity.\n\nURI: http://localhost:3001\nVersion: 1\nChain ID: 1\nNonce: ILxvhrE8HNfb2g96Y\nIssued At: 2022-08-31T21:55:36.490Z",
    "signature": "0x7cb6f3721863845fa76c4f2e23e1d815c4820ddcf1edaa6ee966cdf1d2bf48b87af6b6dccaee7e368d44f393d96dc308fe24232c4c49e3e5c482176aa36c27121b",
    "id": "DOjtqaV9EotbsrbnD",
    "domain": "pets.love",
    "address": "0x30070b0a885a0c774780dfe68b5932643ec511fe",
    "statement": "Please sign this message to confirm your identity.",
    "uri": "http://localhost:3001",
    "version": "1",
    "nonce": "ILxvhrE8HNfb2g96Y",
    "profileId": "0x0dcdf1318f4741f3a29a2aa34d1f836aba9f27edaf7930cfddadc64e91226f90",
    "chain": "0x1"
  }

Does your message/signature verify at Moralis.Auth.verify?

Yes I get back a response of from Moralis.Auth.Verify

{
  "id": "9DvLXDf4qhMzUql4s",
  "domain": "pets.love",
  "address": "0x30070b0a885a0c774780dfe68b5932643ec511fe",
  "statement": "Please sign this message to confirm your identity.",
  "uri": "http://localhost:3001",
  "version": "1",
  "nonce": "p41awV0z7Wr2BFJzR",
  "profileId": "0x0dcdf1318f4741f3a29a2aa34d1f836aba9f27edaf7930cfddadc64e91226f90",
  "chain": "0x1"
}

I changed { authData: { id: authData.address, signature, data } } to { authData: { moralis: { id: authData.address, signature, data } } } and i got an error of ParseError: 252 This authentication method is unsupported. Iโ€™m not sure if that helps, but I figured Iโ€™d give it a shot.

What do you mean with your existing parse db? You are self hosting a parse server with a db or it is with an existing Moralis server?

The existing moralis database

This is not going to work as current Moralis server is also expecting a specific format for the message that is signed

Do you have the type interfaces or an example json I can take a look at?

Not sure what you mean, the message format should be clear from the message that is required to be signed by Moralis v1

So looking at line 283 https://github.com/MoralisWeb3/Moralis-JS-SDK-v1/blob/main/src/MoralisWeb3.js

 await this.enableWeb3(options);
    const { account, web3: internalWeb3, signer } = this.getInternalWeb3Provider();

    if (!account) {
      throw new Error('Cannot authenticate, no account returned from provider');
    }

    const message = options?.signingMessage || MoralisWeb3.getSigningData();
    const data = await createSigningData(message);
    const ethAddress = account.toLowerCase();
    if (!ethAddress) throw new Error('Address not found');

    const signature = await signer.signMessage(data);
    if (!signature) throw new Error('Data not signed');
    const authData = { id: ethAddress, signature, data };

i need to implement const { account, web3: internalWeb3, signer } = this.getInternalWeb3Provider(); and const message = options?.signingMessage || MoralisWeb3.getSigningData(); const data = await createSigningData(message); ?

Am I on the right path?

Rather than what the 2.0 docs say

const config = {
           domain: process.env.APP_DOMAIN,
           statement: 'Please sign this message to confirm your identity.',
           uri: process.env.NEXTAUTH_URL,
           timeout: 60,
       };
       const message = await Moralis.Auth.requestMessage({
           address,
           chain,
           network,
           ...config,
       });

there is a difference between v2 and v1, what are you trying to do?

Iโ€™m trying to use the v2 auth system and update the user session table in the database when logging in.

These docs push me in the direction of spinning up a new instance of the db server which is not what I want to do https://docs.moralis.io/docs/web3-parse-server-authentication

what is the reason behind trying to do this? you can not change the rules of validation from current Moralis Server in order to be able to make it work

Iโ€™m not trying to change the rules of validation Iโ€™m trying to comply with them. My auth system and database api is already built using v1 but Iโ€™m cleaning up my front end and wanting to use v2 there with nextauth as the session provider.

I donโ€™t completely understand, you will not be able to use moralis v2 auth with a moralis v1 server because the required message format is different

If thats the case, what is the format of the message needed so I can rewrite my code to that format? Or is there a v2 server with upgraded auth?

You will find the message format in the sdk code on GitHub for moralis v1 sdk (it has a timestamp, app id).

There isnโ€™t a v2 server, the idea is to allow users to self host the server in the future.

private async createSigningData (message) {
    let data

    try {
      const { dateTime } = await Parse.Cloud.run('getServerTime')
      const applicationId = Parse.applicationId

      data = `${message}\n\nId: ${applicationId}:${dateTime}`
      this.logger.debug('Signing Message')
      this.logger.debug(data)
    } catch (error) {
      this.logger.error(error)
      data = `${message}`
    }

    return data
  }

This is the code I have generating the message

 pets.love wants you to sign in with your Ethereum account:
0x30070B0A885A0c774780Dfe68B5932643eC511fE

Please sign this message to confirm your identity.

URI: http://localhost:3001
Version: 1
Chain ID: 1
Nonce: 74H7LHQPqqkvp0rrh
Issued At: 2022-09-01T07:15:04.572Z

Id: gy2RJJxcllaxSUmSXlgTDiU489RBL8w1hsdq708E:1662016507883

this seems close to be able to work, maybe multiple \n\n make it now work