Skip to content

Warn that SHOPIFY_APP_AUTOMATION_TOKEN and SHOPIFY_CLI_PARTNERS_TOKEN are deprecated - #8901

Merged
egaodd merged 2 commits into
mainfrom
eddie/service-account-token-4-deprecation-warning
Oct 15, 2026
Merged

egaodd merged 2 commits into
mainfrom
eddie/service-account-token-4-deprecation-warning

Conversation

@egaodd

@egaodd egaodd commented Oct 14, 2026 •

Copy link
Copy Markdown
Contributor

Part of shop/issues-develop#24007 · Builds on #8900

TL;DR: While the CLI authenticates with SHOPIFY_APP_AUTOMATION_TOKEN or SHOPIFY_CLI_PARTNERS_TOKEN, commands print a warning, at most once a day: the variable is deprecated, and the same token should move to SHOPIFY_SERVICE_ACCOUNT_TOKEN. Both old names keep working; nothing else changes.

  1. Rename SHOPIFY_ORGANIZATION_AUTOMATION_TOKEN to SHOPIFY_SERVICE_ACCOUNT_TOKEN #8898: rename to SHOPIFY_SERVICE_ACCOUNT_TOKEN
  2. Never use saved logins in store info while the service account token is set #8899: store info / store open never use a saved login while the token is set
  3. Report service_account_token as the auth method for the service account token #8900: telemetry reports service_account_token as the auth method
  4. Deprecation warning for SHOPIFY_APP_AUTOMATION_TOKEN and SHOPIFY_CLI_PARTNERS_TOKEN ← this one

WHY are these changes introduced?

SHOPIFY_SERVICE_ACCOUNT_TOKEN is the variable going forward. The CLI reads all three variables the same way, so any token that works in SHOPIFY_APP_AUTOMATION_TOKEN or SHOPIFY_CLI_PARTNERS_TOKEN works in the new one. Both old names stay as aliases with no removal date yet. This warning is how people still using them find out about the new name. It's also step 1 of the deprecation policy in CONTRIBUTING: mark the interface deprecated and warn at runtime, in a minor release.

WHAT is this pull request doing?

  • BaseCommand.init calls a new showDeprecatedAutomationTokenVariableWarning(), next to the existing showNpmFlagWarning(). It renders a renderWarning that names the variable in use, for example:

    SHOPIFY_APP_AUTOMATION_TOKEN is deprecated.
    Move the token to SHOPIFY_SERVICE_ACCOUNT_TOKEN. SHOPIFY_APP_AUTOMATION_TOKEN still works for now, but a future release will stop reading it.

  • At most once a day: the warning runs through runAtMinimumInterval(..., {days: 1}), like the CLI's warnings about available upgrades and multiple installations. CI jobs usually start from a fresh environment, so they still see it on each run.
  • When it shows: deprecatedAutomationTokenVariable(), added in automation-token.ts, returns the app or Partner variable when it's the one the CLI uses. It returns nothing when the variable is empty or set together with SHOPIFY_SERVICE_ACCOUNT_TOKEN, because those already fail with their own error.
  • Output: text mode prints the warning to stderr. In --json mode, renderWarning emits it as a diagnostic event, so stdout stays valid JSON.
  • Doc comment: getAppAutomationToken()'s comment now lists both old variables as deprecated.
  • Changeset (@shopify/cli-kit: minor) announcing the deprecation.

How to manually test your changes?

SHOPIFY_APP_AUTOMATION_TOKEN=x shopify store list
SHOPIFY_APP_AUTOMATION_TOKEN=x shopify store list
SHOPIFY_APP_AUTOMATION_TOKEN=x shopify store list --json
SHOPIFY_CLI_PARTNERS_TOKEN=x shopify store list
SHOPIFY_SERVICE_ACCOUNT_TOKEN=x shopify store list
  1. Shows the deprecation warning on stderr, then the usual token exchange error for a fake token.
  2. Run again straight away: no warning, because it already showed today.
  3. Stdout holds only the JSON error. To see the warning as a {"type":"diagnostic","level":"warning",…} event on stderr, first clear the day limit by removing most-recent-occurrence-warn-on-deprecated-automation-token-variable from the CLI's config file (or use a fresh XDG_CONFIG_HOME on Linux).
  4. Names SHOPIFY_CLI_PARTNERS_TOKEN in the warning, if the day limit is clear.
  5. Shows no deprecation warning.

Checklist

  • I've considered possible cross-platform impacts (Mac, Linux, Windows)
  • I've considered possible documentation changes
  • I've considered analytics changes to measure impact
  • The change is user-facing — I've identified the correct bump type (patch for bug fixes · minor for new features · major for breaking changes) and added a changeset with pnpm changeset add

SHOPIFY_SERVICE_ACCOUNT_TOKEN replaces SHOPIFY_APP_AUTOMATION_TOKEN and takes
the same token. The old name keeps working as an alias, with no removal date
yet. Following the deprecation policy in CONTRIBUTING, commands now print a
warning while the CLI authenticates with SHOPIFY_APP_AUTOMATION_TOKEN, so
people still using it learn about the new name before it's removed.

The check runs when a command starts, next to the NPM flag warning. It stays
quiet when the variables can't be used (empty, or set together with
SHOPIFY_SERVICE_ACCOUNT_TOKEN), because the CLI reports that error instead.
In JSON mode the warning is a diagnostic event, so stdout stays valid JSON.

SHOPIFY_CLI_PARTNERS_TOKEN gets no warning: those tokens can't be created any
more and expire on their own, so renaming the variable wouldn't help.

Co-authored-by: Eddie Gao <eddie.gao@shopify.com>
@egaodd
egaodd requested a review from a team as a code owner October 14, 2026 21:13
@github-actions github-actions Bot added the Area: @shopify/cli @shopify/cli package issues label Oct 14, 2026
'@shopify/cli-kit': minor
---

Warn that `SHOPIFY_APP_AUTOMATION_TOKEN` is deprecated in favor of `SHOPIFY_SERVICE_ACCOUNT_TOKEN`, which takes the same token. `SHOPIFY_APP_AUTOMATION_TOKEN` keeps working for now.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

lol, it didn't last long...

}
await removeDuplicatedPlugins(this.config)
this.showNpmFlagWarning()
await this.showDeprecatedAutomationTokenVariableWarning()

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

you are showing the warning in every command run? do we want to limit like once per day or something like that?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Good call. It now goes through runAtMinimumInterval with {days: 1}, like the upgrade and multiple-installation warnings. CI runs usually start from a fresh environment, so they still see it once per job.

@isaacroldan

Copy link
Copy Markdown
Contributor

Not covered: SHOPIFY_CLI_PARTNERS_TOKEN. Partner tokens can't be created any more and expire on their own, so for them the fix is a new service account, not a renamed variable.

Partners tokens are essentially the same type of tokens (they also represent service accounts). The tokens expiring doesn't mean that someone can't use the old ENV VAR with the new tokens... specially since getAppAutomationToken basically gets the token from any of the 3 ENV Vars...

In conclusion, if we are showing a warning to deprecate one env var, we should include the Partners env var too..

Review feedback on the deprecation warning:

- SHOPIFY_CLI_PARTNERS_TOKEN reads the same tokens as the other two
  variables, so it's deprecated in favor of SHOPIFY_SERVICE_ACCOUNT_TOKEN
  as well. The warning now names whichever deprecated variable is in use.
- Showing it on every command is noisy. Like the CLI's other warnings
  (available upgrade, multiple installations), it now uses
  runAtMinimumInterval to show at most once a day. CI jobs usually start
  from a fresh environment, so they still see it on each run.

Co-authored-by: Eddie Gao <eddie.gao@shopify.com>
@egaodd egaodd changed the title Warn that SHOPIFY_APP_AUTOMATION_TOKEN is deprecated Warn that SHOPIFY_APP_AUTOMATION_TOKEN and SHOPIFY_CLI_PARTNERS_TOKEN are deprecated Oct 15, 2026
@github-actions

Copy link
Copy Markdown
Contributor

Differences in type declarations

We detected differences in the type declarations generated by Typescript for this branch compared to the baseline ('main' branch). Please, review them to ensure they are backward-compatible. Here are some important things to keep in mind:

  • Some seemingly private modules might be re-exported through public modules.
  • If the branch is behind main you might see odd diffs, rebase main into this branch.

New type declarations

We found no new type declarations in this PR

Existing type declarations

packages/cli-kit/dist/private/node/constants.d.ts
@@ -8,7 +8,7 @@ export declare const environmentVariables: {
     env: string;
     noAnalytics: string;
     optOutInstrumentation: string;
-    organizationAutomationToken: string;
+    serviceAccountToken: string;
     appAutomationToken: string;
     partnersToken: string;
     runAsUser: string;
packages/cli-kit/dist/private/node/session.d.ts
@@ -61,7 +61,7 @@ export interface OAuthSession {
     appManagement?: string;
     userId: string;
 }
-type AuthMethod = 'partners_token' | 'device_auth' | 'theme_access_token' | 'custom_app_token' | 'none';
+type AuthMethod = 'partners_token' | 'service_account_token' | 'device_auth' | 'theme_access_token' | 'custom_app_token' | 'none';
 /**
  * Retrieves a stable user identifier for analytics, or `'unknown'` if none applies.
  *
@@ -82,7 +82,8 @@ export declare function setLastSeenUserIdAfterAuth(id: string): void;
  * This function checks for the authentication method in the following order:
  * 1. Returns the cached auth method if it's not 'none'.
  * 2. Checks for a cached session, which implies 'device_auth' was used.
- * 3. Checks for a partners token in the environment.
+ * 3. Checks for an automation token in the environment: `service_account_token` for SHOPIFY_SERVICE_ACCOUNT_TOKEN,
+ *    `partners_token` for the app and Partner variables.
  * 4. Checks for a theme password in the environment.
  * 5. If none of the above are true, returns 'none'.
  *
packages/cli-kit/dist/public/node/base-command.d.ts
@@ -26,6 +26,7 @@ declare abstract class BaseCommand extends Command {
     protected _run<T>(): Promise<T>;
     protected init(): Promise<unknown>;
     protected showNpmFlagWarning(): void;
+    protected showDeprecatedAutomationTokenVariableWarning(): Promise<void>;
     protected exitWithTimestampWhenEnvVariablePresent(): void;
     protected parse<TFlags extends FlagOutput & {
         path?: string;
packages/cli-kit/dist/public/node/environment.d.ts
@@ -11,9 +11,9 @@
 export declare function getEnvironmentVariables(): NodeJS.ProcessEnv;
 /**
  * Returns the automation token the CLI authenticates with, from the first of these variables that is set:
- * SHOPIFY_ORGANIZATION_AUTOMATION_TOKEN, SHOPIFY_APP_AUTOMATION_TOKEN, or the deprecated SHOPIFY_CLI_PARTNERS_TOKEN.
+ * SHOPIFY_SERVICE_ACCOUNT_TOKEN, or the deprecated SHOPIFY_APP_AUTOMATION_TOKEN and SHOPIFY_CLI_PARTNERS_TOKEN.
  *
- * Returns undefined when the variables can't be used (an empty value, or the organization variable set alongside
+ * Returns undefined when the variables can't be used (an empty value, or the service account variable set alongside
  * another one). Callers then fall back to the login flow, which reports the problem instead of logging in.
  *
  * @returns The automation token, or undefined if there is no usable one.
packages/cli-kit/dist/public/node/notifications-system.d.ts
@@ -26,7 +26,7 @@ declare const NotificationSchema: zod.ZodObject<{
     id: string;
     type: "info" | "error" | "warning";
     message: string;
-    frequency: "once" | "always" | "once_a_day" | "once_a_week";
+    frequency: "always" | "once" | "once_a_day" | "once_a_week";
     ownerChannel: string;
     title?: string | undefined;
     cta?: {
@@ -43,7 +43,7 @@ declare const NotificationSchema: zod.ZodObject<{
     id: string;
     type: "info" | "error" | "warning";
     message: string;
-    frequency: "once" | "always" | "once_a_day" | "once_a_week";
+    frequency: "always" | "once" | "once_a_day" | "once_a_week";
     ownerChannel: string;
     title?: string | undefined;
     cta?: {
@@ -86,7 +86,7 @@ declare const NotificationsSchema: zod.ZodObject<{
         id: string;
         type: "info" | "error" | "warning";
         message: string;
-        frequency: "once" | "always" | "once_a_day" | "once_a_week";
+        frequency: "always" | "once" | "once_a_day" | "once_a_week";
         ownerChannel: string;
         title?: string | undefined;
         cta?: {
@@ -103,7 +103,7 @@ declare const NotificationsSchema: zod.ZodObject<{
         id: string;
         type: "info" | "error" | "warning";
         message: string;
-        frequency: "once" | "always" | "once_a_day" | "once_a_week";
+        frequency: "always" | "once" | "once_a_day" | "once_a_week";
         ownerChannel: string;
         title?: string | undefined;
         cta?: {
@@ -122,7 +122,7 @@ declare const NotificationsSchema: zod.ZodObject<{
         id: string;
         type: "info" | "error" | "warning";
         message: string;
-        frequency: "once" | "always" | "once_a_day" | "once_a_week";
+        frequency: "always" | "once" | "once_a_day" | "once_a_week";
         ownerChannel: string;
         title?: string | undefined;
         cta?: {
@@ -141,7 +141,7 @@ declare const NotificationsSchema: zod.ZodObject<{
         id: string;
         type: "info" | "error" | "warning";
         message: string;
-        frequency: "once" | "always" | "once_a_day" | "once_a_week";
+        frequency: "always" | "once" | "once_a_day" | "once_a_week";
         ownerChannel: string;
         title?: string | undefined;
         cta?: {
packages/cli-kit/dist/public/node/session.d.ts
@@ -148,15 +148,25 @@ export interface EnsureAuthenticatedBusinessPlatformOptions extends EnsureAuthen
  */
 export declare function ensureAuthenticatedBusinessPlatform(scopes?: BusinessPlatformScope[], options?: EnsureAuthenticatedBusinessPlatformOptions): Promise<string>;
 /**
- * Fails when SHOPIFY_ORGANIZATION_AUTOMATION_TOKEN is set, for commands that can't run with that token.
+ * Whether the CLI authenticates with SHOPIFY_SERVICE_ACCOUNT_TOKEN.
  *
- * Organization automation tokens can't log in as a user or call a store's Admin API, so commands that need either
+ * True whenever that variable is set, even when it's empty or set together with another automation token variable.
+ * Commands use this to skip logins saved on this machine, and authentication then reports any problem with the
+ * variables.
+ *
+ * @returns True when SHOPIFY_SERVICE_ACCOUNT_TOKEN is set.
+ */
+export declare function usingServiceAccountToken(): boolean;
+/**
+ * Fails when SHOPIFY_SERVICE_ACCOUNT_TOKEN is set, for commands that can't run with that token.
+ *
+ * Service account tokens can't log in as a user or call a store's Admin API, so commands that need either
  * refuse to run instead of quietly using the person's own login. `ensureAuthenticated` runs this check before any
  * login. Commands that run on a login saved by `shopify store auth` call it before loading that login.
  *
- * @throws AbortError when SHOPIFY_ORGANIZATION_AUTOMATION_TOKEN is set.
+ * @throws AbortError when SHOPIFY_SERVICE_ACCOUNT_TOKEN is set.
  */
-export declare function ensureNoOrganizationAutomationToken(): void;
+export declare function ensureNoServiceAccountToken(): void;
 /**
  * Logout from Shopify.
  *
packages/cli-kit/dist/private/node/session/automation-token.d.ts
@@ -4,7 +4,7 @@ interface AutomationTokenVariablesProblem {
 }
 /**
  * Returns the name of the automation token variable the CLI authenticates with: the first one that is set, in
- * the order SHOPIFY_ORGANIZATION_AUTOMATION_TOKEN, SHOPIFY_APP_AUTOMATION_TOKEN, SHOPIFY_CLI_PARTNERS_TOKEN.
+ * the order SHOPIFY_SERVICE_ACCOUNT_TOKEN, SHOPIFY_APP_AUTOMATION_TOKEN, SHOPIFY_CLI_PARTNERS_TOKEN.
  *
  * A variable set to an empty string still counts as set, so `automationTokenVariablesProblem` can report it.
  *
@@ -12,11 +12,34 @@ interface AutomationTokenVariablesProblem {
  * @returns The variable name, or undefined when none of them is set.
  */
 export declare function automationTokenVariable(env?: NodeJS.ProcessEnv): string | undefined;
+/**
+ * Returns the `env_auth_method` analytics value for the automation token variable the CLI authenticates with:
+ * `service_account_token` for SHOPIFY_SERVICE_ACCOUNT_TOKEN, and `partners_token` for SHOPIFY_APP_AUTOMATION_TOKEN and
+ * SHOPIFY_CLI_PARTNERS_TOKEN, which existing dashboards already expect.
+ *
+ * The value tells which variable held the token, not which kind of token it is: the CLI can't tell tokens apart, and
+ * any of them works in any of the variables. It shows how much usage has moved to SHOPIFY_SERVICE_ACCOUNT_TOKEN.
+ *
+ * @param env - Environment variables to read.
+ * @returns The auth method to report.
+ */
+export declare function automationTokenAuthMethod(env?: NodeJS.ProcessEnv): 'service_account_token' | 'partners_token';
+/**
+ * Returns the deprecated automation token variable the CLI authenticates with: SHOPIFY_APP_AUTOMATION_TOKEN or
+ * SHOPIFY_CLI_PARTNERS_TOKEN. Both are deprecated in favor of SHOPIFY_SERVICE_ACCOUNT_TOKEN, which takes the same
+ * tokens.
+ *
+ * Returns undefined when the variables can't be used, since the CLI reports that problem instead.
+ *
+ * @param env - Environment variables to read.
+ * @returns The deprecated variable in use, or undefined.
+ */
+export declare function deprecatedAutomationTokenVariable(env?: NodeJS.ProcessEnv): string | undefined;
 /**
  * Explains why the automation token variables can't be used, so a misconfigured environment fails instead of
  * falling back to the logged-in user.
  *
- * - SHOPIFY_ORGANIZATION_AUTOMATION_TOKEN can't be set together with SHOPIFY_APP_AUTOMATION_TOKEN or
+ * - SHOPIFY_SERVICE_ACCOUNT_TOKEN can't be set together with SHOPIFY_APP_AUTOMATION_TOKEN or
  *   SHOPIFY_CLI_PARTNERS_TOKEN.
  * - The selected variable can't be empty.
  *

Base automatically changed from eddie/service-account-token-3-telemetry to main October 15, 2026 16:59
@egaodd
egaodd added this pull request to the merge queue Oct 15, 2026
Merged via the queue into main with commit 1f535b1 Oct 15, 2026
26 of 28 checks passed
@egaodd
egaodd deleted the eddie/service-account-token-4-deprecation-warning branch October 15, 2026 17:22
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Area: @shopify/cli @shopify/cli package issues

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants