diff --git a/docs/backend/generic-setup.md b/docs/backend/generic-setup.md index c20b21664..19192f545 100644 --- a/docs/backend/generic-setup.md +++ b/docs/backend/generic-setup.md @@ -11,66 +11,67 @@ myst: # GenericSetup -GenericSetup is a framework to modify the Plone site during add-on package installation and uninstallation. - -It provides XML-based rules to change the site settings. - ```{todo} remove archetypes example code everywhere ``` +This chapter describes how to use GenericSetup to modify the Plone site during add-on package installation and uninstallation. + + +## Usage overview + GenericSetup is mainly used to prepare the Plone site for add-on packages, by: - registering Registry entries, such as resources and configuration - setting various properties - registering portlets -- registering portal_catalog search query indexes -- providing upgrade steps for addon version upgrades +- registering `portal_catalog` search query indexes +- providing upgrade steps for add-on version upgrades +- enable specific behaviors - and other preparations -GenericSetup is mostly used to apply an add-on's specific changes to the site configuration and to enable specific behaviors when the add-on installer is run. - +GenericSetup provides XML-based rules to change the site settings. GenericSetup XML files are usually in a {file}`profiles/default` folder inside the add-on package. All run-time through-the-web ({term}`TTW`) configurable items—for example, viewlet order through the `/@@manage-viewlets` page—are made repeatable using GenericSetup profile files. -You can always change the configuration options through Plone or using the Management Interface, and then you export the resulting profile as an XML file, using the *Export* tab in `portal_setup` accessible from the Management Interface. +You can always change the configuration options through either Plone or the {term}`Zope Management Interface` (ZMI), and then export the resulting profile as an XML file. +To export, navigate to {menuselection}`Site Setup --> Management Interface`, then click {guilabel}`portal_setup`, and finally click the {guilabel}`Export` tab to select the steps to export. -Directly editing XML profile files does not change anything on the site, even after Zope restart. -This is because run-time TTW configurable items are stored in the database. +Directly editing XML profile files does not change anything on the site, even after a Zope restart. +This is because run-time TTW configurable items are stored in the database, instead of the file system. -If you edit profile files, you need to either reimport the edited files using the `portal_setup` tool or fully rerun the add-on package installer in Plone control panel. - -This import will read XML files and change the Plone database accordingly. +If you edit profile files, you need to either reimport the edited files using the `portal_setup` tool or fully rerun the add-on package installer by navigating to {menuselection}`Site Setup --> Add-ons`. +The import or rerun will read XML files and change the Plone database accordingly. ```{note} -Difference between ZCML and GenericSetup - -ZCML changes affect loaded Python code in **all** sites inside Zope whereas GenericSetup XML files affect only one Plone site and its database. +ZCML changes affect loaded Python code in all sites inside Zope, whereas GenericSetup XML files affect only one Plone site and its database. GenericSetup XML files are always database changes. -Relationship between ZCML and site-specific behavior is usually done using {doc}`layers `. -ZCML directives, like viewlets and views, are registered to be active only on a certain layer using `layer` attribute. +Creating relationships between ZCML and site-specific behavior is usually done using {doc}`layers `. +ZCML directives, like viewlets and views, are registered to be active only on a certain layer using the `layer` attribute. When GenericSetup XML is imported through `portal_setup`, or the add-on package installer is run for a Plone site, the layer is activated for the particular site only, enabling all views registered for this layer. ``` ```{note} -The `metadata.xml` file (add-on dependency and version information) is read during Plone start-up. -If this file has problems, your add-on might not appear in the installer control panel. +The {file}`metadata.xml` file, which contains add-on dependency and version information, is read during Plone start up. +If this file has problems, your add-on might not appear in the add-on installer control panel. ``` +```{seealso} +- [GenericSetup package page](https://pypi.python.org/pypi/Products.GenericSetup) +- [GenericSetup source code](https://github.com/zopefoundation/Products.GenericSetup) +``` -- [GenericSetup package page](https://pypi.python.org/pypi/Products.GenericSetup). -- [GenericSetup source code](https://github.com/zopefoundation/Products.GenericSetup). -## Creating A Profile +## Create a profile -You use `` directive in your add-on package's `configure.zcml`. +Use the `` directive in your add-on package's {file}`configure.zcml`. The name for the default profile executed by the Plone add-on installer is `default`. -If you need different profiles, for example for unit testing, you can declare them here. +If you need different profiles, for example, for unit testing, you can declare them here. -XML files for the `default` profile go in the `profiles/default` folder inside your add-on package. +XML files for the `default` profile go in the {file}`profiles/default` folder inside your add-on package. ```xml ``` -### Multiple Profiles +### Multiple profiles -When you have more than one profile in your add-on package, the add-ons control panel needs to decide which one to use when you install it. +When you have more than one profile in your add-on package, the add-ons control panel decides which one to use when you install it. -Since Plone 5.1, when there is a `default` profile, it is always used as the installation profile, regardless of other profile names. +When there is a `default` profile, it's used as the installation profile, except when this `default` profile is marked in an `INonInstallable` utility. +In this case, it's ignored, and Plone falls back to using the first profile sorted alphabetically by `name`. -Exception: when this `default` profile is marked in an `INonInstallable` utility, it is ignored and Plone falls back to using the first from the alphabetical sorting. - -```{note} -In Plone 5.0 and lower, -the profiles are sorted alphabetically by id, -and the first one is chosen. -If you have profiles `base` and `default`, -the `base` profile is installed. -It is recommended to let `default` be the alphabetically first profile. +```{versionchanged} Plone 5.1 +The profile `name` of `default` now takes precedence over the `name` of the first profile sorted alphabetically. +In previous versions, the first profile sorted alphabetically by `name` was chosen without regard to the `default` name. ``` -## Add-on-specific Issues -Add-on packages may contain: +## Add-on properties + +Add-on packages may contain any of the following items. -- A default GenericSetup XML profile which is automatically run when the package is installed using the quick-installer. - The profile name is usually `default`. -- Other profiles which the user may install using the `portal_setup` *Import* tab, or which can be manually enabled for unit tests. -- An "Import various" step, which runs Python code every time the GenericSetup XML profile is installed. - See {ref}`custominstall`. -- A `pre_handler` or `post_handler` when you use GenericSetup 1.8.2 or higher. - See note at {ref}`custominstall`. +- A default GenericSetup XML profile, which is automatically run when the package is installed using the quick-installer. + The profile name is usually `default`. +- Other profiles, which the user may install using the ZMI {guilabel}`portal_setup` under the {guilabel}`Export` tab, or which can be manually enabled for unit tests. +- An `setup_various` step, which runs Python code every time the GenericSetup XML profile is installed. + See {ref}`genericsetup-custom-installer-code-label`. +- A `pre_handler` or `post_handler` when you use GenericSetup 1.8.2 or later. + See {ref}`genericsetup-custom-installer-code-label`. -For more information about custom import steps, see: +```{seealso} +[Custom import steps](https://web.archive.org/web/20151016163743/https://plone.293351.n2.nabble.com/indexing-of-content-created-by-Generic-Setup-td4454703.html) +``` -- -## Listing Available Profiles +## List available profiles -Example: +List all known profiles for the Plone instance. -``` -# List all profiles know to the Plone instance. +```python setup_tool = self.portal.portal_setup profiles = setup_tool.listProfileInfo() for profile in profiles: - print str(profile) + print str(profile) ``` Sample results: @@ -157,40 +154,46 @@ Sample results: ... ``` -## Installing A Profile -This is usually unit test specific question how to enable certain add-ons for unit testing. +## Install a profile + +This section describes how to install a profile and enable add-ons for unit tests. + -### plone.app.testing +### `plone.app.testing` -See [Product and profile installation](http://docs.plone.org/external/plone.app.testing/docs/source/README.html#product-and-profile-installation). +See [Product and profile installation](https://github.com/plone/plone.app.testing#product-and-profile-installation). -### Manually + +### Manual installation You might want to install profiles manually if they need to be enabled only for certain tests. -The profile name is in the format `profile-${package_name}:${profile id}` +The profile name is in the format `profile-${package_name}:${profile id}`. -Unit testing example: +Run the extended profile of the `your.addonpackage` package for unit tests. -``` -# Run the extended profile of the "your.addonpackage" package. -setup_tool.runAllImportStepsFromProfile('profile-your.addonpackage:extended') +```python +setup_tool.runAllImportStepsFromProfile('your.addonpackage:extended') ``` -```{note} -Since Products.GenericSetup 1.8.0 the `profile-` part is optional. -The code can handle both. +```{versionchanged} Products.GenericSetup 1.8.0 +Since `Products.GenericSetup` 1.8.0, the `profile-` prefix is optional. +In previous versions, the prefix was required, for example, `profile-your.addonpackage:extended`. +GenericSetup supports both forms. ``` -## Missing Upgrade Procedure -In the Add-ons control panel you may see a warning that your add-on package is [missing an upgrade procedure](http://stackoverflow.com/questions/15316583/how-to-define-a-procedure-to-upgrade-an-add-on). +## Missing upgrade procedure + +In the {guilabel}`Add-ons` control panel, you may see a warning that your add-on package is [missing an upgrade procedure](https://stackoverflow.com/questions/15316583/how-to-define-a-procedure-to-upgrade-an-add-on). This means you need to write some {ref}`genericsetup-upgrade-steps-label`. -## Uninstall Profile +(genericsetup-uninstall-profile-label)= + +## Uninstall profile When you deactivate an add-on in the control panel, Plone looks for a profile with the name `uninstall` and applies it. @@ -204,12 +207,10 @@ If you do activate the add-on, no deactivate button will be shown. GenericSetup profile can contain dependencies to other add-on package installers and profiles. -For example, if you want to declare a dependency to the *your.addonpackage* package, that it is automatically installed when your add-on is installed, -you can use the declaration below. +For example, if you want to declare a dependency to the `your.addonpackage` package that it is automatically installed when your add-on is installed, then use the declaration below. +This way you can be sure that all layers, portlets, and other features which require database changes are usable from `your.addonpackage` when it is run. -This way you can be sure that all layers, portlets and other features which require database changes are usable from *your.addonpackage* when it is run. - -`metadata.xml`: +Edit {file}`metadata.xml`. ```xml @@ -221,7 +222,7 @@ This way you can be sure that all layers, portlets and other features which requ ``` -*your.addonpackage* declares the profile in its configure.zcml: +`your.addonpackage` declares the profile in its {file}`configure.zcml`. ```xml @@ -261,49 +262,38 @@ To declare a dependency on the `simple` profile of `Products.PluggableAuthServic ``` -## Metadata version numbers - -Some old add-on packages may have a `metadata.xml` without version number, but this is considered bad practice. - -What should the version number in your `metadata.xml` be? - -This mostly matters when you are adding upgrade steps, see also the [Upgrade steps] section. - -Upgrade steps have a sort order in which they are executed. This used to be alphabetical sorting. -When you had eleven upgrade steps, marked from 1 through 11, alphabetical sorting meant this order: 1, 10, 11, 2, 3, etc. +## Metadata version numbers -If you are seeing this, then you are using an old version of GenericSetup. +The metadata `version` number in your {file}`metadata.xml` indicates the version of your add-on package. +It's used to determine whether the add-on package needs to be upgraded. -You want numerical sorting here, which is correctly done currently. Versions with dots work fine too. +Upgrade steps are executed in the Python version sort order, according to [Version specifiers](https://packaging.python.org/en/latest/specifications/version-specifiers/). -They get ordered just like they would when used for packages on PyPI. +```{note} +Legacy add-on packages might not have a version number, or use an integer version number. +In old versions of GenericSetup, sorting was done alphabetically, not according to the Python version specifiers. +If you experience problems with upgrade steps, you might need to upgrade GenericSetup, or add a metadata `version` number to align with your package's version number. +``` -Best practice for all versions of GenericSetup is this: +```{seealso} +{ref}`genericsetup-upgrade-steps-label` +``` -- Start with 1000. - This avoids problems with ancient GenericSetup that used alphabetical sorting. -- Simply increase the version by 1 each time you need a new metadata version. - For example: 1001, 1002, etc. -- If your add-on package version number changes, but your profile stays the same and no upgrade step is needed, you should **not** change the metadata version. - There is no need. -- If you make changes for a new major release, you should increase the metadata version significantly. - This leaves room for small metadata version increases on a maintenance branch. - Example: - You have branch master with version 1025. - You make backwards incompatible changes and you increase the version to 2000. - You create a maintenance branch where the next metadata version will be 1026. (genericsetup-custom-installer-code-label)= -## Custom Installer Code (`setuphandlers.py`) +## Custom installer code -Besides out-of-the-box XML steps which provide both install and uninstall, -GenericSetup provides a way to run custom Python code when your add-on package is installed and uninstalled. +In addition to upgrade steps to install and uninstall add-ons, GenericSetup provides a way to run custom Python code when your add-on package is installed and uninstalled. +The following examples show how to do this. -In `configure.zcml`: +First, edit {file}`configure.zcml`, adding a `pre_handler` and `post_handler` attribute to the `registerProfile` element. + +```{code-block} xml +:linenos: +:emphasize-lines: 11-13 -``` ``` -In `setuphandlers.py`: +Then edit {file}`setuphandlers.py`, adding the Python functions `run_before` and `run_after` according to the `pre_handler` and `post_handler` attributes. ```python def run_before(context): # This is run before running the first import step of - # the default profile. context is portal_setup. + # the default profile. The context is portal_setup. # If you need the same context as you would get in # an import step, like setup_various below, do this: profile_id = 'profile-your.addonpackage:default' good_old_context = context._getImportContext(profile_id) - ... + # ... def run_after(context): # This is run after running the last import step of - # the default profile. context is portal_setup. - ... + # the default profile. The context is portal_setup. + # ... ``` -The best practice is to create a `setuphandlers.py` file which contains a function `setup_various()` which runs the required Python code -to make changes to Plone site object. - +The best practice is to create a {file}`setuphandlers.py` file, and include a function `setup_various()` which runs the required Python code to make changes to the Plone site object. This function is registered as a custom `genericsetup:importStep` in XML. -```{note} -When you write a custom `importStep`, remember to write uninstallation code as well. -``` - However, the trick is that all GenericSetup import steps, including your custom step, are run for *every* add-on package when they are installed. -If your need to run code which is **specific to your add-on install only** you need to use a marker text file which is checked by the GenericSetup context. +If you need to run code which is **specific to your add-on install only** you need to use a marker text file which is checked by the GenericSetup context. -Also you need to register this custom import step in `configure.zcml`: +Also, you need to register this custom import step in {file}`configure.zcml`. ```xml ``` +````{tip} +When you write a custom `importStep`, remember to write uninstallation code as well. +```{seealso} +{ref}`genericsetup-uninstall-profile-label` +``` +```` + You can run other steps before yours by using the `depends` directive. For instance, if your import step depends on a content type to be installed first, you must use: @@ -464,7 +455,7 @@ See {ref}`genericsetup-generic-setup-files-label` for a list. ``` -(genericsetup-upgrade-steps-label)- +(genericsetup-upgrade-steps-label)= ## Upgrade Steps @@ -584,7 +575,7 @@ Some of the most used ones are here: - - -After restarting Zope, your upgrade step should be visible in the Management Interface: +After restarting Zope, your upgrade step should be visible in the ZMI: the `portal_setup` tool has a tab `Upgrades`. Select your package profile to see which upgrade steps Zope knows about for your add-on. @@ -730,7 +721,7 @@ For example, if you only need to change the 'Allow anonymous to view about' prop True - ``` @@ -758,7 +749,7 @@ Example: ``` ```{note} -In the portal_actions tool, in the Management Interface, you will see an i18n domain specified for each action. +In the portal_actions tool, in the ZMI, you will see an i18n domain specified for each action. ``` - `catalog.xml`: no i18n needed @@ -796,7 +787,7 @@ Example: - `workflows`: use the **plone** domain -(genericsetup-generic-setup-files-label)- +(genericsetup-generic-setup-files-label)= ## Generic Setup Files @@ -1478,7 +1469,7 @@ ValueError: The permission Pass the bridge is invalid. ``` A permission is created on the Zope level when it is used in code. -See {doc}`Creating permissions `. +See {ref}`backend-security-permissions-label`. When a role in a permission does not exist, it is silently ignored. The roles listed in a permission are not added. @@ -1500,14 +1491,13 @@ This will reset the permission to the same settings as on the Zope level: ```{eval-rst} .. automodule:: Products.GenericSetup.rolemap - :members: importRolemap RolemapImportConfigurator - + :members: importRolemap, RolemapImportConfigurator ``` ### sharing.xml The sharing.xml file let you add custom roles to the sharing tab. -For reference, visit: {ref}`security-label`. +For reference, visit {doc}`/backend/security`. ### typeinfo @@ -1747,4 +1737,4 @@ Next to this, the `workflows` directory is checked. This contains sub directories with the same name as the workflows. Each sub directory contains a file `definition.xml` with the definition for this workflow. -See {ref}`workflows-label`. +See {doc}`/backend/workflows`. diff --git a/docs/developer-guide/create-a-backend-add-on.md b/docs/developer-guide/create-a-backend-add-on.md index e51e1d9f0..1a535cde1 100644 --- a/docs/developer-guide/create-a-backend-add-on.md +++ b/docs/developer-guide/create-a-backend-add-on.md @@ -19,7 +19,7 @@ Follow the section {ref}`create-project-cookieplone-system-requirements` to set ## Generate the add-on project with `plonecli` -Choose your desired local development base folder and run the following command to create an addon project with `plonecli` +Choose your desired local development base folder and run the following command to create an add-on project with `plonecli`. ```shell uvx plonecli create addon @@ -139,7 +139,7 @@ Currently documented subtemplates: - behavior: {ref}`backend-behaviors-label` - content_type: {ref}`creating-content-types-label` - controlpanel: {ref}`control-panels-label` -- form: {reg}`forms-label` +- form: {ref}`forms-label` - mockup_pattern: {ref}`mockup-and-patternslib-label` - theme_barceloneta: {ref}`create-a-theme-add-on-label` diff --git a/docs/glossary.md b/docs/glossary.md index 1ee4f8e3c..a3bdbdb78 100644 --- a/docs/glossary.md +++ b/docs/glossary.md @@ -159,6 +159,7 @@ Dexterity Dublin Core The Dublin Core Schema is a small set of vocabulary terms that can be used to describe web resources (video, images, web pages, etc.), as well as physical resources such as books or CDs, and objects like artworks. +Zope Management Interface ZMI The {term}`Zope` Management Interface. The ZMI is a direct interface into the backend software stack of Plone. diff --git a/styles/config/vocabularies/Plone/accept.txt b/styles/config/vocabularies/Plone/accept.txt index c0b583ac1..a4a79779a 100644 --- a/styles/config/vocabularies/Plone/accept.txt +++ b/styles/config/vocabularies/Plone/accept.txt @@ -61,6 +61,7 @@ transpilation transpile[drs]{0,1} [Uu]ncomment [Uu]nhide +uninstallation unregister untranspiled UUID