Skip to content

Manifest Reference

Manifest Reference

Meta information (required)

Meta-information about your app.

xml
<meta>
    <!-- This is the element for the technical name of your app and must equal the name of the folder your app is contained in -->
    <name>MyExampleApp</name>
    <!-- In this element, you can set a label for your app. To include translations use the `lang` attribute -->
    <label>Label</label>
    <label lang="de-DE">Name</label>
    <!-- Translatable, a description of your app -->
    <description>A description</description>
    <description lang="de-DE">Eine Beschreibung</description>
    
    <author>Your Company Ltd.</author>
    <copyright>(c) by Your Company Ltd.</copyright>
    <version>1.0.0</version>
    <license>MIT</license>
    <compatibility>~6.5.0</compatibility>
    <!-- Optional, you can set the path to an icon that should be shown for your app, the icon needs to a `png` file -->
    <icon>icon.png</icon>
    <!-- Optional, in this element you can link to your privacy policy -->
    <privacy>https://your-company.com/privacy</privacy>
    <!-- Optional, Translatable, in this element you can describe the changes the shop owner needs to apply to his shops privacy policy, e.g. because you process personal information on an external server -->
    <privacyPolicyExtensions>
        This app processes following personal information on servers based in the U.S.:
        - Address information
        - Order positions
        - Order value
    </privacyPolicyExtensions>
    <privacyPolicyExtensions lang="de-DE">
        Diese App verarbeitet folgende personenbezogene Daten auf Servern in den USA:
        - Adress-Informationen
        - Bestellpositionen
        - Bestellsumme
    </privacyPolicyExtensions>
</meta>

INFO

The following configurations are all optional.

Setup

Can be omitted if no communication between Shopware and your app is needed. For more follow the app base guide.

xml
<?xml version="1.0" encoding="UTF-8"?>
<manifest xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
          xsi:noNamespaceSchemaLocation="https://raw.githubusercontent.com/shopware/shopware/trunk/src/Core/Framework/App/Manifest/Schema/manifest-2.0.xsd">
    <meta>
        ...
    </meta>
    <setup>
        <!-- The URL which will be used for the registration -->
        <registrationUrl>https://my.example.com/registration</registrationUrl>
        <!-- Dev only, the secret that is used to sign the registration request -->
        <secret>mysecret</secret>
    </setup>
</manifest>

Storefront

Can be omitted if your app template needs higher load priority than other plugins/apps. For more follow the storefront guide.

xml
<?xml version="1.0" encoding="UTF-8"?>
<manifest xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"  xsi:noNamespaceSchemaLocation="https://raw.githubusercontent.com/shopware/shopware/trunk/src/Core/Framework/App/Manifest/Schema/manifest-2.0.xsd">
    <meta>
        ....
    </meta>
    <storefront>
        <template-load-priority>100</template-load-priority>
    </storefront>
</manifest>

Permissions

Optional, can be omitted if your app does not need permissions. For more follow the app base guide.

xml
<?xml version="1.0" encoding="UTF-8"?>
<manifest xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="https://raw.githubusercontent.com/shopware/shopware/trunk/src/Core/Framework/App/Manifest/Schema/manifest-2.0.xsd">
    <meta>
        ...
    </meta>
    <permissions>
        <read>product</read>
        <create>product</create>
        <update>product</update>

        <delete>order</delete>

        <!-- Since version 6.4.12.0 your app can request additional non-CRUD privileges-->
        <permission>system:cache:info</permission>
    </permissions>
</manifest>

Allowed hosts

A list of all external endpoints your app communicates with (since 6.4.12.0)

xml
<allowed-hosts>
    <host>example.com</host>
</allowed-hosts>

Webhooks

Register webhooks you want to receive, keep in mind that the name needs to be unique. For more follow the app webhook guide.

xml
<?xml version="1.0" encoding="UTF-8"?>
<manifest xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="https://raw.githubusercontent.com/shopware/shopware/trunk/src/Core/Framework/App/Manifest/Schema/manifest-2.0.xsd">
    <meta>
        ...
    </meta>
    <webhooks>
        <webhook name="product-changed" url="https://example.com/event/product-changed" event="product.written"/>
    </webhooks>
</manifest>

Admin extension

Only needed if the Administration should be extended. For more follow the add custom module guide.

xml
<admin>
    <!-- Optional, entry point for the Admin Extension API (since 6.4.12.0) -->
    <base-app-url>https://app.example.com</base-app-url>
    <!-- Register a custom module that is used as a parent menu entry for other modules -->
    <module name="myAdminModules"
            parent="sw-marketing"
            position="50"
    >
        <label>My modules</label>
        <label lang="de-DE">Meine Module</label>
    </module>
    <!-- Register a custom module (iframe), that should be loaded from the given source -->
    <module name="exampleModule"
            source="https://example.com/promotion/view/promotion-module"
            parent="app-MyExampleApp-myAdminModules"
    >
        <label>Example Module</label>
        <label lang="de-DE">Beispiel Modul</label>
    </module>
    <!-- Register a module that is opened from the app store and your list of installed apps -->
    <main-module source="https://example.com/main-module"/>
    <!-- Register action buttons that should be displayed in the detail and listing pages of the Administration -->
    <!-- view is one of: "list", "detail" -->
    <action-button action="setPromotion" entity="promotion" view="detail" url="https://example.com/promotion/set-promotion">
        <label>set Promotion</label>
    </action-button>
    <action-button action="deletePromotion" entity="promotion" view="detail" url="https://example.com/promotion/delete-promotion">
        <label>delete Promotion</label>
    </action-button>
    <action-button action="restockProduct" entity="product" view="list" url="https://example.com/restock">
        <label>restock</label>
    </action-button>
</admin>

Custom fields

Add your custom fields easily via the manifest.xml. For more follow the custom fields app guide.

xml
<?xml version="1.0" encoding="UTF-8"?>
<manifest xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="https://raw.githubusercontent.com/shopware/shopware/trunk/src/Core/Framework/App/Manifest/Schema/manifest-2.0.xsd">
    <meta>
        ...
    </meta>
    <custom-fields>
        <!-- register each custom field set you may want to add -->
        <custom-field-set>
            <!-- the technical name of the custom field set, needs to be unique, therefor use your vendor prefix -->
            <name>swag_example_set</name>
            <!-- Translatable, the label of the field set -->
            <label>Example Set</label>
            <label lang="de-DE">Beispiel-Set</label>
            <!-- define the entities to which your field set should be assigned -->
            <related-entities>
                <order/>
            </related-entities>
            <!-- define the fields in your set -->
            <fields>
                <!-- the element type, defines the type of the field -->
                <!-- the name needs to be unique, therefore use your vendor prefix -->
                <text name="swag_code">
                    <!-- Translatable, the label of the field -->
                    <label>Example field</label>
                    <!-- Optional, Default = 1, order your fields by specifying the position -->
                    <position>1</position>
                    <!-- Optional, Default = false, mark a field as required -->
                    <required>false</required>
                    <!-- Optional, Translatable, the help text for the field -->
                    <help-text>Example field</help-text>
                </text>
                <float name="swag_test_float_field">
                    <label>Test float field</label>
                    <label lang="de-DE">Test-Kommazahlenfeld</label>
                    <help-text>This is an float field.</help-text>
                    <position>2</position>
                    <!-- some elements allow more configuration, like placeholder, main and max values etc. -->
                    <!-- Your IDE should give you pretty good autocompletion support to explore the configuration for a given type -->
                    <placeholder>Enter an float...</placeholder>
                    <min>0.5</min>
                    <max>1.6</max>
                    <steps>0.2</steps>
                </float>
            </fields>
        </custom-field-set>
    </custom-fields>
</manifest>

Cookies

Add a single cookie to the consent manager. For more follow the cookies with apps guide.

xml
<?xml version="1.0" encoding="UTF-8"?>
<manifest xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="https://raw.githubusercontent.com/shopware/shopware/trunk/src/Core/Framework/App/Manifest/Schema/manifest-2.0.xsd">
    <meta>
        <name>ExampleAppWithCookies</name>
        <version>1.0.0</version>
        <!-- other meta data goes here -->
    </meta>
    <cookies>
        <cookie>
            <cookie>my-cookie</cookie>
            <snippet-name>example-app-with-cookies.my-cookie.name</snippet-name>
            <snippet-description>example-app-with-cookies.my-cookie.description</snippet-description>
            <value>a static value for the cookie</value>
            <!-- Expiration in days -->
            <expiration>1</expiration>
        </cookie>
    </cookies>
</manifest>

Add a cookie group to the consent manager. For more follow the cookies with apps guide.

xml
<?xml version="1.0" encoding="UTF-8"?>
<manifest xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="https://raw.githubusercontent.com/shopware/shopware/trunk/src/Core/Framework/App/Manifest/Schema/manifest-2.0.xsd">
    <meta>
        <name>ExampleAppWithCookies</name>
        <version>1.0.0</version>
        <!-- other meta data goes here -->
    </meta>
    <cookies>
        <group>
            <snippet-name>example-app-with-cookies.cookie-group.name</snippet-name>
            <snippet-description>example-app-with-cookies.cookie-group.description</snippet-description>
            <entries>
                <cookie>
                    <cookie>my-cookie</cookie>
                    <snippet-name>example-app-with-cookies.my-cookie.name</snippet-name>
                    <snippet-description>example-app-with-cookies.my-cookie.description</snippet-description>
                    <value>a static value for the cookie</value>
                    <!-- Expiration in days -->
                    <expiration>1</expiration>
                </cookie>
            </entries>
        </group>
    </cookies>
</manifest>

Payments

Add your payment methods via payments and handle your synchronous and asynchronous via an external app-server. For more follow the app payment guide.

xml
<?xml version="1.0" encoding="UTF-8"?>
<manifest xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="https://raw.githubusercontent.com/shopware/shopware/trunk/src/Core/Framework/App/Manifest/Schema/manifest-2.0.xsd">
    <meta>
        <!-- The name of the app should not change. Otherwise, all payment methods are created as duplicates. -->
        <name>PaymentApp</name>
        <!-- ... -->
    </meta>

    <payments>
        <payment-method>
            <!-- The identifier of the payment method should not change. Otherwise, a separate method is created. -->
            <identifier>asynchronousPayment</identifier>
            <name>Asynchronous payment</name>
            <name lang="de-DE">Asynchrone Zahlung</name>
            <description>This payment method requires forwarding to payment provider.</description>
            <description lang="de-DE">Diese Zahlungsmethode erfordert eine Weiterleitung zu einem Zahlungsanbieter.</description>
            <pay-url>https://payment.app/async/pay</pay-url>
            <finalize-url>https://payment.app/async/finalize</finalize-url>
            <!-- This optional path to this icon must be relative to the manifest.xml -->
            <icon>Resources/paymentLogo.png</icon>
        </payment-method>

        <payment-method>
            <!-- The identifier of the payment method should not change. Otherwise a separate method is created. -->
            <identifier>synchronousPayment</identifier>
            <name>Synchronous payment</name>
            <name lang="de-DE">Synchrone Zahlung</name>
            <description>This payment method does everything in one request.</description>
            <description lang="de-DE">Diese Zahlungsmethode arbeitet in einem Request.</description>
            <!-- This URL is optional for synchronous payments (see below). -->
            <pay-url>https://payment.app/sync/process</pay-url>
        </payment-method>

        <payment-method>
            <!-- The identifier of the payment method should not change. Otherwise a separate method is created. -->
            <identifier>simpleSynchronousPayment</identifier>
            <name>Simple Synchronous payment</name>
            <name lang="de-DE">Einfache synchrone Zahlung</name>
            <description>This payment will not do anything and stay on 'open' after order.</description>
            <description lang="de-DE">Diese Zahlungsmethode wird die Transaktion auf 'offen' belassen.</description>
            <!-- No URL is provided. -->
        </payment-method>

        <payment-method>
            <!-- The identifier of the payment method should not change. Otherwise a separate method is created. -->
            <identifier>preparedPayment</identifier>
            <name>Payment, that offers everything</name>
            <name lang="de-DE">Eine Zahlungsart, die alles kann</name>
            <validate-url>https://payment.app/prepared/validate</validate-url>
            <capture-url>https://payment.app/prepared/capture</capture-url>
            <!-- This optional path to this icon must be relative to the manifest.xml -->
            <icon>Resources/paymentLogo.png</icon>
        </payment-method>

        <payment-method>
            <!-- The identifier of the payment method should not change. Otherwise a separate method is created. -->
            <identifier>refundPayment</identifier>
            <name>Refund payments</name>
            <name lang="de-DE">Einfache Erstattungen</name>
            <refund-url>https://payment.app/refund</refund-url>
            <!-- This optional path to this icon must be relative to the manifest.xml -->
            <icon>Resources/paymentLogo.png</icon>
        </payment-method>

        <payment-method>
            <!-- The identifier of the payment method should not change. Otherwise a separate method is created. -->
            <identifier>recurringPayment</identifier>
            <name>Recurring payments</name>
            <name lang="de-DE">Einfache wiederkehrende Zahlungen</name>
            <recurring-url>https://payment.app/recurring</recurring-url>
            <!-- This optional path to this icon must be relative to the manifest.xml -->
            <icon>Resources/paymentLogo.png</icon>
        </payment-method>
    </payments>
</manifest>

Shipping methods

Add your shipping methods via shipping-methods and handle your synchronous and asynchronous via an external app-server. For more follow the shipping methods guide.

xml
<?xml version="1.0" encoding="UTF-8" ?>
<manifest xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
          xsi:noNamespaceSchemaLocation="https://raw.githubusercontent.com/shopware/shopware/trunk/src/Core/Framework/App/Manifest/Schema/manifest-2.0.xsd">
    <meta>
        <!-- Make sure that the name of your app does not change anymore, otherwise there will be duplicates of your shipping methods -->
        <name>NameOfYourShippingMethodApp</name>
        <!-- ... -->
    </meta>
    <shipping-methods>
        <shipping-method>
            <!-- The identifier should not change after the first release -->
            <identifier>NameOfYourFirstShippingMethod</identifier>
            <name>First shipping method</name>

            <delivery-time>
                <!-- Requires a new generated UUID for your new delivery time -->
                <id>c8864e36a4d84bd4a16cc31b5953431b</id>
                <name>From 2 to 4 days</name>
                <min>2</min>
                <max>4</max>
                <unit>day</unit>
            </delivery-time>
        </shipping-method>
    </shipping-methods>
</manifest>

Rule conditions

The identifier of the rule condition must be unique should not change. Otherwise a separate rule condition is created, and uses of the old one are lost. For more follow the rule conditions guide.

xml
<?xml version="1.0" encoding="UTF-8"?>
<manifest xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="https://raw.githubusercontent.com/shopware/shopware/trunk/src/Core/Framework/App/Manifest/Schema/manifest-2.0.xsd">
    <meta>
        <!-- ... -->
    </meta>
    <rule-conditions>
        <rule-condition>
            <!-- The identifier of the rule condition must be unique should not change. Otherwise a separate rule condition is created and uses of the old one are lost. -->
            <identifier>my_custom_condition</identifier>
            <!-- Translatable, a name of your rule condition -->
            <name>Custom condition</name>
            <name lang="de-DE">Eigene Bedingung</name>
            <!-- A thematic group the condition should be assigned too, available groups are: general, customer, cart, item, promotion, misc -->
            <group>misc</group>
            <!-- The *.twig file that contains the corresponding script for the condition. It must be placed in the directory Resources/scripts/rule-conditions starting from your app's root directory -->
            <script>custom-condition.twig</script>
            <!-- Define the fields you want the user to fill out for use as data within your condition -->
            <constraints>
                <!-- the element type, defines the type of the field -->
                <!-- the elements available here are the same as for custom fields -->
                <single-select name="operator">
                    <placeholder>Choose an operator...</placeholder>
                    <placeholder lang="de-DE">Bitte Operatoren wählen</placeholder>
                    <options>
                        <option value="=">
                            <name>Is equal to</name>
                            <name lang="de-DE">Ist gleich</name>
                        </option>
                        <option value="!=">
                            <name>Is not equal to</name>
                            <name lang="de-DE">Ist nicht gleich</name>
                        </option>
                    </options>
                    <required>true</required>
                </single-select>
                <text name="firstName">
                    <placeholder>Enter first name</placeholder>
                    <placeholder lang="de-DE">Bitte Vornamen eingeben</placeholder>
                    <required>true</required>
                </text>
            </constraints>
        </rule-condition>
    </rule-conditions>
</manifest>

Tax

Add an external tax provider to your app that is calculating your taxes on the fly for complex tax setups. For more follow the tax provider guide.

xml
<?xml version="1.0" encoding="UTF-8"?>
<manifest xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="https://raw.githubusercontent.com/shopware/shopware/trunk/src/Core/Framework/App/Manifest/Schema/manifest-2.0.xsd">
    <meta>
        <!-- The name of the app should not change. Otherwise all payment methods are created as duplicates. -->
        <name>PaymentApp</name>
        <!-- ... -->
    </meta>
    <tax>
        <tax-provider>
            <!-- Unique identifier of the tax provider -->
            <identifier>myCustomTaxProvider</identifier>
            <!-- Display name of the tax provider -->
            <name>My custom tax provider</name>
            <!-- Priority of the tax provider - can be changed in the administration as well -->
            <priority>1</priority>
            <!-- Url of your implementation - is called during checkout to provide taxes -->
            <process-url>https://tax-provider.app/provide-taxes</process-url>
        </tax-provider>
    </tax>
</manifest>