Greenruhm / connect

Greenruhm Connect is your white label, custom-branded connection to the music metaverse. It allows you to provide music NFT services inside your app with your branding.
MIT License
1 stars 0 forks source link

feat: utilize 'error-causes' for sdk functions error handling #59

Closed oliver-day closed 1 year ago

oliver-day commented 1 year ago

Description

NOTE: I have included an UserRejectedConsentToShareEmail error so that all errors generated in the existing sign in and sign up flows are created with error-causes. In an upcoming PR, we will move away from using magic.connect.requestUserInfo() and this error will no longer be necessary so it can be removed at that point in time ( https://github.com/Greenruhm/connect/issues/61 ).

To view UI changes associated with changes shown here navigate to https://github.com/Greenruhm/connect/pull/60

oliver-day commented 1 year ago

Hey @ericelliott, after some more debugging I believe the issue we were facing on Thursday was due to a circular dependency between src/features/user/sign-up.js and src/services/greenruhm-api/index.js.

If const { signUpErrors } = require('../../features/user/sign-up'); is included at the top of the src/services/greenruhm-api/index.js file the createUser function imported into src/features/user/sign-up.js as createGreenruhmUser is undefined:

"TypeError: createGreenruhmUser is not a function
    at _callee4$ (webpack-internal:///./src/features/user/sign-up.js:312:59)
    at tryCatch (webpack-internal:///./node_modules/next/dist/compiled/regenerator-runtime/runtime.js:45:40)
    at Generator.invoke [as _invoke] (webpack-internal:///./node_modules/next/dist/compiled/regenerator-runtime/runtime.js:274:22)
    at prototype.<computed> [as next] (webpack-internal:///./node_modules/next/dist/compiled/regenerator-runtime/runtime.js:97:21)
    at asyncGeneratorStep (webpack-internal:///./node_modules/next/dist/compiled/@babel/runtime/helpers/asyncToGenerator.js:3:24)
    at _next (webpack-internal:///./node_modules/next/dist/compiled/@babel/runtime/helpers/asyncToGenerator.js:25:9)"

Based on this documentation, I believe this is due to an unfinished copy of the src/services/greenruhm-api/index.js exports object being imported into src/features/user/sign-up.js .

If the const { signUpErrors } = require('../../features/user/sign-up'); statement is instead moved from the top of src/services/greenruhm-api/index.js file to within the createUser function definition, then the createUser function will be defined when it is imported into src/features/user/sign-up.js and the correct behavior is observed.

const createUser = async ({
  displayName,
  username,
  email,
  walletAddress,
} = {}) => {
  const res = await fetch(`${GREENRUHM_URL}/api/create-account`, {
    method: 'POST',
    body: JSON.stringify({ displayName, username, email, walletAddress }),
  });

  if (res.status === 500) {
    const { signUpErrors } = require('../../features/user/sign-up');   // <----------------
    throw createError(signUpErrors.InternalServerError);
  }

  const body = await res.json();
  if (body.error) {
    throw createError(body.error.cause);
  }
  return body;
};

The other option that also resolves this circular dependency is to include these require statements after the module exports statements in src/services/greenruhm-api/index.js:

module.exports.createDrop = createDrop;
module.exports.createUser = createUser;
module.exports.getCloudinarySignature = getCloudinarySignature;
module.exports.getDrop = getDrop;
module.exports.getProfile = getProfile;
module.exports.updateDropMedia = updateDropMedia;
module.exports.updateLastSignedIn = updateLastSignedIn;

// To avoid circular dependencies
const { signUpErrors } = require('../../features/user/sign-up');
const { signInErrors } = require('../../features/user/sign-in');

Let me know your thoughts on this.

ericelliott commented 1 year ago

Can we avoid the circular dependency entirely by exporting the errors from a shared module that both of the other modules depend on, instead?

oliver-day commented 1 year ago

Can we avoid the circular dependency entirely by exporting the errors from a shared module that both of the other modules depend on, instead?

Hey @ericelliott, yes we can. I have now done that by breaking out the named error causes into sign-up-error-causes.js and sign-in-error-causes.js modules. Expected behavior is observed for these changes alongside the example components changes in https://github.com/Greenruhm/connect/pull/60 .

ericelliott commented 1 year ago

Looks like there's a bunch of logging in the test run.

    Dispatching action:  {} Previous state:  undefined
    New state: {
      user: { email: '', walletAddress: '', sessionToken: '', isSignedIn: false },
      apiKey: { apiKey: null, status: 'Unknown' }
    }
    Dispatching action:  { payload: '<your-api-key>', type: 'apiKey/updateApiKey' } Previous state:  {
      user: { email: '', walletAddress: '', sessionToken: '', isSignedIn: false },
      apiKey: { apiKey: null, status: 'Unknown' }
    }
    New state: {
      user: { email: '', walletAddress: '', sessionToken: '', isSignedIn: false },
      apiKey: { apiKey: '<your-api-key>', status: 'Unknown' }
    }
    Dispatching action:  { payload: '<your-api-key>', type: 'apiKey/updateApiKey' } Previous state:  {
      user: { email: '', walletAddress: '', sessionToken: '', isSignedIn: false },
      apiKey: { apiKey: '<your-api-key>', status: 'Unknown' }
    }
    New state: {
      user: { email: '', walletAddress: '', sessionToken: '', isSignedIn: false },
      apiKey: { apiKey: '<your-api-key>', status: 'Unknown' }
    }
ericelliott commented 1 year ago

Sorry for the delay. Travis stopped working and I needed to consult with customer support to get it working again. Builds are now running full steam ahead!