A Custom Application configuration file defines the necessary requirements to develop and build your application. The configuration of a Custom Application is typically defined in a JSON file `custom-application-config.json` in the root of your project directory (next to `package.json`). # Supported file extensions The configuration file can be defined in different syntax formats, but it is expected that the file is named `custom-application-config`. The following file extensions can be used: `.json`, `.js`, `.cjs`, `.mjs`, `.ts`. For example: ```js title="custom-application-config.mjs" import { entryPointUriPath } from './constants'; const name = 'Test application'; /** * @type {import('@commercetools-frontend/application-config').ConfigOptions} */ const config = { name, entryPointUriPath, // ... }; module.exports = config; ``` ```js title="./constants.js" const entryPointUriPath = 'test'; module.exports = { entryPointUriPath }; ``` # Editor support To facilitate the usage of the application config, you should instruct your editor to provide hints and code completion (IntelliSense) depending on the format of the configuration file. ## Use JSDoc @type expression For non-JSON files, you can annotate the configuration object with a JSDOc `@type` tag, pointing it to the exported TypeScript declaration of the `@commercetools-frontend/application-config` package. ```js title="custom-application-config.js" /** * @type {import('@commercetools-frontend/application-config').ConfigOptions} */ const config = { // ... }; module.exports = config; ``` For TypeScript files `.ts`, you can import the type directly instead. ```ts title="custom-application-config.ts" import type { ConfigOptions } from '@commercetools-frontend/application-config'; const config: ConfigOptions = { // ... }; export default config; ``` # Configuration properties To learn more about the application config properties, read the following. ## `name` The name of the Custom Application, for information purposes. ```json { "name": "Channels app" } ``` ## `description` An optional description of the Custom Application, for information purposes. ```json { "description": "Manage Channels" } ``` ## `entryPointUriPath` The unique identifier of the Custom Application, similarly to the `projectKey` of your Project. This value determines the route at which the Custom Application is [served by the Merchant Center Proxy](https://docs.commercetools.com/merchant-center-customizations/concepts/merchant-center-proxy-router). ``` /:projectKey/:entryPointUriPath ``` The value is considered unique within each [cloud Region](https://docs.commercetools.com/merchant-center-customizations/concepts/merchant-center-api#cloud-regions) environment, meaning that there can't be any duplicates. Choosing the `entryPointUriPath` is important and should be done carefully as it affects routing and permissions. ```json { "entryPointUriPath": "channels" } ``` The `entryPointUriPath` value must adhere to the following restrictions: - Only lowercase alphanumeric characters are allowed. - Must be between 2 and 64 characters. - Underscores and hyphens are allowed except as leading, trailing, and adjacent characters. Furthermore, the `entryPointUriPath` value is bound to user permissions of the Custom Application and is used to [derive the unique name of the user permissions](https://docs.commercetools.com/merchant-center-customizations/concepts/oauth-scopes-and-user-permissions#user-permissions). Some values are reserved for internal usage and cannot be used: - `account` - `audit-log` - `dashboard` - `categories` - `change-history` - `customers` - `exports` - `discounts` - `operations` - `impex` - `imports` - `imports-exports` - `orders` - `products` - `settings` - `welcome` - `disabled` - `standalone-prices` Note that the list can be extended at any time. Last update 2022-08-11. Even though the `entryPointUriPath` is a unique identifier of a Custom Application, and thus should be defined statically in the source code, it can also be defined dynamically via environment variables using the [environment placeholders](https://docs.commercetools.com/merchant-center-customizations/tooling-and-configuration/custom-application-config#use-variable-placeholders). This may be the case if the Custom Application is to be deployed in different environments. We explain this further in the [troubleshooting section](https://docs.commercetools.com/merchant-center-customizations/troubleshooting/#use-a-test-or-staging-environment). ## `cloudIdentifier` The [identifier of the cloud Region](https://docs.commercetools.com/merchant-center-customizations/concepts/merchant-center-api#cloud-identifiers) that the Custom Application uses to connect to commercetools API platform. The values map to the actual Merchant Center API URL for that Region. ```json { "cloudIdentifier": "gcp-eu" } ``` If a cloud Region is not listed in the values above, you can override the value by adding a `mcApiUrl` property to the Custom Application config file with the full origin URL. ## `mcApiUrl` The origin URL of the [Merchant Center API](https://docs.commercetools.com/merchant-center-customizations/concepts/merchant-center-api#hostnames). The value takes precedence over the `cloudIdentifier`. Use this only if the `cloudIdentifier` does not contain a value for the environment you want to connect to. ## `env` An object holding environment specific configurations, for example `development` or `production`. Which environment is used depends on the environment variable `MC_APP_ENV`. If `MC_APP_ENV` isn't set, `NODE_ENV` will be used. If neither is set, it defaults to `development`. The `MC_APP_ENV` is useful if you want to run the production build of the Custom Application locally. In this case the `NODE_ENV` needs to be set to `production`. However, because the application runs locally, you need to have the URL references pointing to localhost, thus the `MC_APP_ENV` needs to be set to `development`. ## `env.development.initialProjectKey` A `projectKey` of a commercetools Project you have access to. To be used as the default Project upon login in development. ```json { "env": { "development": { "initialProjectKey": "my-project-key" } } } ``` ## `env.development.teamId` Local development is allowed for users belonging to the `Administrators` Team of your Organization with no additional configuration required. If you need to apply more granular permissions for local development of a Custom Application, specify the `teamId` of the user's team. For more information, see [Granular permissions for local development](https://docs.commercetools.com/merchant-center-customizations/troubleshooting#granular-permissions-for-local-development). ## `env.production.applicationId` The Custom Application ID is provided when you add a Custom Application in the Merchant Center (Organizations > Custom Applications > Configure > Add). For more information, see [Managing Custom Applications in the Merchant Center](https://docs.commercetools.com/merchant-center-customizations/merchant-center/managing-custom-applications). ```json { "env": { "production": { "applicationId": "ckvtahxl90097sys6har1e6n3" } } } ``` As long as you are developing the Custom Application locally, you can define any random value as it's a required field. ## `env.production.url` The full URL value where the Custom Application is hosted at. The Merchant Center serves Custom Applications on its own domain, but requests are internally forwarded to this URL. For more information, see [Merchant Center Proxy Router](https://docs.commercetools.com/merchant-center-customizations/concepts/merchant-center-proxy-router). ```json { "env": { "production": { "url": "https://channels.app" } } } ``` This value is also used to configure the [Content Security Policy (CSP)](https://developer.mozilla.org/en-US/docs/Web/HTTP/CSP) HTTP headers to allow the browser to request data from the application domain. ## `env.production.cdnUrl` The full URL value where the Custom Application [static assets](https://docs.commercetools.com/merchant-center-customizations/development/going-to-production#about-static-assets) are hosted, for example when using an external CDN. ```json { "env": { "production": { "cdnUrl": "https://cdn.channels.app" } } } ``` If the static assets are hosted alongside the Custom Application, you can omit this option and the Custom Application `env.production.url` value will be used instead. ## `additionalEnv` An optional object that should be used to inject properties used within your Custom Application. These properties are then made available to the [runtime application environment](https://docs.commercetools.com/merchant-center-customizations/tooling-and-configuration/custom-application-config#runtime-application-environment). For example, if the Custom Application should reference an external API, or have links to certain support pages: ```json { "additionalEnv": { "trackingSentry": "https://000@sentry.io/000", "channelsSupportUrl": "https://support.channels.app" } } ``` ## `oAuthScopes` This field defines the [OAuth scopes and user permissions](https://docs.commercetools.com/merchant-center-customizations/concepts/oauth-scopes-and-user-permissions) required by your Custom Application. The configuration is primarily used for local development and does not require prior application registration. For production deployments, use the Merchant Center UI to configure permissions, or use the [`config:sync`](https://docs.commercetools.com/merchant-center-customizations/tooling-and-configuration/cli#configsync) command to synchronize the Merchant Center configuration from this file, creating or updating the remote customization. You can have "view-only" or "manage-only" OAuth Scopes and leave the other list field empty, as long as at least one OAuth Scope is specified. Alternatively, if at least one additional permission group is configured in [additionalOAuthScopes](https://docs.commercetools.com/merchant-center-customizations/tooling-and-configuration/custom-application-config#additionaloauthscopes), both "view-only" or "manage-only" OAuth Scopes list fields can be left empty. ## `oAuthScopes.view` A list of "view-only" [OAuth Scopes](https://docs.commercetools.com/merchant-center-customizations/api/scopes) required by the Custom Application and associated with the `View` permission. ```json { "oAuthScopes": { "view": ["view_states"] } } ``` ## `oAuthScopes.manage` A list of "manage-only" [OAuth Scopes](https://docs.commercetools.com/merchant-center-customizations/api/scopes) required by the Custom Application and associated with the `Manage` permission. ```json { "oAuthScopes": { "manage": ["manage_orders"] } } ``` Using `manage_` OAuth Scopes always imply the corresponding `view_` OAuth Scope. ## `additionalOAuthScopes` This feature is available from version `21.21.0` onwards. The optional configuration for defining more granular [OAuth Scopes and user permissions](https://docs.commercetools.com/merchant-center-customizations/concepts/oauth-scopes-and-user-permissions#permission-groups). ## `additionalOAuthScopes.*.name` A unique name for the additional permission group. ```json { "additionalOAuthScopes": [ { "name": "movies" } ] } ``` The name value must adhere to the following restrictions: - Only lowercase alphabetic characters are allowed. - Must be between 2 and 64 characters. - Hyphens are allowed except as leading, trailing, and adjacent characters. ## `additionalOAuthScopes.*.view` A list of "view-only" [OAuth Scopes](https://docs.commercetools.com/merchant-center-customizations/api/scopes) required by the Custom Application and associated with the `View` permission. ```json { "additionalOAuthScopes": [ { "name": "movies", "view": ["view_products"], "manage": [] }, { "name": "merch", "view": ["view_categories"], "manage": [] } ] } ``` ## `additionalOAuthScopes.*.manage` A list of "manage-only" [OAuth Scopes](https://docs.commercetools.com/merchant-center-customizations/api/scopes) required by the Custom Application and associated with the `Manage` permission. ```json { "additionalOAuthScopes": [ { "name": "movies", "view": [], "manage": ["manage_products"] }, { "name": "merch", "view": [], "manage": ["manage_categories"] } ] } ``` ## `headers` An optional object to configure HTTP headers used by the Custom Application. ## `headers.csp` An optional object to extend the default [Content Security Policy (CSP)](https://developer.mozilla.org/en-US/docs/Web/HTTP/CSP) directives. The following directives are allowed to be used: - `connect-src` - `font-src` - `frame-src` - `img-src` - `media-src` - `script-src` - `style-src` You can specify various [CSP source values](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Security-Policy/Sources#host-source) (including wildcards `*`) to control from where certain types of content can be loaded or executed. ```json { "headers": { "csp": { "connect-src": ["https://api.stripe.com"], "frame-src": ["https://js.stripe.com", "https://hooks.stripe.com"], "script-src": ["https://js.stripe.com"] } } } ``` The required [Content Security Policy (CSP)](https://developer.mozilla.org/en-US/docs/Web/HTTP/CSP) headers are inferred by default from the `cloudIdentifier` and the `env.production.url`. This includes the hostname where the Custom Application is hosted and the hostname of the Merchant Center API Gateway. ## `headers.permissionsPolicies` An optional object to configure the [HTTP `Permissions-Policy` header](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Permissions-Policy). The `headers.permissionPolicies` object is used only for local development. To enable these features for production, you need to instruct your hosting server to return the header with the modified values. The Merchant Center Proxy Router will then attempt to merge the values with the default ones. ```json { "headers": { "permissionsPolicies": { "microphone": "()", "camera": "()", "payment": "()", "usb": "()", "geolocation": "()" } } } ``` ## `headers.strictTransportSecurity` An optional list to extend the [HTTP `Strict-Transport-Security` header](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Strict-Transport-Security). ```json { "headers": { "strictTransportSecurity": ["includeSubDomains", "preload"] } } ``` ## `icon` The visual identifier of the Custom Application in the Merchant Center. You can choose one of the following predefined icons by referencing it with the special expansion-like syntax `${path:}`: ```json { "icon": "${path:@commercetools-frontend/assets/application-icons/.svg}" } ``` ## `mainMenuLink` An object describing the main link to the Custom Application in the Merchant Center main navigation. ## `mainMenuLink.defaultLabel` The label to be rendered if there is no matching localized label for the user locale. ```json { "mainMenuLink": { "defaultLabel": "Channels" } } ``` ## `mainMenuLink.labelAllLocales` A list of localized fields `{ locale, value }` with translated labels for each application locale, available in the user profile. ```json { "mainMenuLink": { "labelAllLocales": [ { "locale": "en", "value": "Popular Channels" }, { "locale": "de", "value": "Beliebte Channels" } ] } } ``` Labels can also be references using the i18n translation files. For more information, see [Intl message references](https://docs.commercetools.com/merchant-center-customizations/tooling-and-configuration/custom-application-config#intl-message-references). ## `mainMenuLink.permissions` A list of the [user permissions](https://docs.commercetools.com/merchant-center-customizations/concepts/oauth-scopes-and-user-permissions#user-permissions) specific to your Custom Application. Users must have at least one of the specified permissions to see the link in the Merchant Center main navigation. Leaving the list of permissions empty makes the menu link always visible (no restrictions are applied). ```json { "mainMenuLink": { "permissions": ["ViewChannels"] } } ``` The values of the user permissions for the Custom Application are always derived from the `entryPointUriPath`. For more information, see [Apply user permissions](https://docs.commercetools.com/merchant-center-customizations/development/permissions#apply-user-permissions). ## `submenuLinks` A list of objects describing the sub-links to the Custom Application in the Merchant Center main navigation. The Merchant Center displays submenu items in the order they appear in this list. To update the display order, we recommend that you use the Merchant Center interface. For more information, see [Reorder submenu items](https://docs.commercetools.com/merchant-center-customizations/merchant-center/managing-custom-applications#reorder-submenu-items) in the Merchant Center user documentation. Alternatively, you can modify the `submenuLinks` property in the config file and run [config:sync](https://docs.commercetools.com/merchant-center-customizations/merchant-center-customizations/tooling-and-configuration/cli#configsync) to apply the changes to the deployed Custom Application. ## `submenuLinks.*.uriPath` The URI path relative to the `entryPointUriPath` of the Custom Application. For example, given the `entryPointUriPath: channels`, and the (sub)route `uriPath: new`, the menu link results in `/channels/new`. ```json { "submenuLinks": [ { "uriPath": "new" } ] } ``` The main navigation links in the Merchant Center are marked as active based on an exact match strategy with the current page route. For example, if a sub-link is set as `new` and the current page route is `/channels/new`, the link is marked as active. However, if the page route is at `/channels` or `/channels/123` instead of `/channels/new`, the link doesn't match and isn't marked as active. Be aware of how you configure the sub-links and how they're supposed to match with the application routes: - Avoid using `/` as the sub-link. While this is technically allowed, you're adding a duplicated menu link because it's the same as the `mainMenuLink`. - Avoid sublinks to routes that redirect to other routes because they'll never match. For example, if you have a main page with sub-routes such as `/channels/config/general` and `/channels/config/new`, and the routes are configured to redirect from `/channels/config` to `/channels/config/general`, defining the sub-link `/channels/config` will never match any route because of the redirect. ## `submenuLinks.*.defaultLabel` The label to be rendered if there is no matching localized label for the user locale. ```json { "submenuLinks": [ { "defaultLabel": "Create Channel" } ] } ``` ## `submenuLinks.*.labelAllLocales` A list of localized fields `{ locale, value }` with translated labels for each application locale, available in the user profile. ```json { "submenuLinks": [ { "labelAllLocales": [ { "locale": "en", "value": "Create Channel" }, { "locale": "de", "value": "Channel erstellen" } ] } ] } ``` Labels can also be references using the i18n translation files. For more information, see [Intl message references](https://docs.commercetools.com/merchant-center-customizations/tooling-and-configuration/custom-application-config#intl-message-references). ## `submenuLinks.*.permissions` A list of the [user permissions](https://docs.commercetools.com/merchant-center-customizations/concepts/oauth-scopes-and-user-permissions#user-permissions) specific to your Custom Application. Users must have at least one of the specified permissions to see the link in the Merchant Center main navigation. Leaving the list of permissions empty makes the menu link always visible (no restrictions are applied). ```json { "submenuLinks": [ { "permissions": ["ManageChannels"] } ] } ``` The values of the user permissions for the Custom Application are always derived from the `entryPointUriPath`. For more information, see [Apply user permissions](https://docs.commercetools.com/merchant-center-customizations/development/permissions#apply-user-permissions). # Use variable placeholders Variable placeholders are a way of injecting certain information into the "static" configuration file. ## Environment variable references To make the application config more reusable across different environments, you can use references to environment variables within the application config file. References are specified with a special expansion-like syntax `${}` together with the prefix key `env:`. For example, to load an environment variable called `APP_URL`, you would use `${env:APP_URL}`. Imagine developing a Custom Application that can be used in the same Regions (Europe and North America) as the commerce APIs. We can assign the `${env:CLOUD_IDENTIFIER}` reference to the field `cloudIdentifier` and pass the actual value using environment variables. ```json { "cloudIdentifier": "${env:CLOUD_IDENTIFIER}" } ``` The `CLOUD_IDENTIFIER` environment variable can be provided in various ways. For example: - as an inline environment variable when running a script command ```console CLOUD_IDENTIFIER=gcp-eu mc-scripts start ``` - using a [dotenv](https://github.com/motdotla/dotenv) file ```bash title=".env-eu" CLOUD_IDENTIFIER=gcp-eu ``` ```console mc-scripts --env .env-eu start ``` - by defining the environment variables in your CI service You can also pass multiple references to the same value: ```json { "additionalEnv": { "authorityUrl": "https://${env:IDP_URL}/${env:IDP_ID}" } } ``` ## Intl message references This feature is available from version `20.8.0` onwards. References for Intl messages are specified with a special expansion-like syntax `${}` together with the prefix key `intl:`. For example, to load a translation message from the `en.json` file named `Menu.Channels`, you would use `${intl:en:Menu.Channels}`. This is useful when specifying [menu link labels](https://docs.commercetools.com/merchant-center-customizations/tooling-and-configuration/custom-application-config#mainmenulink). ```json { "mainMenuLink": { "defaultLabel": "${intl:en:Menu.Channels}", "labelAllLocales": [ { "locale": "en", "value": "${intl:en:Menu.Channels}" }, { "locale": "de", "value": "${intl:de:Menu.Channels}" } ] } } ``` The reference placeholder assumes that the Custom Application has the translation files in one of the following locations: - `/src/i18n/data/.json` - `/i18n/data/.json` ## File path references This feature is available from version `20.8.0` onwards. References to files are specified with a special expansion-like syntax `${}` together with the prefix key `path:`. This is useful when specifying the [`icon`](https://docs.commercetools.com/merchant-center-customizations/tooling-and-configuration/custom-application-config#icon) of the Custom Application. ```json { "icon": "${path:./app.svg}" } ``` You can use a path relative to the application folder or a path to a module. ```json { "icon": "${path:@commercetools-frontend/assets/application-icons/rocket.svg}" } ``` # Runtime application environment Much of the information specified in the application config is injected into the runtime environment and available via the global variable `window.app`. It is recommended to always pass the value to the [``](https://docs.commercetools.com/merchant-center-customizations/tooling-and-configuration/commercetools-frontend-application-shell#applicationshell). ```jsx highlightLines="3" const EntryPoint = () => ( ); ``` The `environment` prop is parsed and injected into a React Context, making it available to the entire application. To access it, use the `@commercetools-frontend/application-shell-connectors` package. ```jsx import { useApplicationContext } from '@commercetools-frontend/application-shell-connectors'; const MyComponent = () => { const applicationName = useApplicationContext( (context) => context.environment.applicationName ); return
{`Welcome to the application ${applicationName}!`}
; }; ``` All the properties defined in the `additionalEnv` object are made available to the `context.environment` object. For more information, see [Custom user properties](https://docs.commercetools.com/merchant-center-customizations/tooling-and-configuration/commercetools-frontend-application-shell-connectors#custom-user-properties).