Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add specific error for invalid_target error #4436

Merged
merged 1 commit into from
Sep 16, 2024

Conversation

itsjustriley
Copy link
Contributor

@itsjustriley itsjustriley commented Sep 11, 2024

WHY are these changes introduced?

Resolves #271

When a user has an invalid store url, or the wrong permissions, when using theme dev in the cli they currently receive an ambiguous invalid_target error message.

WHAT is this pull request doing?

Replacing ambiguous invalid_target error with specific messaging. (Modified an existing error message to work in the pertinent file, added handling for 'invalid_target' specifically).

image

paired with @EvilGenius13 @AribaRajput @lukeh-shopify

How to test your changes?

  1. Build the updated CLI pnpm build
  2. shopify-dev theme dev --store wrong_store
  3. Authenticate
  4. Confirm updated error message is displayed in terminal

Post-release steps

Measuring impact

How do we know this change was effective? Please choose one:

  • n/a - this doesn't need measurement, e.g. a linting rule or a bug-fix
  • Existing analytics will cater for this addition
  • PR includes analytics changes to measure impact

Checklist

  • I've considered possible cross-platform impacts (Mac, Linux, Windows)
  • I've considered possible documentation changes

This comment has been minimized.

Copy link
Contributor

github-actions bot commented Sep 11, 2024

Coverage report

St.
Category Percentage Covered / Total
🟡 Statements
72.93% (-0.06% 🔻)
8353/11454
🟡 Branches
69.52% (-0.01% 🔻)
4079/5867
🟡 Functions
71.68% (-0.07% 🔻)
2172/3030
🟡 Lines
73.27% (-0.06% 🔻)
7903/10786
Show files with reduced coverage 🔻
St.
File Statements Branches Functions Lines
🟢
... / fetch.ts
89.74% (-0.26% 🔻)
78.57% 87.5%
91.43% (-0.24% 🔻)
🟢
... / conf-store.ts
100%
89.19% (-1.05% 🔻)
100% 100%
🟡
... / session.ts
75.81% (-1.12% 🔻)
64.29% (-0.49% 🔻)
90%
76.03% (-1.13% 🔻)

Test suite run success

1878 tests passing in 851 suites.

Report generated by 🧪jest coverage report action from 9cc4d7c

// There's an scenario when Identity returns "invalid_request" when exchanging an identity token.
// This means the token is invalid. We clear the session and throw an error to let the caller know.
return new InvalidRequestError()
}
if (errorMessage === 'invalid_target') {
Copy link
Contributor

@jamesmengo jamesmengo Sep 11, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

function tokenRequestErrorHandler(error: string) {
  if (error === 'invalid_grant') {
    // There's an scenario when Identity returns "invalid_grant" when trying to refresh the token
    // using a valid refresh token. When that happens, we take the user through the authentication flow.
    return new InvalidGrantError()
  }
  if (error === 'invalid_request') {
    // There's an scenario when Identity returns "invalid_request" when exchanging an identity token.
    // This means the token is invalid. We clear the session and throw an error to let the caller know.
    return new InvalidRequestError()
  }
  if (error === 'invalid_target') {
  // add a comment here
    return new InvalidTargetError(INVALID_TARGET_ERROR_MESSAGE)
  }
  // eslint-disable-next-line @shopify/cli/no-error-factory-functions
  return new AbortError(error)
}

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

^ can we try keeping these patterns as is?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@jamesmengo Riley originally had this, but we realised the two custom error types only exist because they are exported and handled upstream. As all we want to do is exit with a message, and we wanted to avoid disabling the eslint rule again, we just wanted to fall back onto the existing AbortError. Another side effect of extending the ExtendableError is that the stack trace is printed out along with the readable error message, which we didn't think was helpful.

Maybe our best option here is create (and not export) a class InvalidTargetError that extends AbortError. This avoids the linting issue of using error factory functions, and keeps the patterns consistent. Also +1 to turning the error message into a constant

Copy link
Contributor

@jamesmengo jamesmengo Sep 11, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the context! That's a great observation that I wasn't aware of :)

As long as the message is in a constant, I'm happy :). I'll save us from having a let vs const debate here since the impact is minimal 😆

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree with extracting the message to a constant. And maybe there's no need to create a new error, you could just do something like return new AbortError(INVALID_TARGET_ERROR_MESSAGE).

'you should be the store owner or create a staff account on the store.' +
'\n\n' +
"If you're the store owner, then you need to log in to the store directly using the " +
'store URL at least once before you log in using Shopify CLI.' +
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
'store URL at least once before you log in using Shopify CLI.' +
'store URL at least once before you log in using Shopify CLI. ' +

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This wording comes from the Ruby CLI, but I think it's ok to stray from 100% parity here to improve this message ever so slightly.

This is non-blocking, and I'm ok with creating a new issue if you want to address that separately

You are not authorized to use the CLI to develop in the provided store.

You cannot use Shopify CLI with development stores if you only have Partner staff member access. To use Shopify CLI on a development store, you must either be the store owner or have a staff account on the store.

If you are the store owner, you need to log in to the store directly using the store URL at least once before logging in with Shopify CLI. Logging into the Shopify admin directly connects the development store with your Shopify login.

Copy link
Contributor

@jamesmengo jamesmengo left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Functionally, this works and looks like it's in the right place to me. Great work!

Most of my feedback are small nits to follow conventions set by the foundations team.
I would recommend asking @Shopify/cli-foundations for a review as well, since this is in cli-kit 🙂.

I don't have too much familiarity with the specific cases in which invalid_target is returned as an error so just wanted to double check that we're not missing any cases when invalid_target may be returned as it seems like the conditions are slightly different from the ruby implementation

cc: @lukeh-shopify
Thanks for these changes!

Copy link
Contributor

@lukeh-shopify lukeh-shopify left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

+1 to James' suggestions of checking with the foundations team, and then going back to your original implementation of using a specific error class that's not exported

Copy link
Contributor

@gonzaloriestra gonzaloriestra left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM, Thanks!

// There's an scenario when Identity returns "invalid_request" when exchanging an identity token.
// This means the token is invalid. We clear the session and throw an error to let the caller know.
return new InvalidRequestError()
}
if (errorMessage === 'invalid_target') {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree with extracting the message to a constant. And maybe there's no need to create a new error, you could just do something like return new AbortError(INVALID_TARGET_ERROR_MESSAGE).

@itsjustriley itsjustriley added this pull request to the merge queue Sep 16, 2024
Merged via the queue into main with commit 379b752 Sep 16, 2024
@itsjustriley itsjustriley deleted the invalid_target-error-update branch September 16, 2024 18:14
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants