中文
Shopify knowledge · Comparison

Three Kinds of Shopify App: Public, Custom, and the Retired Admin-Created App

Compares the two distribution methods Shopify still lets you create — public and custom — against the retired admin-created custom app, covering who creates each one, install scope, authentication, billing, and the configuration consequences of a distribution method you can never change.

"It's an app we built for ourselves" says nothing about what the app actually is. What determines its permissions, authentication path, ability to charge merchants, and whether any of that can be changed later is its distribution method — not how the developer describes its purpose. Only two distribution methods are available for new apps today. A third, legacy form keeps working in the stores that already have it but can no longer be created.

The three forms side by side

PublicCustomAdmin-created (retired)
Still creatableYesYesNo
Created byA developer; App Store listing requires reviewA developer or a merchantThe merchant, in their own admin
Install scopeMany storesOne store, several stores in the same Plus organization, or transfer-disabled development storesOnly the store that created it
AuthenticationToken exchange when embedded, authorization code grant when notSame as publicA pre-generated Admin API access token, no OAuth
Can be embeddedYesYesNo
Shopify app billingAvailableNot availableNot available

Source: App distribution. A custom-distribution app can't charge merchants through Shopify's app billing system, so any commercial app that needs Shopify to collect payment has to use public distribution.

The admin-created app is history

An admin-created app is one the merchant builds under Apps and sales channels → Develop apps in the Shopify admin: it hands out a long-lived Admin API access token directly, skips OAuth entirely, and cannot be embedded. Shopify now treats it as legacy. Generate access tokens for admin-created custom apps states that new apps of this kind can no longer be created and that existing ones keep working. The Help Center puts the cutoff at January 1, 2026: legacy custom apps created before that date can still be managed from the admin — see About apps.

So "a merchant-built app is the kind where you copy a token out of the admin" is now an outdated assumption. A merchant building an app today does it in the Dev Dashboard and ends up with an ordinary custom-distribution app: its configuration file carries embedded, [access_scopes] and [auth], and authentication is still token exchange or the authorization code grant. To classify an app, read its configuration and authentication path, not who clicked Create.

Created by the merchant, owned by the merchant's organization

A custom-distribution app belongs to the organization that created it. When a merchant creates the app inside their own Dev Dashboard organization, the developer has to work with an account that belongs to that organization; CLI commands run from an account outside it are rejected because that account is not a member (observed in practice, not a documented rule). When you take over a project like this, confirm three things first: which organization owns the app, whether your account is a member of it, and which store the app is bound to.

The distribution method is permanent

App distribution states that the distribution method cannot be changed once selected. "Ship it as a custom app now, list it on the App Store later" is therefore not a migration path — changing form means creating a second app and going through installation and authorization again. Answer two questions before choosing: will this app ever need to be installed on a store outside the original merchant (or their Plus organization), and will it ever charge merchants through Shopify? A yes to either rules out custom distribution.

A configuration consequence you have to handle

When the merchant has created only one app, development and production share a single app identity — and application_url can only hold one value at a time. In that setup automatically_update_urls_on_dev has to be false, or every shopify app dev run rewrites the app URL the merchant actually sees to the developer's local tunnel address. Shopify's own description of the field is that when it is false your URLs won't be updated on dev, and it lists that value as the recommendation for production apps — see App configuration.

If development and production genuinely need to stay out of each other's way, the answer is two app identities and two configuration files, not automatic URL rewriting.