[docs][backport]Backportapalooza 10 (#71621)

* Feature freeze date has been merged with Ansible-2.10.0beta1 (#71494)

(cherry picked from commit c586d436fa)

* Add --allow-disabled to sanity docs (#71524)

(cherry picked from commit bc6461432e)

* Update intro_patterns.rst (#71542)

Call out the trailing comma when specifying a single host. Small snag that took me a while to notice.

(cherry picked from commit ec3920cef1)

* ansible-vault: Fix typo in help message (#71485)

(cherry picked from commit 215eb730e1)

* update install for 2.10 (#71543)

* update install for 2.10

(cherry picked from commit f75223d2c6)

* User guide overhaul, Table of Contents (#71553)

(cherry picked from commit b694dbadfe)

* update backport instructions for 2.11 (#71567)

* update backport instructions in docs/docsite/rst/community/development_process.rst

Co-authored-by: Matt Martz <matt@sivel.net>
(cherry picked from commit 7f9258b024)

* More docs updates to reflect collections ecosystem (#71597)

(cherry picked from commit 96aee766f4)

* DOCS: Mentions ansible-base, adds collections pointers to Community and Dev Guides (#71480)

(cherry picked from commit 29b20bd1b1)

Co-authored-by: Toshio Kuratomi <a.badger@gmail.com>
Co-authored-by: Amin Vakil <info@aminvakil.com>
Co-authored-by: Matt Deacalion <matt@dirtymonkey.co.uk>
Co-authored-by: Fabien Malfoy <fabien.malfoy@laposte.net>
Co-authored-by: Alicia Cozine <879121+acozine@users.noreply.github.com>
pull/71648/head
Sandra McCann 4 years ago committed by GitHub
parent 7caa7e1162
commit 1af7c6c003
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

@ -4,15 +4,19 @@
The Ansible Development Cycle The Ansible Development Cycle
***************************** *****************************
The Ansible development cycle happens on two levels. At a macro level, the team plans releases and tracks progress with roadmaps and projects. At a micro level, each PR has its own lifecycle. Ansible developers (including community contributors) add new features, fix bugs, and update code in many different repositories. The `ansible/ansible repository <https://github.com/ansible/ansible>`_ contains the code for basic features and functions, such as copying module code to managed nodes. This code is also known as ``ansible-base``. Other repositories contain plugins and modules that enable Ansible to execute specific tasks, like adding a user to a particular database or configuring a particular network device. These repositories contain the source code for collections.
Development on ``ansible-base`` occurs on two levels. At the macro level, the ``ansible-base`` developers and maintainers plan releases and track progress with roadmaps and projects. At the micro level, each PR has its own lifecycle.
Development on collections also occurs at the macro and micro levels. Each collection has its own macro development cycle. For more information on the collections development cycle, see :ref:`contributing_maintained_collections`. The micro-level lifecycle of a PR is similar in collections and in ``ansible-base``.
.. contents:: .. contents::
:local: :local:
Macro development: roadmaps, releases, and projects Macro development: ``ansible-base`` roadmaps, releases, and projects
=================================================== =====================================================================
If you want to follow the conversation about what features will be added to Ansible for upcoming releases and what bugs are being fixed, you can watch these resources: If you want to follow the conversation about what features will be added to ``ansible-base`` for upcoming releases and what bugs are being fixed, you can watch these resources:
* the :ref:`roadmaps` * the :ref:`roadmaps`
* the :ref:`Ansible Release Schedule <release_and_maintenance>` * the :ref:`Ansible Release Schedule <release_and_maintenance>`
@ -27,7 +31,7 @@ If you want to follow the conversation about what features will be added to Ansi
Micro development: the lifecycle of a PR Micro development: the lifecycle of a PR
======================================== ========================================
Ansible accepts code through **pull requests** ("PRs" for short). GitHub provides a great overview of `how the pull request process works <https://help.github.com/articles/about-pull-requests/>`_ in general. The ultimate goal of any pull request is to get merged and become part of a collection or ansible-base. If you want to contribute a feature or fix a bug in ``ansible-base`` or in a collection, you must open a **pull request** ("PR" for short). GitHub provides a great overview of `how the pull request process works <https://help.github.com/articles/about-pull-requests/>`_ in general. The ultimate goal of any pull request is to get merged and become part of a collection or ``ansible-base``.
Here's an overview of the PR lifecycle: Here's an overview of the PR lifecycle:
* Contributor opens a PR * Contributor opens a PR
@ -132,7 +136,7 @@ Once a human applies the ``shipit`` label, the :ref:`committers <community_commi
Making your PR merge-worthy Making your PR merge-worthy
=========================== ===========================
We don't merge every PR. Here are some tips for making your PR useful, attractive, and merge-worthy. We do not merge every PR. Here are some tips for making your PR useful, attractive, and merge-worthy.
.. _community_changelogs: .. _community_changelogs:
@ -202,16 +206,16 @@ Here are some examples:
remote_src=True even if mode was not set as a parameter. This failed on remote_src=True even if mode was not set as a parameter. This failed on
filesystems which do not have permission bits (https://github.com/ansible/ansible/issues/29444). filesystems which do not have permission bits (https://github.com/ansible/ansible/issues/29444).
You can find more example changelog fragments in the `changelog directory <https://github.com/ansible/ansible/tree/stable-2.9/changelogs/fragments>`_ for the 2.9 release. You can find more example changelog fragments in the `changelog directory <https://github.com/ansible/ansible/tree/stable-2.10/changelogs/fragments>`_ for the 2.10 release.
Once you've written the changelog fragment for your PR, commit the file and include it with the pull request. After you have written the changelog fragment for your PR, commit the file and include it with the pull request.
.. _backport_process: .. _backport_process:
Backporting merged PRs Backporting merged PRs in ``ansible-base``
====================== ===========================================
All Ansible PRs must be merged to the ``devel`` branch first. After a pull request has been accepted and merged to the ``devel`` branch, the following instructions will help you create a pull request to backport the change to a previous stable branch. All ``ansible-base`` PRs must be merged to the ``devel`` branch first. After a pull request has been accepted and merged to the ``devel`` branch, the following instructions will help you create a pull request to backport the change to a previous stable branch.
We do **not** backport features. We do **not** backport features.
@ -219,7 +223,7 @@ We do **not** backport features.
These instructions assume that: These instructions assume that:
* ``stable-2.9`` is the targeted release branch for the backport * ``stable-2.10`` is the targeted release branch for the backport
* ``https://github.com/ansible/ansible.git`` is configured as a * ``https://github.com/ansible/ansible.git`` is configured as a
``git remote`` named ``upstream``. If you do not use ``git remote`` named ``upstream``. If you do not use
a ``git remote`` named ``upstream``, adjust the instructions accordingly. a ``git remote`` named ``upstream``, adjust the instructions accordingly.
@ -232,7 +236,7 @@ We do **not** backport features.
:: ::
git fetch upstream git fetch upstream
git checkout -b backport/2.9/[PR_NUMBER_FROM_DEVEL] upstream/stable-2.9 git checkout -b backport/2.10/[PR_NUMBER_FROM_DEVEL] upstream/stable-2.10
#. Cherry pick the relevant commit SHA from the devel branch into your feature #. Cherry pick the relevant commit SHA from the devel branch into your feature
branch, handling merge conflicts as necessary: branch, handling merge conflicts as necessary:
@ -247,10 +251,10 @@ We do **not** backport features.
:: ::
git push origin backport/2.9/[PR_NUMBER_FROM_DEVEL] git push origin backport/2.10/[PR_NUMBER_FROM_DEVEL]
#. Submit the pull request for ``backport/2.9/[PR_NUMBER_FROM_DEVEL]`` #. Submit the pull request for ``backport/2.10/[PR_NUMBER_FROM_DEVEL]``
against the ``stable-2.9`` branch against the ``stable-2.10`` branch
#. The Release Manager will decide whether to merge the backport PR before #. The Release Manager will decide whether to merge the backport PR before
the next minor release. There isn't any need to follow up. Just ensure that the automated the next minor release. There isn't any need to follow up. Just ensure that the automated
@ -258,7 +262,7 @@ We do **not** backport features.
.. note:: .. note::
The choice to use ``backport/2.9/[PR_NUMBER_FROM_DEVEL]`` as the The choice to use ``backport/2.10/[PR_NUMBER_FROM_DEVEL]`` as the
name for the feature branch is somewhat arbitrary, but conveys meaning name for the feature branch is somewhat arbitrary, but conveys meaning
about the purpose of that branch. It is not required to use this format, about the purpose of that branch. It is not required to use this format,
but it can be helpful, especially when making multiple backport PRs for but it can be helpful, especially when making multiple backport PRs for

@ -6,7 +6,7 @@ Contributing to the Ansible Documentation
Ansible has a lot of documentation and a small team of writers. Community support helps us keep up with new features, fixes, and changes. Ansible has a lot of documentation and a small team of writers. Community support helps us keep up with new features, fixes, and changes.
Improving the documentation is an easy way to make your first contribution to the Ansible project. You don't have to be a programmer, since most of our documentation is written in YAML (module documentation) or `reStructuredText <http://docutils.sourceforge.net/rst.html>`_ (rST). Some collection-level documentation is written in a subset of `Markdown <https://github.com/ansible/ansible/issues/68119#issuecomment-596723053>`_. If you're using Ansible, you already use YAML in your playbooks. rST and Markdown are mostly just text. You don't even need git experience, if you use the ``Edit on GitHub`` option. Improving the documentation is an easy way to make your first contribution to the Ansible project. You do not have to be a programmer, since most of our documentation is written in YAML (module documentation) or `reStructuredText <http://docutils.sourceforge.net/rst.html>`_ (rST). Some collection-level documentation is written in a subset of `Markdown <https://github.com/ansible/ansible/issues/68119#issuecomment-596723053>`_. If you are using Ansible, you already use YAML in your playbooks. rST and Markdown are mostly just text. You do not even need git experience, if you use the ``Edit on GitHub`` option.
If you find a typo, a broken example, a missing topic, or any other error or omission on this documentation website, let us know. Here are some ways to support Ansible documentation: If you find a typo, a broken example, a missing topic, or any other error or omission on this documentation website, let us know. Here are some ways to support Ansible documentation:
@ -47,7 +47,7 @@ You can also contribute by reviewing open documentation `issues <https://github.
Opening a new issue and/or PR Opening a new issue and/or PR
============================= =============================
If the problem you've noticed is too complex to fix with the ``Edit on GitHub`` option, and no open issue or PR already documents the problem, please open an issue and/or a PR on the ``ansible/ansible`` repo. If the documentation page has no ``Edit on GitHub`` option, check if the page is for a module within a collection. If so, follow the link to the collection on Galaxy and select the ``repo`` button in the upper right corner to find the source repository for that collection and module. The Collection README file should contain information on how to contribute to that collection, or report issues. If the problem you have noticed is too complex to fix with the ``Edit on GitHub`` option, and no open issue or PR already documents the problem, please open an issue and/or a PR on the correct underlying repo - ``ansible/ansible`` for most pages that are not plugin or module documentation. If the documentation page has no ``Edit on GitHub`` option, check if the page is for a module within a collection. If so, follow the link to the collection on Galaxy and select the ``repo`` button in the upper right corner to find the source repository for that collection and module. The Collection README file should contain information on how to contribute to that collection, or report issues.
A great documentation GitHub issue or PR includes: A great documentation GitHub issue or PR includes:
@ -206,7 +206,7 @@ Unfortunately, leftover rST-files from previous document-generating can occasion
Joining the documentation working group Joining the documentation working group
======================================= =======================================
The Documentation Working Group is just getting started, please visit the `community repo <https://github.com/ansible/community>`_ for more information. The Documentation Working Group (DaWGs) meets weekly on Tuesdays on the #ansible-docs channel on freenode IRC. For more information, including links to our agenda and a calendar invite, please visit the `working group page in the community repo <https://github.com/ansible/community/wiki/Docs>`_.
.. seealso:: .. seealso::
:ref:`More about testing module documentation <testing_module_documentation>` :ref:`More about testing module documentation <testing_module_documentation>`

@ -43,7 +43,7 @@ Participate in your local meetup
There are Ansible meetups `all over the world <https://www.meetup.com/topics/ansible/>`_. Join your local meetup. Attend regularly. Ask good questions. Volunteer to give a presentation about how you use Ansible. There are Ansible meetups `all over the world <https://www.meetup.com/topics/ansible/>`_. Join your local meetup. Attend regularly. Ask good questions. Volunteer to give a presentation about how you use Ansible.
If there isn't a meetup near you, we'll be happy to help you `start one <https://www.ansible.com/community/events/ansible-meetups>`_. If there is no meetup near you, we are happy to help you `start one <https://www.ansible.com/community/events/ansible-meetups>`_.
File and verify issues File and verify issues
====================== ======================
@ -58,14 +58,14 @@ Review and submit pull requests
As you become more familiar with how Ansible works, you may be able to fix issues or develop new features yourself. If you think you have a fix for a bug in Ansible, or if you have a new feature that you would like to share with millions of Ansible users, read all about the :ref:`Ansible development process <community_development_process>` and and :ref:`how to contribute to collections <contributing_maintained_collections>` to learn how to get your code accepted into Ansible. As you become more familiar with how Ansible works, you may be able to fix issues or develop new features yourself. If you think you have a fix for a bug in Ansible, or if you have a new feature that you would like to share with millions of Ansible users, read all about the :ref:`Ansible development process <community_development_process>` and and :ref:`how to contribute to collections <contributing_maintained_collections>` to learn how to get your code accepted into Ansible.
Another good way to help is to review pull requests that other Ansible users have submitted. The Ansible community keeps a full list of `open pull requests by file <https://ansible.sivel.net/pr/byfile.html>`_, so if there's a particular module or plug-in that particularly interests you, you can easily keep track of all the relevant new pull requests and provide testing or feedback. Another good way to help is to review pull requests that other Ansible users have submitted. The Ansible community keeps a full list of `open pull requests by file <https://ansible.sivel.net/pr/byfile.html>`_, so if a particular module or plugin interests you, you can easily keep track of all the relevant new pull requests and provide testing or feedback.
Become a collection maintainer Become a collection maintainer
============================== ==============================
Once you have learned about the development process and have contributed code to a collection, we encourage you to become a maintainer of that collection. There are hundreds of modules in dozens of Ansible collections, and the vast majority of them are written and maintained entirely by members of the Ansible community. Once you have learned about the development process and have contributed code to a collection, we encourage you to become a maintainer of that collection. There are hundreds of modules in dozens of Ansible collections, and the vast majority of them are written and maintained entirely by members of the Ansible community.
To learn more about the responsibilities of being an Ansible module maintainer, please read our :ref:`module maintainer guidelines <maintainers>`. To learn more about the responsibilities of being an Ansible module maintainer, please read our :ref:`collection maintainer guidelines <maintainers>`.
.. _community_working_groups: .. _community_working_groups:

@ -8,7 +8,7 @@ Welcome to the Ansible Community Guide!
The purpose of this guide is to teach you everything you need to know about being a contributing member of the Ansible community. All types of contributions are welcome and necessary to Ansible's continued success. The purpose of this guide is to teach you everything you need to know about being a contributing member of the Ansible community. All types of contributions are welcome and necessary to Ansible's continued success.
This page outlines the most common situations and questions that bring readers to this section. If you prefer a traditional table of contents, there's one at the bottom of the page. This page outlines the most common situations and questions that bring readers to this section. If you prefer a :ref:`traditional table of contents <community_toc>`, you can find one at the bottom of the page.
Getting started Getting started
@ -34,7 +34,7 @@ Going deeper
============ ============
* I think Ansible is broken. How do I :ref:`report a bug <reporting_bugs>`? * I think Ansible is broken. How do I :ref:`report a bug <reporting_bugs>`?
* I need functionality that Ansible doesn't offer. How do I :ref:`request a feature <request_features>`? * I need functionality that Ansible does not offer. How do I :ref:`request a feature <request_features>`?
* How do I :ref:`contribute to an Ansible-maintained collection <contributing_maintained_collections>`? * How do I :ref:`contribute to an Ansible-maintained collection <contributing_maintained_collections>`?
* I am waiting for a particular feature. How do I see what is :ref:`planned for future Ansible Releases <roadmaps>`? * I am waiting for a particular feature. How do I see what is :ref:`planned for future Ansible Releases <roadmaps>`?
* I have a specific Ansible interest or expertise (for example, VMware, Linode, and so on.). How do I get involved in a :ref:`working group <working_group_list>`? * I have a specific Ansible interest or expertise (for example, VMware, Linode, and so on.). How do I get involved in a :ref:`working group <working_group_list>`?
@ -45,9 +45,9 @@ Going deeper
Working with the Ansible repo Working with the Ansible repo
============================= =============================
* I want to code my first changes to Ansible. How do I :ref:`set up my Python development environment <environment_setup>`? * I want to make my first code changes to a collection or to ``ansible-base``. How do I :ref:`set up my Python development environment <environment_setup>`?
* I would like to get more efficient as a developer. How can I find :ref:`editors, linters, and other tools <other_tools_and_programs>` that will support my Ansible development efforts? * I would like to get more efficient as a developer. How can I find :ref:`editors, linters, and other tools <other_tools_and_programs>` that will support my Ansible development efforts?
* I want my PR to meet Ansible's guidelines. Where can I find guidance on :ref:`coding in Ansible <developer_guide>`? * I want my code to meet Ansible's guidelines. Where can I find guidance on :ref:`coding in Ansible <developer_guide>`?
* I want to learn more about Ansible roadmaps, releases, and projects. How do I find information on :ref:`the development cycle <community_development_process>`? * I want to learn more about Ansible roadmaps, releases, and projects. How do I find information on :ref:`the development cycle <community_development_process>`?
* I would like to connect Ansible to a new API or other resource. How do I :ref:`create a collection <developing_modules_in_groups>`? * I would like to connect Ansible to a new API or other resource. How do I :ref:`create a collection <developing_modules_in_groups>`?
* My pull request is marked ``needs_rebase``. How do I :ref:`rebase my PR <rebase_guide>`? * My pull request is marked ``needs_rebase``. How do I :ref:`rebase my PR <rebase_guide>`?
@ -56,10 +56,12 @@ Working with the Ansible repo
* I am ready to step up as a collection maintainer. What are the :ref:`guidelines for maintainers <maintainers>`? * I am ready to step up as a collection maintainer. What are the :ref:`guidelines for maintainers <maintainers>`?
* A module in a collection I maintain is obsolete. How do I :ref:`deprecate a module <deprecating_modules>`? * A module in a collection I maintain is obsolete. How do I :ref:`deprecate a module <deprecating_modules>`?
.. _community_toc:
Traditional Table of Contents Traditional Table of Contents
============================= =============================
If you prefer to read the entire Community Guide, here's a list of the pages in order: If you prefer to read the entire Community Guide, here is a list of the pages in order:
.. toctree:: .. toctree::
:maxdepth: 2 :maxdepth: 2

@ -1,11 +1,8 @@
********************************** ***************************
Developing the Ansible Core Engine Developing ``ansible-base``
********************************** ***************************
Although many of the pieces of the Ansible Core Engine are plugins that can be Although ``ansible-base`` (the code hosted in the `ansible/ansible repository <https://github.com/ansible/ansible>`_ on GitHub) includes a few plugins that can be swapped out via playbook directives or configuration, much of the code there is not modular. The documents here give insight into how the parts of ``ansible-base`` work together.
swapped out via playbook directives or configuration, there are still pieces
of the Engine that are not modular. The documents here give insight into how
those pieces work together.
.. toctree:: .. toctree::
:maxdepth: 1 :maxdepth: 1

@ -5,17 +5,17 @@
Adding modules and plugins locally Adding modules and plugins locally
********************************** **********************************
The easiest, quickest, and the most popular way to extend Ansible is to use a local module or a plugin. You can create them or copy existing ones for local use. You can store a local module or plugin on your Ansible control node and share it with your team or organization. You can also share a local plugin or module by embedding it in a role and publishing it on Ansible Galaxy. If you are using roles on Ansible Galaxy, then you are already using local modules and plugins without realizing it. The easiest, quickest, and the most popular way to extend Ansible is to use a local module or a plugin. You can create them or copy existing ones for local use. You can store a local module or plugin on your Ansible control node and share it with your team or organization. You can also share a local plugin or module by including it in a collection or embedding it in a role, then publishing the collection or role on Ansible Galaxy. If you are using roles on Ansible Galaxy, then you are already using local modules and plugins without realizing it.
If you are using an existing module or plugin but Ansible can't find it, this page is all you need. However, if you want to create a plugin or a module, go to :ref:`developing_plugins` and :ref:`developing_modules_general` topics and then return to this page to know how to add it locally. If you are using an existing module or plugin but Ansible can't find it, this page is all you need. However, if you want to create a plugin or a module, go to :ref:`developing_plugins` and :ref:`developing_modules_general` topics and then return to this page to know how to add it locally.
Extending Ansible with local modules and plugins offers lots of shortcuts such as: Extending Ansible with local modules and plugins offers lots of shortcuts such as:
* You can copy other people's modules and plugins. * You can copy other people's modules and plugins.
* If you're writing a new module, you can choose any programming language you like. * When writing a new module, you can choose any programming language you like.
* You don't have to clone the main Ansible repo. * You do not have to clone any repositories.
* You don't have to open a pull request. * You do not have to open a pull request.
* You don't have to add tests (though we recommend that you do!). * You do not have to add tests (though we recommend that you do!).
To save a local module or plugin such that Ansible can find and use it, add the module or plugin in the appropriate directory (the directories are specified in later parts of this topic). To save a local module or plugin such that Ansible can find and use it, add the module or plugin in the appropriate directory (the directories are specified in later parts of this topic).
@ -24,9 +24,9 @@ To save a local module or plugin such that Ansible can find and use it, add the
.. _modules_vs_plugins: .. _modules_vs_plugins:
Modules and plugins: what's the difference? Modules and plugins: what is the difference?
=========================================== ============================================
If you're looking to add local functionality to Ansible, you might wonder whether you need a module or a plugin. Here's a quick overview to help you decide between the two: If you are looking to add local functionality to Ansible, you might wonder whether you need a module or a plugin. Here is a quick overview to help you decide between the two:
* Modules are reusable, standalone scripts that can be used by the Ansible API, the :command:`ansible` command, or the :command:`ansible-playbook` command. Modules provide a defined interface. Each module accepts arguments and returns information to Ansible by printing a JSON string to stdout before exiting. Modules execute on the target system (usually that means on a remote system) in separate processes. * Modules are reusable, standalone scripts that can be used by the Ansible API, the :command:`ansible` command, or the :command:`ansible-playbook` command. Modules provide a defined interface. Each module accepts arguments and returns information to Ansible by printing a JSON string to stdout before exiting. Modules execute on the target system (usually that means on a remote system) in separate processes.
* :ref:`Plugins <plugins_lookup>` augment Ansible's core functionality and execute on the control node within the ``/usr/bin/ansible`` process. Plugins offer options and extensions for the core features of Ansible - transforming data, logging output, connecting to inventory, and more. * :ref:`Plugins <plugins_lookup>` augment Ansible's core functionality and execute on the control node within the ``/usr/bin/ansible`` process. Plugins offer options and extensions for the core features of Ansible - transforming data, logging output, connecting to inventory, and more.

@ -1,7 +1,7 @@
.. _developing_module_utilities: .. _developing_module_utilities:
************************************* *************************************
Using and Developing Module Utilities Using and developing module utilities
************************************* *************************************
Ansible provides a number of module utilities, or snippets of shared code, that Ansible provides a number of module utilities, or snippets of shared code, that
@ -17,7 +17,7 @@ constructed dynamically for each task invocation, by extracting imports and
resolving those matching the namespace against a :ref:`search path <ansible_search_path>` derived from the resolving those matching the namespace against a :ref:`search path <ansible_search_path>` derived from the
active configuration. active configuration.
To reduce the maintenance burden on your own local modules, you can extract To reduce the maintenance burden in a collection or in local modules, you can extract
duplicated code into one or more module utilities and import them into your modules. For example, if you have your own custom modules that import a ``my_shared_code`` library, you can place that into a ``./module_utils/my_shared_code.py`` file like this:: duplicated code into one or more module utilities and import them into your modules. For example, if you have your own custom modules that import a ``my_shared_code`` library, you can place that into a ``./module_utils/my_shared_code.py`` file like this::
from ansible.module_utils.my_shared_code import MySharedCodeClient from ansible.module_utils.my_shared_code import MySharedCodeClient
@ -27,14 +27,11 @@ When you run ``ansible-playbook``, Ansible will merge any files in your local ``
Naming and finding module utilities Naming and finding module utilities
=================================== ===================================
You can generally tell what a module utility does from its name and/or its location. For example, ``openstack.py`` contains utilities for modules that work with OpenStack instances. You can generally tell what a module utility does from its name and/or its location. Generic utilities (shared code used by many different kinds of modules) live in the main ansible/ansible codebase, in the ``common`` subdirectory or in the root directory of ``lib/ansible/module_utils``. Utilities used by a particular set of modules generally live in the same collection as those modules. For example:
Generic utilities (shared code used by many different kinds of modules) live in the ``common`` subdirectory or in the root directory. Utilities
used by a particular set of modules generally live in a sub-directory that mirrors
the directory for those modules. For example:
* ``lib/ansible/module_utils/urls.py`` contains shared code for parsing URLs * ``lib/ansible/module_utils/urls.py`` contains shared code for parsing URLs
* ``lib/ansible/module_utils/storage/emc/`` contains shared code related to EMC * ``openstack.cloud.plugins.module_utils.openstack.py`` contains utilities for modules that work with OpenStack instances
* ``lib/ansible/modules/storage/emc/`` contains modules related to EMC * ``ansible.netcommon.plugins.module_utils.network.common.config.py`` contains utility functions for use by networking modules
Following this pattern with your own module utilities makes everything easy to find and use. Following this pattern with your own module utilities makes everything easy to find and use.
@ -43,11 +40,7 @@ Following this pattern with your own module utilities makes everything easy to f
Standard module utilities Standard module utilities
========================= =========================
Ansible ships with an extensive library of ``module_utils`` files. Ansible ships with an extensive library of ``module_utils`` files. You can find the module utility source code in the ``lib/ansible/module_utils`` directory under your main Ansible path. We describe the most widely used utilities below. For more details on any specific module utility, please see the `source code for module_utils <https://github.com/ansible/ansible/tree/devel/lib/ansible/module_utils>`_.
You can find the module
utility source code in the ``lib/ansible/module_utils`` directory under
your main Ansible path. We've described the most widely used utilities below. For more details on any specific module utility,
please see the `source code for module_utils <https://github.com/ansible/ansible/tree/devel/lib/ansible/module_utils>`_.
.. include:: shared_snippets/licensing.txt .. include:: shared_snippets/licensing.txt
@ -55,23 +48,22 @@ please see the `source code for module_utils <https://github.com/ansible/ansible
- ``basic.py`` - General definitions and helper utilities for Ansible modules - ``basic.py`` - General definitions and helper utilities for Ansible modules
- ``common/dict_transformations.py`` - Helper functions for dictionary transformations - ``common/dict_transformations.py`` - Helper functions for dictionary transformations
- ``common/file.py`` - Helper functions for working with files - ``common/file.py`` - Helper functions for working with files
- ``common/text/`` - Helper functions for converting and formatting text. - ``common/text/`` - Helper functions for converting and formatting text
- ``common/parameters.py`` - Helper functions for dealing with module parameters - ``common/parameters.py`` - Helper functions for dealing with module parameters
- ``common/sys_info.py`` - Functions for getting distribution and platform information - ``common/sys_info.py`` - Functions for getting distribution and platform information
- ``common/validation.py`` - Helper functions for validating module parameters against a module argument spec - ``common/validation.py`` - Helper functions for validating module parameters against a module argument spec
- ``facts/`` - Directory of utilities for modules that return facts. See `PR 23012 <https://github.com/ansible/ansible/pull/23012>`_ for more information - ``facts/`` - Directory of utilities for modules that return facts. See `PR 23012 <https://github.com/ansible/ansible/pull/23012>`_ for more information
- ``ismount.py`` - Single helper function that fixes os.path.ismount
- ``json_utils.py`` - Utilities for filtering unrelated output around module JSON output, like leading and trailing lines - ``json_utils.py`` - Utilities for filtering unrelated output around module JSON output, like leading and trailing lines
- ``known_hosts.py`` - utilities for working with known_hosts file
- ``network/common/config.py`` - Configuration utility functions for use by networking modules
- ``network/common/netconf.py`` - Definitions and helper functions for modules that use Netconf transport
- ``network/common/parsing.py`` - Definitions and helper functions for Network modules
- ``network/common/network.py`` - Functions for running commands on networking devices
- ``network/common/utils.py`` - Defines commands and comparison operators and other utilises for use in networking modules
- ``powershell/`` - Directory of definitions and helper functions for Windows PowerShell modules - ``powershell/`` - Directory of definitions and helper functions for Windows PowerShell modules
- ``pycompat24.py`` - Exception workaround for Python 2.4 - ``pycompat24.py`` - Exception workaround for Python 2.4
- ``service.py`` - Utilities to enable modules to work with Linux services (placeholder, not in use) - ``service.py`` - Utilities to enable modules to work with Linux services (placeholder, not in use)
- ``shell.py`` - Functions to allow modules to create shells and work with shell commands
- ``six/__init__.py`` - Bundled copy of the `Six Python library <https://pypi.org/project/six/>`_ to aid in writing code compatible with both Python 2 and Python 3 - ``six/__init__.py`` - Bundled copy of the `Six Python library <https://pypi.org/project/six/>`_ to aid in writing code compatible with both Python 2 and Python 3
- ``splitter.py`` - String splitting and manipulation utilities for working with Jinja2 templates - ``splitter.py`` - String splitting and manipulation utilities for working with Jinja2 templates
- ``urls.py`` - Utilities for working with http and https requests - ``urls.py`` - Utilities for working with http and https requests
Several commonly-used utilities migrated to collections in Ansible 2.10, including:
- ``ismount.py`` migrated to ``ansible.posix.plugins.module_utils.mount.py`` - Single helper function that fixes os.path.ismount
- ``known_hosts.py`` migrated to ``community.general.plugins.module_utils.known_hosts.py`` - utilities for working with known_hosts file
For a list of migrated content with destination collections, see https://github.com/ansible/ansible/blob/devel/lib/ansible/config/ansible_builtin_runtime.yml.

@ -5,41 +5,31 @@
Should you develop a module? Should you develop a module?
**************************** ****************************
Developing Ansible modules is easy, but often it isn't necessary. Before you start writing a new module, ask: Developing Ansible modules is easy, but often it is not necessary. Before you start writing a new module, ask:
1. Does a similar module already exist? 1. Does a similar module already exist?
An existing module may cover the functionality you want. Ansible Core includes thousands of modules. Search our :ref:`list of existing modules <all_modules>` to see if there's a module that does what you need. An existing module may cover the functionality you want. Ansible collections include thousands of modules. Search our :ref:`list of included collections <list_of_collections>` or `Ansible Galaxy <https://galaxy.ansible.com>`_ to see if an existing module does what you need.
2. Does a Pull Request already exist? 2. Should you use or develop an action plugin instead of a module?
An existing Pull Request may cover the functionality you want. If someone else has already started developing a similar module, you can review and test it. There are a few ways to find open module Pull Requests:
* `GitHub new module PRs <https://github.com/ansible/ansible/labels/new_module>`_
* `All updates to modules <https://github.com/ansible/ansible/labels/module>`_
* `New module PRs listed by directory <https://ansible.sivel.net/pr/byfile.html>`_ search for `lib/ansible/modules/`
If you find an existing PR that looks like it addresses your needs, please provide feedback on the PR. Community feedback speeds up the review and merge process.
3. Should you use or develop an action plugin instead?
An action plugin may be the best way to get the functionality you want. Action plugins run on the control node instead of on the managed node, and their functionality is available to all modules. For more information about developing plugins, read the :ref:`developing plugins page <developing_plugins>`. An action plugin may be the best way to get the functionality you want. Action plugins run on the control node instead of on the managed node, and their functionality is available to all modules. For more information about developing plugins, read the :ref:`developing plugins page <developing_plugins>`.
4. Should you use a role instead? 3. Should you use a role instead of a module?
A combination of existing modules may cover the functionality you want. You can write a role for this type of use case. Check out the :ref:`roles documentation<playbooks_reuse_roles>`. A combination of existing modules may cover the functionality you want. You can write a role for this type of use case. Check out the :ref:`roles documentation<playbooks_reuse_roles>`.
5. Should you write multiple modules instead of one module? 4. Should you create a collection instead of a single module?
The functionality you want may be too large for a single module. If you want to connect Ansible to a new cloud provider, database, or network platform, you may need to :ref:`develop a related group of modules<developing_modules_in_groups>`. The functionality you want may be too large for a single module. If you want to connect Ansible to a new cloud provider, database, or network platform, you may need to :ref:`develop a new collection<developing_modules_in_groups>`.
* Modules should have a concise and well defined functionality. Basically, follow the UNIX philosophy of doing one thing well. * Each module should have a concise and well defined functionality. Basically, follow the UNIX philosophy of doing one thing well.
* Modules should not require that a user know all the underlying options of an API/tool to be used. For instance, if the legal values for a required module parameter cannot be documented, that's a sign that the module would be rejected. * A module should not require that a user know all the underlying options of an API/tool to be used. For instance, if the legal values for a required module parameter cannot be documented, that's a sign that the module would be rejected.
* Modules should typically encompass much of the logic for interacting with a resource. A lightweight wrapper around an API that does not contain much logic would likely cause users to offload too much logic into a playbook, and for this reason the module would be rejected. Instead try creating multiple modules for interacting with smaller individual pieces of the API. * Modules should typically encompass much of the logic for interacting with a resource. A lightweight wrapper around an API that does not contain much logic would likely cause users to offload too much logic into a playbook, and for this reason the module would be rejected. Instead try creating multiple modules for interacting with smaller individual pieces of the API.
If your use case isn't covered by an existing module, an open PR, an action plugin, or a role, and you don't need to create multiple modules, then you're ready to start developing a new module. Choose from the topics below for next steps: If your use case isn't covered by an existing module, an action plugin, or a role, and you don't need to create multiple modules, then you're ready to start developing a new module. Choose from the topics below for next steps:
* I want to :ref:`get started on a new module <developing_modules_general>`. * I want to :ref:`get started on a new module <developing_modules_general>`.
* I want to review :ref:`tips and conventions for developing good modules <developing_modules_best_practices>`. * I want to review :ref:`tips and conventions for developing good modules <developing_modules_best_practices>`.
@ -53,10 +43,8 @@ If your use case isn't covered by an existing module, an open PR, an action plug
.. seealso:: .. seealso::
:ref:`all_modules` :ref:`list_of_collections`
Learn about available modules Browse existing collections, modules, and plugins
`GitHub modules directory <https://github.com/ansible/ansible/tree/devel/lib/ansible/modules>`_
Browse module source code
`Mailing List <https://groups.google.com/group/ansible-devel>`_ `Mailing List <https://groups.google.com/group/ansible-devel>`_
Development mailing list Development mailing list
`irc.freenode.net <http://irc.freenode.net>`_ `irc.freenode.net <http://irc.freenode.net>`_

@ -13,7 +13,7 @@ As you design and develop modules, follow these basic conventions and tips for c
Scoping your module(s) Scoping your module(s)
====================== ======================
Especially if you want to contribute your module(s) back to Ansible Core, make sure each module includes enough logic and functionality, but not too much. If you're finding these guidelines tricky, consider :ref:`whether you really need to write a module <module_dev_should_you>` at all. Especially if you want to contribute your module(s) to an existing Ansible Collection, make sure each module includes enough logic and functionality, but not too much. If these guidelines seem confusing, consider :ref:`whether you really need to write a module <module_dev_should_you>` at all.
* Each module should have a concise and well-defined functionality. Basically, follow the UNIX philosophy of doing one thing well. * Each module should have a concise and well-defined functionality. Basically, follow the UNIX philosophy of doing one thing well.
* Do not add ``get``, ``list`` or ``info`` state options to an existing module - create a new ``_info`` or ``_facts`` module. * Do not add ``get``, ``list`` or ``info`` state options to an existing module - create a new ``_info`` or ``_facts`` module.
@ -31,8 +31,8 @@ Designing module interfaces
General guidelines & tips General guidelines & tips
========================= =========================
* Each module should be self-contained in one file, so it can be auto-transferred by Ansible. * Each module should be self-contained in one file, so it can be auto-transferred by ``ansible-base``.
* Module name MUST use underscores instead of hyphens or spaces as a word separator. Using hyphens and spaces will prevent Ansible from importing your module. * Module name MUST use underscores instead of hyphens or spaces as a word separator. Using hyphens and spaces will prevent ``ansible-base`` from importing your module.
* Always use the ``hacking/test-module.py`` script when developing modules - it will warn you about common pitfalls. * Always use the ``hacking/test-module.py`` script when developing modules - it will warn you about common pitfalls.
* If you have a local module that returns facts specific to your installations, a good name for this module is ``site_facts``. * If you have a local module that returns facts specific to your installations, a good name for this module is ``site_facts``.
* Eliminate or minimize dependencies. If your module has dependencies, document them at the top of the module file and raise JSON error messages when dependency import fails. * Eliminate or minimize dependencies. If your module has dependencies, document them at the top of the module file and raise JSON error messages when dependency import fails.
@ -46,7 +46,7 @@ Functions and Methods
* Each function should be concise and should describe a meaningful amount of work. * Each function should be concise and should describe a meaningful amount of work.
* "Don't repeat yourself" is generally a good philosophy. * "Don't repeat yourself" is generally a good philosophy.
* Function names should use underscores: ``my_function_name``. * Function names should use underscores: ``my_function_name``.
* Each function's name should describes what it does. * The name of each function should describe what the function does.
* Each function should have a docstring. * Each function should have a docstring.
* If your code is too nested, that's usually a sign the loop body could benefit from being a function. Parts of our existing code are not the best examples of this at times. * If your code is too nested, that's usually a sign the loop body could benefit from being a function. Parts of our existing code are not the best examples of this at times.

@ -1,18 +1,18 @@
.. _developing_modules_checklist: .. _developing_modules_checklist:
.. _module_contribution: .. _module_contribution:
*********************************** **********************************************************
Contributing your module to Ansible Contributing your module to an existing Ansible collection
*********************************** **********************************************************
If you want to contribute a module to Ansible, you must meet our objective and subjective requirements. Please read the details below, and also review our :ref:`tips for module development <developing_modules_best_practices>`. If you want to contribute a module to an existing collection, you must meet the community's objective and subjective requirements. Please read the details below, and also review our :ref:`tips for module development <developing_modules_best_practices>`.
Modules accepted into the `main project repo <https://github.com/ansible/ansible>`_ ship with every Ansible installation. However, contributing to the main project isn't the only way to distribute a module - you can embed modules in roles on Galaxy or simply share copies of your module code for :ref:`local use <developing_locally>`. Modules accepted into certain collections are included in every Ansible release on PyPI. However, contributing to one of these collections is not the only way to distribute a module - you can :ref:`create your own collection <developing_collections>`, embed modules in roles on Galaxy or simply share copies of your module code for :ref:`local use <developing_locally>`.
Contributing to Ansible: objective requirements Contributing modules: objective requirements
=============================================== ===============================================
To contribute a module to Ansible, you must: To contribute a module to most Ansible collections, you must:
* write your module in either Python or Powershell for Windows * write your module in either Python or Powershell for Windows
* use the ``AnsibleModule`` common code * use the ``AnsibleModule`` common code
@ -29,12 +29,14 @@ To contribute a module to Ansible, you must:
* if a module is named ``<something>_facts``, it should be because its main purpose is returning ``ansible_facts``. Do not name modules that do not do this with ``_facts``. Only use ``ansible_facts`` for information that is specific to the host machine, for example network interfaces and their configuration, which operating system and which programs are installed. * if a module is named ``<something>_facts``, it should be because its main purpose is returning ``ansible_facts``. Do not name modules that do not do this with ``_facts``. Only use ``ansible_facts`` for information that is specific to the host machine, for example network interfaces and their configuration, which operating system and which programs are installed.
* Modules that query/return general information (and not ``ansible_facts``) should be named ``_info``. General information is non-host specific information, for example information on online/cloud services (you can access different accounts for the same online service from the same host), or information on VMs and containers accessible from the machine. * Modules that query/return general information (and not ``ansible_facts``) should be named ``_info``. General information is non-host specific information, for example information on online/cloud services (you can access different accounts for the same online service from the same host), or information on VMs and containers accessible from the machine.
Additional requirements may apply for certain collections. Review the individual collection repositories for more information.
Please make sure your module meets these requirements before you submit your PR/proposal. If you have questions, reach out via `Ansible's IRC chat channel <http://irc.freenode.net>`_ or the `Ansible development mailing list <https://groups.google.com/group/ansible-devel>`_. Please make sure your module meets these requirements before you submit your PR/proposal. If you have questions, reach out via `Ansible's IRC chat channel <http://irc.freenode.net>`_ or the `Ansible development mailing list <https://groups.google.com/group/ansible-devel>`_.
Contributing to Ansible: subjective requirements Contributing to Ansible: subjective requirements
================================================ ================================================
If your module meets our objective requirements, we'll review your code to see if we think it's clear, concise, secure, and maintainable. We'll consider whether your module provides a good user experience, helpful error messages, reasonable defaults, and more. This process is subjective, and we can't list exact standards for acceptance. For the best chance of getting your module accepted into the Ansible repo, follow our :ref:`tips for module development <developing_modules_best_practices>`. If your module meets these objective requirements, collection maintainers will review your code to see if they think it's clear, concise, secure, and maintainable. They will consider whether your module provides a good user experience, helpful error messages, reasonable defaults, and more. This process is subjective, with no exact standards for acceptance. For the best chance of getting your module accepted, follow our :ref:`tips for module development <developing_modules_best_practices>`.
Other checklists Other checklists
================ ================

@ -5,7 +5,7 @@
Module format and documentation Module format and documentation
******************************* *******************************
If you want to contribute your module to Ansible, you must write your module in Python and follow the standard format described below. (Unless you're writing a Windows module, in which case the :ref:`Windows guidelines <developing_modules_general_windows>` apply.) In addition to following this format, you should review our :ref:`submission checklist <developing_modules_checklist>`, :ref:`programming tips <developing_modules_best_practices>`, and :ref:`strategy for maintaining Python 2 and Python 3 compatibility <developing_python_3>`, as well as information about :ref:`testing <developing_testing>` before you open a pull request. If you want to contribute your module to most Ansible collections, you must write your module in Python and follow the standard format described below. (Unless you're writing a Windows module, in which case the :ref:`Windows guidelines <developing_modules_general_windows>` apply.) In addition to following this format, you should review our :ref:`submission checklist <developing_modules_checklist>`, :ref:`programming tips <developing_modules_best_practices>`, and :ref:`strategy for maintaining Python 2 and Python 3 compatibility <developing_python_3>`, as well as information about :ref:`testing <developing_testing>` before you open a pull request.
Every Ansible module written in Python must begin with seven standard sections in a particular order, followed by the code. The sections in order are: Every Ansible module written in Python must begin with seven standard sections in a particular order, followed by the code. The sections in order are:
@ -19,22 +19,21 @@ Every Ansible module written in Python must begin with seven standard sections i
.. warning:: **Copy old modules with care!** .. warning:: **Copy old modules with care!**
Some older modules in Ansible Core have ``imports`` at the bottom of the file, ``Copyright`` notices with the full GPL prefix, and/or ``DOCUMENTATION`` fields in the wrong order. These are legacy files that need updating - do not copy them into new modules. Over time we're updating and correcting older modules. Please follow the guidelines on this page! Some older Ansible modules have ``imports`` at the bottom of the file, ``Copyright`` notices with the full GPL prefix, and/or ``DOCUMENTATION`` fields in the wrong order. These are legacy files that need updating - do not copy them into new modules. Over time we are updating and correcting older modules. Please follow the guidelines on this page!
.. _shebang: .. _shebang:
Python shebang & UTF-8 coding Python shebang & UTF-8 coding
=============================== ===============================
Every Ansible module must begin with ``#!/usr/bin/python`` - this "shebang" allows ``ansible_python_interpreter`` to work. Begin your Ansible module with ``#!/usr/bin/python`` - this "shebang" allows ``ansible_python_interpreter`` to work. Follow the shebang immediately with ``# -*- coding: utf-8 -*-`` to clarify that the file is UTF-8 encoded.
This is immediately followed by ``# -*- coding: utf-8 -*-`` to clarify that the file is UTF-8 encoded.
.. _copyright: .. _copyright:
Copyright and license Copyright and license
===================== =====================
After the shebang and UTF-8 coding, there should be a `copyright line <https://www.gnu.org/licenses/gpl-howto.en.html>`_ with the original copyright holder and a license declaration. The license declaration should be ONLY one line, not the full GPL prefix.: After the shebang and UTF-8 coding, add a `copyright line <https://www.gnu.org/licenses/gpl-howto.en.html>`_ with the original copyright holder and a license declaration. The license declaration should be ONLY one line, not the full GPL prefix.:
.. code-block:: python .. code-block:: python
@ -185,7 +184,7 @@ All fields in the ``DOCUMENTATION`` block are lower-case. All fields are require
:suboptions: :suboptions:
* If this option takes a dict or list of dicts, you can define the structure here. * If this option takes a dict or list of dicts, you can define the structure here.
* See :ref:`azure_rm_securitygroup_module`, :ref:`azure_rm_azurefirewall_module` and :ref:`os_ironic_node_module` for examples. * See :ref:`ansible_collections.azure.azcollection.azure_rm_securitygroup_module`, :ref:`ansible_collections.azure.azcollection.azure_rm_azurefirewall_module`, and :ref:`ansible_collections.openstack.cloud.baremetal_node_action_module` for examples.
:requirements: :requirements:
@ -265,7 +264,7 @@ content in a uniform way:
Documentation fragments Documentation fragments
----------------------- -----------------------
If you're writing multiple related modules, they may share common documentation, such as authentication details, file mode settings, ``notes:`` or ``seealso:`` entries. Rather than duplicate that information in each module's ``DOCUMENTATION`` block, you can save it once as a doc_fragment plugin and use it in each module's documentation. In Ansible, shared documentation fragments are contained in a ``ModuleDocFragment`` class in `lib/ansible/plugins/doc_fragments/ <https://github.com/ansible/ansible/tree/devel/lib/ansible/plugins/doc_fragments>`_. To include a documentation fragment, add ``extends_documentation_fragment: FRAGMENT_NAME`` in your module's documentation. If you are writing multiple related modules, they may share common documentation, such as authentication details, file mode settings, ``notes:`` or ``seealso:`` entries. Rather than duplicate that information in each module's ``DOCUMENTATION`` block, you can save it once as a doc_fragment plugin and use it in each module's documentation. In Ansible, shared documentation fragments are contained in a ``ModuleDocFragment`` class in `lib/ansible/plugins/doc_fragments/ <https://github.com/ansible/ansible/tree/devel/lib/ansible/plugins/doc_fragments>`_ or the equivalent directory in a collection. To include a documentation fragment, add ``extends_documentation_fragment: FRAGMENT_NAME`` in your module documentation. Use the fully qualified collection name for the FRAGMENT_NAME (for example, ``community.kubernetes.k8s_auth_options``).
Modules should only use items from a doc fragment if the module will implement all of the interface documented there in a manner that behaves the same as the existing modules which import that fragment. The goal is that items imported from the doc fragment will behave identically when used in another module that imports the doc fragment. Modules should only use items from a doc fragment if the module will implement all of the interface documented there in a manner that behaves the same as the existing modules which import that fragment. The goal is that items imported from the doc fragment will behave identically when used in another module that imports the doc fragment.

@ -9,7 +9,7 @@ A module is a reusable, standalone script that Ansible runs on your behalf, eith
If you need functionality that is not available in any of the thousands of Ansible modules found in collections, you can easily write your own custom module. When you write a module for local use, you can choose any programming language and follow your own rules. Use this topic to learn how to create an Ansible module in Python. After you create a module, you must add it locally to the appropriate directory so that Ansible can find and execute it. For details about adding a module locally, see :ref:`developing_locally`. If you need functionality that is not available in any of the thousands of Ansible modules found in collections, you can easily write your own custom module. When you write a module for local use, you can choose any programming language and follow your own rules. Use this topic to learn how to create an Ansible module in Python. After you create a module, you must add it locally to the appropriate directory so that Ansible can find and execute it. For details about adding a module locally, see :ref:`developing_locally`.
.. contents:: Topics .. contents::
:local: :local:
.. _environment_setup: .. _environment_setup:
@ -91,7 +91,7 @@ Creating a module
To create a new module: To create a new module:
1. Navigate to the correct directory for your new module: ``$ cd lib/ansible/modules/``. If you are developing module using collection, ``$ cd plugins/modules/`` inside your collection development tree. 1. Navigate to the correct directory for your new module: ``$ cd lib/ansible/modules/``. If you are developing a module in a :ref:`collection <developing_collections>`, ``$ cd plugins/modules/`` inside your collection development tree.
2. Create your new module file: ``$ touch my_test.py``. 2. Create your new module file: ``$ touch my_test.py``.
3. Paste the content below into your new module file. It includes the :ref:`required Ansible format and documentation <developing_modules_documenting>` and some example code. 3. Paste the content below into your new module file. It includes the :ref:`required Ansible format and documentation <developing_modules_documenting>` and some example code.
4. Modify and extend the code to do what you want your new module to do. See the :ref:`programming tips <developing_modules_best_practices>` and :ref:`Python 3 compatibility <developing_python_3>` pages for pointers on writing clean, concise module code. 4. Modify and extend the code to do what you want your new module to do. See the :ref:`programming tips <developing_modules_best_practices>` and :ref:`Python 3 compatibility <developing_python_3>` pages for pointers on writing clean, concise module code.
@ -102,8 +102,9 @@ To create a new module:
Exercising your module code Exercising your module code
=========================== ===========================
Once you've modified the sample code above to do what you want, you can try out your module. After you modify the sample code above to do what you want, you can try out your module.
Our :ref:`debugging tips <debugging_modules>` will help if you run into bugs as you exercise your module code. Our :ref:`debugging tips <debugging_modules>` will help if you run into bugs as you verify your module code.
Exercising module code locally Exercising module code locally
------------------------------ ------------------------------
@ -195,19 +196,10 @@ test/units/modules/.../test/my_test.py``
Contributing back to Ansible Contributing back to Ansible
============================ ============================
If you would like to contribute to the main Ansible repository If you would like to contribute to ``ansible-base`` by adding a new feature or fixing a bug, `create a fork <https://help.github.com/articles/fork-a-repo/>`_ of the ansible/ansible repository and develop against a new feature branch using the ``devel`` branch as a starting point. When you you have a good working code change, you can submit a pull request to the Ansible repository by selecting your feature branch as a source and the Ansible devel branch as a target.
by adding a new feature or fixing a bug, `create a fork <https://help.github.com/articles/fork-a-repo/>`_
of the Ansible repository and develop against a new feature If you want to contribute a module to an :ref:`Ansible collection <contributing_maintained_collections>`, review our :ref:`submission checklist <developing_modules_checklist>`, :ref:`programming tips <developing_modules_best_practices>`, and :ref:`strategy for maintaining Python 2 and Python 3 compatibility <developing_python_3>`, as well as information about :ref:`testing <developing_testing>` before you open a pull request.
branch using the ``devel`` branch as a starting point.
When you you have a good working code change, you can
submit a pull request to the Ansible repository by selecting
your feature branch as a source and the Ansible devel branch as
a target.
If you want to contribute your module back to the upstream Ansible repo,
review our :ref:`submission checklist <developing_modules_checklist>`, :ref:`programming tips <developing_modules_best_practices>`,
and :ref:`strategy for maintaining Python 2 and Python 3 compatibility <developing_python_3>`, as well as
information about :ref:`testing <developing_testing>` before you open a pull request.
The :ref:`Community Guide <ansible_community_guide>` covers how to open a pull request and what happens next. The :ref:`Community Guide <ansible_community_guide>` covers how to open a pull request and what happens next.

@ -18,9 +18,9 @@ What's covered in this section:
Introduction Introduction
============ ============
Ansible already ships with a large collection of Cisco ACI modules, however the ACI object model is huge and covering all possible functionality would easily cover more than 1500 individual modules. The `cisco.aci collection <https://galaxy.ansible.com/cisco/aci>`_ already includes a large number of Cisco ACI modules, however the ACI object model is huge and covering all possible functionality would easily cover more than 1500 individual modules.
If you are in need of specific functionality, you have 2 options: If you need specific functionality, you have 2 options:
- Learn the ACI object model and use the low-level APIC REST API using the :ref:`aci_rest <aci_rest_module>` module - Learn the ACI object model and use the low-level APIC REST API using the :ref:`aci_rest <aci_rest_module>` module
- Write your own dedicated modules, which is actually quite easy - Write your own dedicated modules, which is actually quite easy

@ -8,7 +8,7 @@ Developing plugins
.. contents:: .. contents::
:local: :local:
Plugins augment Ansible's core functionality with logic and features that are accessible to all modules. Ansible ships with a number of handy plugins, and you can easily write your own. All plugins must: Plugins augment Ansible's core functionality with logic and features that are accessible to all modules. Ansible collections include a number of handy plugins, and you can easily write your own. All plugins must:
* be written in Python * be written in Python
* raise errors * raise errors
@ -70,8 +70,7 @@ To define configurable options for your plugin, describe them in the ``DOCUMENTA
To access the configuration settings in your plugin, use ``self.get_option(<option_name>)``. For most plugin types, the controller pre-populates the settings. If you need to populate settings explicitly, use a ``self.set_options()`` call. To access the configuration settings in your plugin, use ``self.get_option(<option_name>)``. For most plugin types, the controller pre-populates the settings. If you need to populate settings explicitly, use a ``self.set_options()`` call.
Plugins that support embedded documentation (see :ref:`ansible-doc` for the list) should include well-formed doc strings. If you inherit from a plugin, you must document the options it takes, either via a documentation fragment or as a copy. See :ref:`module_documenting` for more information on correct documentation. Thorough documentation is a good idea even if you're developing a plugin for local use.
Plugins that support embedded documentation (see :ref:`ansible-doc` for the list) must include well-formed doc strings to be considered for merge into the Ansible repo. If you inherit from a plugin, you must document the options it takes, either via a documentation fragment or as a copy. See :ref:`module_documenting` for more information on correct documentation. Thorough documentation is a good idea even if you're developing a plugin for local use.
Developing particular plugin types Developing particular plugin types
================================== ==================================

@ -5,7 +5,7 @@
Ansible module architecture Ansible module architecture
*************************** ***************************
If you're working on Ansible's Core code, writing an Ansible module, or developing an action plugin, this deep dive helps you understand how Ansible's program flow executes. If you're just using Ansible Modules in playbooks, you can skip this section. If you are working on the ``ansible-base`` code, writing an Ansible module, or developing an action plugin, you may need to understand how Ansible's program flow executes. If you are just using Ansible Modules in playbooks, you can skip this section.
.. contents:: .. contents::
:local: :local:

@ -4,14 +4,11 @@
Ansible and Python 3 Ansible and Python 3
******************** ********************
.. contents:: Topics The ``ansible-base`` code runs on both Python 2 and Python 3 because we want Ansible to be able to manage a wide
:local: variety of machines. Contributors to ansible-base and to Ansible Collections should be aware of the tips in this document so that they can write code that will run on the same versions of Python as the rest of Ansible.
Ansible maintains a single code base that runs on both .. contents::
Python 2 and Python 3 because we want Ansible to be able to manage a wide :local:
variety of machines. Contributors to Ansible should be aware of the tips in
this document so that they can write code that will run on the same versions
of Python as the rest of Ansible.
To ensure that your code runs on Python 3 as well as on Python 2, learn the tips and tricks and idioms To ensure that your code runs on Python 3 as well as on Python 2, learn the tips and tricks and idioms
described here. Most of these considerations apply to all three types of Ansible code: described here. Most of these considerations apply to all three types of Ansible code:
@ -20,8 +17,7 @@ described here. Most of these considerations apply to all three types of Ansible
2. modules - the code which Ansible transmits to and invokes on the managed machine. 2. modules - the code which Ansible transmits to and invokes on the managed machine.
3. shared ``module_utils`` code - the common code that's used by modules to perform tasks and sometimes used by controller-side code as well 3. shared ``module_utils`` code - the common code that's used by modules to perform tasks and sometimes used by controller-side code as well
However, the three types of code do not use the same string strategy. If you're developing a module or some ``module_utils`` code, be sure However, the three types of code do not use the same string strategy. If you're developing a module or some ``module_utils`` code, be sure to read the section on string strategy carefully.
to read the section on string strategy carefully.
Minimum version of Python 3.x and Python 2.x Minimum version of Python 3.x and Python 2.x
============================================ ============================================
@ -405,8 +401,4 @@ does have support for the older, percent-formatting.
Testing modules on Python 3 Testing modules on Python 3
=================================== ===================================
Ansible modules are slightly harder to code to support Python 3 than normal code from other Ansible modules are slightly harder to code to support Python 3 than normal code from other projects. A lot of mocking has to go into unit testing an Ansible module, so it's harder to test that your changes have fixed everything or to to make sure that later commits haven't regressed the Python 3 support. Review our :ref:`testing <developing_testing>` pages for more information.
projects. A lot of mocking has to go into unit testing an Ansible module, so
it's harder to test that your changes have fixed everything or to to make sure
that later commits haven't regressed the Python 3 support. Review our :ref:`testing <developing_testing>` pages
for more information.

@ -14,8 +14,7 @@ Rebasing the branch used to create your PR will resolve both of these issues.
Configuring your remotes Configuring your remotes
======================== ========================
Before you can rebase your PR, you need to make sure you have the proper remotes configured. Before you can rebase your PR, you need to make sure you have the proper remotes configured. These instructions apply to any repository on GitHub, including collections repositories. On other platforms (bitbucket, gitlab), the same principles and commands apply but the syntax may be different. We use the ansible/ansible repository here as an example. In other repositories, the branch names may be different. Assuming you cloned your fork in the usual fashion, the ``origin`` remote will point to your fork::
Assuming you cloned your fork in the usual fashion, the ``origin`` remote will point to your fork::
$ git remote -v $ git remote -v
origin git@github.com:YOUR_GITHUB_USERNAME/ansible.git (fetch) origin git@github.com:YOUR_GITHUB_USERNAME/ansible.git (fetch)
@ -33,7 +32,7 @@ Which should leave you with the following remotes::
upstream https://github.com/ansible/ansible.git (fetch) upstream https://github.com/ansible/ansible.git (fetch)
upstream https://github.com/ansible/ansible.git (push) upstream https://github.com/ansible/ansible.git (push)
Checking the status of your branch should show you're up-to-date with your fork at the ``origin`` remote:: Checking the status of your branch should show your fork is up-to-date with the ``origin`` remote::
$ git status $ git status
On branch YOUR_BRANCH On branch YOUR_BRANCH
@ -50,7 +49,7 @@ Once you have an ``upstream`` remote configured, you can rebase the branch for y
This will replay the changes in your branch on top of the changes made in the upstream ``devel`` branch. This will replay the changes in your branch on top of the changes made in the upstream ``devel`` branch.
If there are merge conflicts, you will be prompted to resolve those before you can continue. If there are merge conflicts, you will be prompted to resolve those before you can continue.
Once you've rebased, the status of your branch will have changed:: After you rebase, the status of your branch changes::
$ git status $ git status
On branch YOUR_BRANCH On branch YOUR_BRANCH
@ -59,8 +58,7 @@ Once you've rebased, the status of your branch will have changed::
(use "git pull" to merge the remote branch into yours) (use "git pull" to merge the remote branch into yours)
nothing to commit, working tree clean nothing to commit, working tree clean
Don't worry, this is normal after a rebase. You should ignore the ``git status`` instructions to use ``git pull``. Don't worry, this is normal after a rebase. You should ignore the ``git status`` instructions to use ``git pull``. We'll cover what to do next in the following section.
We'll cover what to do next in the following section.
Updating your pull request Updating your pull request
========================== ==========================
@ -77,8 +75,7 @@ You should check in on the status of your PR after tests have completed to see i
Getting help rebasing Getting help rebasing
===================== =====================
For help with rebasing your PR, or other development related questions, join us on our #ansible-devel IRC chat channel For help with rebasing your PR, or other development related questions, join us on our #ansible-devel IRC chat channel on `freenode.net <https://freenode.net>`_.
on `freenode.net <https://freenode.net>`_.
.. seealso:: .. seealso::

@ -4,12 +4,7 @@
Guidelines for Ansible Amazon AWS module development Guidelines for Ansible Amazon AWS module development
**************************************************** ****************************************************
The Ansible AWS modules and these guidelines are maintained by the Ansible AWS Working Group. For The Ansible AWS collection (on `Galaxy <https://galaxy.ansible.com/community/aws>`_, source code `repository <https://github.com/ansible-collections/community.aws>`_) is maintained by the Ansible AWS Working Group. For further information see the `AWS working group community page <https://github.com/ansible/community/wiki/aws>`_. If you are planning to contribute AWS modules to Ansible then getting in touch with the working group is a good way to start, especially because a similar module may already be under development.
further information see
the `AWS working group community page <https://github.com/ansible/community/wiki/aws>`_.
If you are planning to contribute AWS modules to Ansible then getting in touch with the working
group will be a good way to start, especially because a similar module may already be under
development.
.. contents:: .. contents::
:local: :local:

@ -3,10 +3,7 @@
OpenStack Ansible Modules OpenStack Ansible Modules
========================= =========================
These are a set of modules for interacting with OpenStack as either an admin The OpenStack collection (on `Galaxy <https://galaxy.ansible.com/openstack/cloud>`_, source code `repository <https://opendev.org/openstack/ansible-collections-openstack.git>`_) contains modules for interacting with OpenStack as either an admin or an end user. If the module does not begin with ``os_``, it is either deprecated or soon to be deprecated. This document serves as developer coding guidelines for modules in this collection.
or an end user. If the module does not begin with ``os_``, it's either deprecated
or soon to be. This document serves as developer coding guidelines for
modules intended to be here.
.. contents:: .. contents::
:local: :local:

@ -3,8 +3,7 @@
oVirt Ansible Modules oVirt Ansible Modules
===================== =====================
This is a set of modules for interacting with oVirt/RHV. This document The set of modules for interacting with oVirt/RHV are currently part of the community.general collection (on `Galaxy <https://galaxy.ansible.com/community/general>`_, source code `repository <https://github.com/ansible-collections/community.general/tree/main/plugins/modules/cloud/ovirt>`_). This document serves as developer coding guidelines for creating oVirt/RHV modules.
serves as developer coding guidelines for creating oVirt/RHV modules.
.. contents:: .. contents::
:local: :local:

@ -4,8 +4,7 @@
Guidelines for VMware module development Guidelines for VMware module development
**************************************** ****************************************
The VMware modules and these guidelines are maintained by the VMware Working Group. For The Ansible VMware collection (on `Galaxy <https://galaxy.ansible.com/community/vmware>`_, source code `repository <https://github.com/ansible-collections/vmware>`_) is maintained by the VMware Working Group. For further information see the `team community page <https://github.com/ansible/community/wiki/VMware>`_.
further information see the `team community page <https://github.com/ansible/community/wiki/VMware>`_.
.. contents:: .. contents::
:local: :local:

@ -33,6 +33,9 @@ How to run
# Run all sanity tests # Run all sanity tests
ansible-test sanity ansible-test sanity
# Run all sanity tests including disabled ones
ansible-test sanity --allow-disabled
# Run all sanity tests against against certain files # Run all sanity tests against against certain files
ansible-test sanity lib/ansible/modules/files/template.py ansible-test sanity lib/ansible/modules/files/template.py

@ -54,16 +54,7 @@ later).
can use the :ref:`yum module<yum_module>` or :ref:`dnf module<dnf_module>` in Ansible to install this package on remote systems can use the :ref:`yum module<yum_module>` or :ref:`dnf module<dnf_module>` in Ansible to install this package on remote systems
that do not have it. that do not have it.
* By default, Ansible uses the Python interpreter located at :file:`/usr/bin/python` to run its * By default, before the first Python module in a playbook runs on a host, Ansible attempts to discover a suitable Python interpreter on that host. You can override the discovery behavior by setting the :ref:`ansible_python_interpreter<ansible_python_interpreter>` inventory variable to a specific interpreter, and in other ways. See :ref:`interpreter_discovery` for details.
modules. However, some Linux distributions may only have a Python 3 interpreter installed to
:file:`/usr/bin/python3` by default. On those systems, you may see an error like::
"module_stdout": "/bin/sh: /usr/bin/python: No such file or directory\r\n"
you can either set the :ref:`ansible_python_interpreter<ansible_python_interpreter>` inventory variable (see
:ref:`inventory`) to point at your interpreter or you can install a Python 2 interpreter for
modules to use. You will still need to set :ref:`ansible_python_interpreter<ansible_python_interpreter>` if the Python
2 interpreter is not installed to :command:`/usr/bin/python`.
* Ansible's :ref:`raw module<raw_module>`, and the :ref:`script module<script_module>`, do not depend * Ansible's :ref:`raw module<raw_module>`, and the :ref:`script module<script_module>`, do not depend
on a client side install of Python to run. Technically, you can use Ansible to install a compatible on a client side install of Python to run. Technically, you can use Ansible to install a compatible
@ -84,11 +75,11 @@ Which Ansible version to install is based on your particular needs. You can choo
* Install the latest release with your OS package manager (for Red Hat Enterprise Linux (TM), CentOS, Fedora, Debian, or Ubuntu). * Install the latest release with your OS package manager (for Red Hat Enterprise Linux (TM), CentOS, Fedora, Debian, or Ubuntu).
* Install with ``pip`` (the Python package manager). * Install with ``pip`` (the Python package manager).
* Install from source to access the development (``devel``) version to develop or test the latest features. * Install ``ansible-base`` from source to access the development (``devel``) version to develop or test the latest features.
.. note:: .. note::
You should only run Ansible from ``devel`` if you are modifying the Ansible engine, or trying out features under development. This is a rapidly changing source of code and can become unstable at any point. You should only run ``ansible-base`` from ``devel`` if you are modifying ``ansible-base``, or trying out features under development. This is a rapidly changing source of code and can become unstable at any point.
Ansible creates new releases two to three times a year. Due to this short release cycle, Ansible creates new releases two to three times a year. Due to this short release cycle,
@ -130,7 +121,11 @@ To enable the Ansible Engine repository for RHEL 7, run the following command:
RPMs for currently supported versions of RHEL and CentOS are also available from `EPEL <https://fedoraproject.org/wiki/EPEL>`_. RPMs for currently supported versions of RHEL and CentOS are also available from `EPEL <https://fedoraproject.org/wiki/EPEL>`_.
Ansible version 2.4 and later can manage older operating systems that contain Python 2.6 or higher. .. note::
Since Ansible 2.10 for RHEL is not available at this time, continue to use Ansible 2.9.
Ansible can manage older operating systems that contain Python 2.6 or higher.
.. _from_apt: .. _from_apt:
@ -361,26 +356,33 @@ to the latest version.
.. _from_pip_devel: .. _from_pip_devel:
Installing the development version of Ansible Installing the development version of ``ansible-base``
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
In Ansible 2.10 and later, The `ansible/ansible repository <https://github.com/ansible/ansible>`_ contains the code for basic features and functions, such as copying module code to managed nodes. This code is also known as ``ansible-base``.
.. note:: .. note::
You should only run Ansible from ``devel`` if you are modifying the Ansible engine, or trying out features under development. This is a rapidly changing source of code and can become unstable at any point. You should only run ``ansible-base`` from ``devel`` if you are modifying ``ansible-base`` or trying out features under development. This is a rapidly changing source of code and can become unstable at any point.
.. note:: .. note::
If you have Ansible 2.9 or older installed, you need to use ``pip uninstall ansible`` first to remove older versions of Ansible before re-installing it. If you have Ansible 2.9 or older installed, you need to use ``pip uninstall ansible`` first to remove older versions of Ansible before re-installing it.
The development version of Ansible can be directly installed from GitHub with pip::
You can install the development version of ``ansible-base`` directly from GitHub with pip.
.. code-block:: bash
$ python -m pip install --user https://github.com/ansible/ansible/archive/devel.tar.gz $ python -m pip install --user https://github.com/ansible/ansible/archive/devel.tar.gz
Replace ``devel`` in the URL mentioned above, with any other branch or tag on GitHub to install that version:: Replace ``devel`` in the URL mentioned above, with any other branch or tag on GitHub to install older versions of Ansible (prior to ``ansible-base`` 2.10.) This installs all of Ansible.
.. code-block:: bash
$ python -m pip install --user https://github.com/ansible/ansible/archive/stable-2.9.tar.gz $ python -m pip install --user https://github.com/ansible/ansible/archive/stable-2.9.tar.gz
See :ref:`from_source` for instructions on how to run Ansible directly from source, without the requirement of installation. See :ref:`from_source` for instructions on how to run ``ansible-base`` directly from source, without the requirement of installation.
.. _from_pip_venv: .. _from_pip_venv:
@ -399,14 +401,16 @@ Ansible can also be installed inside a new or existing ``virtualenv``::
.. _from_source: .. _from_source:
Running Ansible from source (devel) Running ``ansible-base`` from source (devel)
----------------------------------- ---------------------------------------------
In Ansible 2.10 and later, The `ansible/ansible repository <https://github.com/ansible/ansible>`_ contains the code for basic features and functions, such as copying module code to managed nodes. This code is also known as ``ansible-base``.
.. note:: .. note::
You should only run Ansible from ``devel`` if you are modifying the Ansible engine, or trying out features under development. This is a rapidly changing source of code and can become unstable at any point. You should only run ``ansible-base`` from ``devel`` if you are modifying ``ansible-base`` or trying out features under development. This is a rapidly changing source of code and can become unstable at any point.
Ansible is easy to run from source. You do not need ``root`` permissions ``ansible-base`` is easy to run from source. You do not need ``root`` permissions
to use it and there is no software to actually install. No daemons to use it and there is no software to actually install. No daemons
or database setup are required. or database setup are required.
@ -415,14 +419,14 @@ or database setup are required.
If you want to use Ansible Tower as the control node, do not use a source installation of Ansible. Please use an OS package manager (like ``apt`` or ``yum``) or ``pip`` to install a stable version. If you want to use Ansible Tower as the control node, do not use a source installation of Ansible. Please use an OS package manager (like ``apt`` or ``yum``) or ``pip`` to install a stable version.
To install from source, clone the Ansible git repository: To install from source, clone the ``ansible-base`` git repository:
.. code-block:: bash .. code-block:: bash
$ git clone https://github.com/ansible/ansible.git $ git clone https://github.com/ansible/ansible.git
$ cd ./ansible $ cd ./ansible
Once ``git`` has cloned the Ansible repository, setup the Ansible environment: Once ``git`` has cloned the ``ansible-base`` repository, setup the Ansible environment:
Using Bash: Using Bash:
@ -449,7 +453,7 @@ Ansible also uses the following Python modules that need to be installed [1]_:
$ python -m pip install --user -r ./requirements.txt $ python -m pip install --user -r ./requirements.txt
To update Ansible checkouts, use pull-with-rebase so any local changes are replayed. To update ``ansible-base`` checkouts, use pull-with-rebase so any local changes are replayed.
.. code-block:: bash .. code-block:: bash
@ -575,8 +579,8 @@ See the `argcomplete documentation <https://argcomplete.readthedocs.io/en/latest
.. _getting_ansible: .. _getting_ansible:
Ansible on GitHub ``ansible-base`` on GitHub
----------------- ---------------------------
You may also wish to follow the `GitHub project <https://github.com/ansible/ansible>`_ if You may also wish to follow the `GitHub project <https://github.com/ansible/ansible>`_ if
you have a GitHub account. This is also where we keep the issue tracker for sharing you have a GitHub account. This is also where we keep the issue tracker for sharing

@ -13,16 +13,20 @@ Release Schedule
.. note:: Dates subject to change. .. note:: Dates subject to change.
.. note:: We plan to post weekly alpha releases to the `PyPI ansible project <https://pypi.org/project/ansible/>`_ for testing. .. note:: We plan to post weekly alpha releases to the `PyPI ansible project <https://pypi.org/project/ansible/>`_ for testing.
.. warning::
We initially were going to have feature freeze on 2020-08-18. We tried this but decided to
change course. Instead, we'll enter feature freeze when ansible-2.10.0 beta1 is released.
- 2020-06-23: ansible-2.10 alpha freeze. - 2020-06-23: ansible-2.10 alpha freeze.
No net new collections will be added to the ``ansible-2.10`` package after this date. No net new collections will be added to the ``ansible-2.10`` package after this date.
- 2020-07-10: Ansible collections freeze date for content shuffling. - 2020-07-10: Ansible collections freeze date for content shuffling.
Content should be in its final collection for the ansible-2.10 series of releases. No more content should move out of the ``community.general`` or ``community.network`` collections. Content should be in its final collection for the ansible-2.10 series of releases. No more content should move out of the ``community.general`` or ``community.network`` collections.
- 2020-08-13: ansible-base 2.10 Release date, see :ref:`base_roadmap_2_10`. - 2020-08-13: ansible-base 2.10 Release date, see :ref:`base_roadmap_2_10`.
- 2020-08-14: final ansible-2.10 alpha. - 2020-08-14: final ansible-2.10 alpha.
- 2020-08-18: Ansible 2.10 beta freeze. - 2020-09-01: ansible-2.10.0 beta1 and feature freeze.
- No new modules or major features will be added after this date. In practice this means we will freeze the semver collection versions to compatible release versions. For example, if the version of community.crypto on this date was community-crypto-1.1.0; ansible-2.10.0 could ship with community-crypto-1.1.1. It would not ship with community-crypto-1.2.0. - No new modules or major features will be added after this date. In practice this means we will freeze the semver collection versions to compatible release versions. For example, if the version of community.crypto on this date was community-crypto-1.1.0; ansible-2.10.0 could ship with community-crypto-1.1.1. It would not ship with community-crypto-1.2.0.
- 2020-09-01: ansible-2.10.0 beta1.
- 2020-09-10: ansible-2.10 final freeze/rc1. - 2020-09-10: ansible-2.10 final freeze/rc1.
- After this date only changes blocking a release are accepted. - After this date only changes blocking a release are accepted.

@ -236,7 +236,7 @@ Become and network automation
As of version 2.6, Ansible supports ``become`` for privilege escalation (entering ``enable`` mode or privileged EXEC mode) on all Ansible-maintained network platforms that support ``enable`` mode. Using ``become`` replaces the ``authorize`` and ``auth_pass`` options in a ``provider`` dictionary. As of version 2.6, Ansible supports ``become`` for privilege escalation (entering ``enable`` mode or privileged EXEC mode) on all Ansible-maintained network platforms that support ``enable`` mode. Using ``become`` replaces the ``authorize`` and ``auth_pass`` options in a ``provider`` dictionary.
You must set the connection type to either ``connection: network_cli`` or ``connection: httpapi`` to use ``become`` for privilege escalation on network devices. Check the :ref:`platform_options` and :ref:`network_modules` documentation for details. You must set the connection type to either ``connection: ansible.netcommon.network_cli`` or ``connection: ansible.netcommon.httpapi`` to use ``become`` for privilege escalation on network devices. Check the :ref:`platform_options` documentation for details.
You can use escalated privileges on only the specific tasks that need them, on an entire play, or on all plays. Adding ``become: yes`` and ``become_method: enable`` instructs Ansible to enter ``enable`` mode before executing the task, play, or playbook where those parameters are set. You can use escalated privileges on only the specific tasks that need them, on an entire play, or on all plays. Adding ``become: yes`` and ``become_method: enable`` instructs Ansible to enter ``enable`` mode before executing the task, play, or playbook where those parameters are set.
@ -251,7 +251,7 @@ To set ``enable`` mode for a specific task, add ``become`` at the task level:
.. code-block:: yaml .. code-block:: yaml
- name: Gather facts (eos) - name: Gather facts (eos)
eos_facts: arista.eos.eos_facts:
gather_subset: gather_subset:
- "!hardware" - "!hardware"
become: yes become: yes
@ -266,7 +266,7 @@ To set enable mode for all tasks in a single play, add ``become`` at the play le
become_method: enable become_method: enable
tasks: tasks:
- name: Gather facts (eos) - name: Gather facts (eos)
eos_facts: arista.eos.eos_facts:
gather_subset: gather_subset:
- "!hardware" - "!hardware"
@ -279,8 +279,8 @@ Often you wish for all tasks in all plays to run using privilege mode, that is b
.. code-block:: yaml .. code-block:: yaml
ansible_connection: network_cli ansible_connection: ansible.netcommon.network_cli
ansible_network_os: eos ansible_network_os: arista.eos.eos
ansible_user: myuser ansible_user: myuser
ansible_become: yes ansible_become: yes
ansible_become_method: enable ansible_become_method: enable
@ -352,7 +352,8 @@ task:
.. code-block:: yaml .. code-block:: yaml
- win_whoami: - Check my user name
ansible.windows.win_whoami:
become: yes become: yes
The output will look something similar to the below: The output will look something similar to the below:
@ -479,7 +480,7 @@ If running on a version of Ansible that is older than 2.5 or the normal
.. code-block:: yaml .. code-block:: yaml
- name: grant the ansible user the SeTcbPrivilege right - name: grant the ansible user the SeTcbPrivilege right
win_user_right: ansible.windows.win_user_right:
name: SeTcbPrivilege name: SeTcbPrivilege
users: '{{ansible_user}}' users: '{{ansible_user}}'
action: add action: add
@ -577,7 +578,7 @@ or with this Ansible task:
.. code-block:: yaml .. code-block:: yaml
- name: allow blank password on become - name: allow blank password on become
win_regedit: ansible.windows.win_regedit:
path: HKLM:\SYSTEM\CurrentControlSet\Control\Lsa path: HKLM:\SYSTEM\CurrentControlSet\Control\Lsa
name: LimitBlankPasswordUse name: LimitBlankPasswordUse
data: 0 data: 0
@ -652,7 +653,7 @@ Here are some examples of how to use ``become_flags`` with Windows tasks:
.. code-block:: yaml .. code-block:: yaml
- name: copy a file from a fileshare with custom credentials - name: copy a file from a fileshare with custom credentials
win_copy: ansible.windows.win_copy:
src: \\server\share\data\file.txt src: \\server\share\data\file.txt
dest: C:\temp\file.txt dest: C:\temp\file.txt
remote_src: yes remote_src: yes
@ -664,12 +665,12 @@ Here are some examples of how to use ``become_flags`` with Windows tasks:
ansible_become_flags: logon_type=new_credentials logon_flags=netcredentials_only ansible_become_flags: logon_type=new_credentials logon_flags=netcredentials_only
- name: run a command under a batch logon - name: run a command under a batch logon
win_whoami: ansible.windows.win_whoami:
become: yes become: yes
become_flags: logon_type=batch become_flags: logon_type=batch
- name: run a command and not load the user profile - name: run a command and not load the user profile
win_whomai: ansible.windows.win_whomai:
become: yes become: yes
become_flags: logon_flags= become_flags: logon_flags=

@ -1,10 +1,85 @@
.. _user_guide_index:
########## ##########
User Guide User Guide
########## ##########
Welcome to the Ansible User Guide! Welcome to the Ansible User Guide! This guide covers how to work with Ansible, including using the command line, working with inventory, interacting with data, writing tasks, plays, and playbooks; executing playbooks, and reference materials. This page outlines the most common situations and questions that bring readers to this section. If you prefer a traditional table of contents, you can find one at the bottom of the page.
Getting started
===============
* I'd like an overview of how Ansible works. Where can I find:
* a :ref:`quick video overview <quickstart_guide>`
* a :ref:`text introduction <intro_getting_started>`
* I'm ready to learn about Ansible. What :ref:`basic_concepts` do I need to learn?
* I want to use Ansible without writing a playbook. How do I use :ref:`ad-hoc commands <intro_adhoc>`?
Writing tasks, plays, and playbooks
===================================
* I'm writing my first playbook. What should I :ref:`know before I begin <playbooks_tips_and_tricks>`?
* I have a specific use case for a task or play:
* Executing tasks with elevated privileges or as a different user with :ref:`become <become>`
* Repeating a task once for each item in a list with :ref:`loops <playbooks_loops>`
* Executing tasks on a different machine with :ref:`delegation <playbooks_delegation>`
* Running tasks only when certain conditions apply with :ref:`conditionals <playbooks_conditionals>` and evaluating conditions with :ref:`tests <playbooks_tests>`
* Grouping a set of tasks together with :ref:`blocks <playbooks_blocks>`
* Running tasks only when something has changed with :ref:`handlers <handlers>`
* Changing the way Ansible :ref:`handles failures <playbooks_error_handling>`)
* Setting remote :ref:`environment values <playbooks_environment>`
* I want to leverage the power of re-usable Ansible artifacts. How do I create re-usable :ref:`files <playbooks_reuse>` and :ref:`roles <playbooks_reuse_roles>`?
* I need to incorporate one file or playbook inside another. What is the difference between :ref:`including and importing <playbooks_reuse_includes>`?
* I want to run selected parts of my playbook. How do I add and use :ref:`tags <tags>`?
Working with inventory
======================
* I have a list of servers and devices I want to automate. How do I create :ref:`inventory <intro_inventory>` to track them?
* I use cloud services and constantly have servers and devices starting and stopping. How do I track them using :ref:`dynamic inventory <intro_dynamic_inventory>`?
* I want to automate specific sub-sets of my inventory. How do I use :ref:`patterns <intro_patterns>`?
Interacting with data
=====================
* I want to use a single playbook against multiple systems with different attributes. How do I use :ref:`variables <playbooks_variables>` to handle the differences?
* I want to retrieve data about my systems. How do I access :ref:`Ansible facts <vars_and_facts>`?
* I need to access sensitive data like passwords with Ansible. How can I protect that data with :ref:`Ansible vault <vault>`?
* I want to change the data I have, so I can use it in a task. How do I use :ref:`filters <playbooks_filters>` to transform my data?
* I need to retrieve data from an external datastore. How do I use :ref:`lookups <playbooks_lookups>` to access databases and APIs?
* I want to ask playbook users to supply data. How do I get user input with :ref:`prompts <playbooks_prompts>`?
* I use certain modules frequently. How do I streamline my inventory and playbooks by :ref:`setting default values for module parameters <module_defaults>`?
This guide covers how to work with Ansible, including using the command line, working with inventory, and writing playbooks. Executing playbooks
===================
Once your playbook is ready to run, you may need to use these topics:
* Executing "dry run" playbooks with :ref:`check mode and diff <check_mode_dry>`
* Running playbooks while troubleshooting with :ref:`start and step <playbooks_start_and_step>`
* Correcting tasks during execution with the :ref:`Ansible debugger <playbook_debugger>`
* Controlling how my playbook executes with :ref:`strategies and more <playbooks_strategies>`
* Running tasks, plays, and playbooks :ref:`asynchronously <playbooks_async>`
Advanced features and reference
===============================
* Using :ref:`advanced syntax <playbooks_advanced_syntax>`
* Manipulating :ref:`complex data <complex_data_manipulation>`
* Using :ref:`plugins <plugins_lookup>`
* Using :ref:`playbook keywords <playbook_keywords>`
* Using :ref:`command-line tools <command_line_tools>`
* Rejecting :ref:`specific modules <plugin_filtering_config>`
* Module :ref:`maintenance <modules_support>`
Traditional Table of Contents
=============================
If you prefer to read the entire User Guide, here's a list of the pages in order:
.. toctree:: .. toctree::
:maxdepth: 2 :maxdepth: 2
@ -12,18 +87,47 @@ This guide covers how to work with Ansible, including using the command line, wo
quickstart quickstart
basic_concepts basic_concepts
intro_getting_started intro_getting_started
intro_adhoc
playbooks
playbooks_intro
playbooks_best_practices
become
playbooks_loops
playbooks_delegation
playbooks_conditionals
playbooks_tests
playbooks_blocks
playbooks_handlers
playbooks_error_handling
playbooks_environment
playbooks_reuse
playbooks_reuse_roles
playbooks_reuse_includes
playbooks_tags
intro_inventory intro_inventory
intro_dynamic_inventory intro_dynamic_inventory
intro_patterns intro_patterns
intro_adhoc
connection_details connection_details
command_line_tools command_line_tools
playbooks playbooks_variables
become playbooks_vars_facts
vault vault
playbooks_filters
playbooks_lookups
playbooks_prompts
playbooks_module_defaults
playbooks_checkmode
playbooks_startnstep
playbooks_debugger
playbooks_strategies
playbooks_async
playbooks_advanced_syntax
complex_data_manipulation
plugin_filtering_config
sample_setup sample_setup
modules modules
../plugins/plugins ../plugins/plugins
../reference_appendices/playbooks_keywords
intro_bsd intro_bsd
windows windows
collections_using collections_using

@ -10,11 +10,6 @@ Before we start exploring the main components of Ansible -- playbooks, configura
../installation_guide/index ../installation_guide/index
../dev_guide/overview_architecture ../dev_guide/overview_architecture
intro_getting_started
intro_inventory
intro_dynamic_inventory
intro_patterns
intro_adhoc
../installation_guide/intro_configuration ../installation_guide/intro_configuration
intro_bsd intro_bsd
intro_windows intro_windows

@ -145,7 +145,7 @@ You can specify a pattern as a regular expression by starting the pattern with `
Patterns and ansible-playbook flags Patterns and ansible-playbook flags
----------------------------------- -----------------------------------
You can change the behavior of the patterns defined in playbooks using command-line options. For example, you can run a playbook that defines ``hosts: all`` on a single host by specifying ``-i 127.0.0.2,``. This works even if the host you target is not defined in your inventory. You can also limit the hosts you target on a particular run with the ``--limit`` flag:: You can change the behavior of the patterns defined in playbooks using command-line options. For example, you can run a playbook that defines ``hosts: all`` on a single host by specifying ``-i 127.0.0.2,`` (note the trailing comma). This works even if the host you target is not defined in your inventory. You can also limit the hosts you target on a particular run with the ``--limit`` flag::
ansible-playbook site.yml --limit datacenter2 ansible-playbook site.yml --limit datacenter2

@ -3,7 +3,7 @@
Introduction to modules Introduction to modules
======================= =======================
Modules (also referred to as "task plugins" or "library plugins") are discrete units of code that can be used from the command line or in a playbook task. Ansible executes each module, usually on the remote target node, and collects return values. Modules (also referred to as "task plugins" or "library plugins") are discrete units of code that can be used from the command line or in a playbook task. Ansible executes each module, usually on the remote managed node, and collects return values. In Ansible 2.10 and later, most modules are hosted in collections.
You can execute modules from the command line:: You can execute modules from the command line::
@ -11,34 +11,27 @@ You can execute modules from the command line::
ansible webservers -m ping ansible webservers -m ping
ansible webservers -m command -a "/sbin/reboot -t now" ansible webservers -m command -a "/sbin/reboot -t now"
Each module supports taking arguments. Nearly all modules take ``key=value`` Each module supports taking arguments. Nearly all modules take ``key=value`` arguments, space delimited. Some modules take no arguments, and the command/shell modules simply take the string of the command you want to run.
arguments, space delimited. Some modules take no arguments, and the command/shell modules simply
take the string of the command you want to run.
From playbooks, Ansible modules are executed in a very similar way:: From playbooks, Ansible modules are executed in a very similar way::
- name: reboot the servers
action: command /sbin/reboot -t now
Which can be abbreviated to::
- name: reboot the servers - name: reboot the servers
command: /sbin/reboot -t now command: /sbin/reboot -t now
Another way to pass arguments to a module is using YAML syntax also called 'complex args' :: Another way to pass arguments to a module is using YAML syntax, also called 'complex args' ::
- name: restart webserver - name: restart webserver
service: service:
name: httpd name: httpd
state: restarted state: restarted
All modules return JSON format data. This means modules can be written in any programming language. Modules should be idempotent, and should avoid making any changes if they detect that the current state matches the desired final state. When used in an Ansible playbook, modules can trigger 'change events' in the form of notifying 'handlers' to run additional tasks. All modules return JSON format data. This means modules can be written in any programming language. Modules should be idempotent, and should avoid making any changes if they detect that the current state matches the desired final state. When used in an Ansible playbook, modules can trigger 'change events' in the form of notifying :ref:`handlers <handlers>` to run additional tasks.
Documentation for each module can be accessed from the command line with the ansible-doc tool:: You can access the documentation for each module from the command line with the ansible-doc tool::
ansible-doc yum ansible-doc yum
For a list of all available modules, see the :ref:`Module Docs <modules_by_category>`, or run the following at a command prompt:: For a list of all available modules, see the :ref:`Collection docs <list_of_collections>`, or run the following at a command prompt::
ansible-doc -l ansible-doc -l

@ -32,7 +32,7 @@ Maintenance
Issue Reporting Issue Reporting
=============== ===============
If you find a bug that affects a plugin in the main Ansible repo: If you find a bug that affects a plugin in the main Ansible repo, also known as ``ansible-base``:
#. Confirm that you are running the latest stable version of Ansible or the devel branch. #. Confirm that you are running the latest stable version of Ansible or the devel branch.
#. Look at the `issue tracker in the Ansible repo <https://github.com/ansible/ansible/issues>`_ to see if an issue has already been filed. #. Look at the `issue tracker in the Ansible repo <https://github.com/ansible/ansible/issues>`_ to see if an issue has already been filed.
@ -56,7 +56,7 @@ If you find a bug that affects a module in an Automation Hub collection:
Support Support
======= =======
All plugins that remain in ansible-base and all collections hosted in Automation Hub are supported by Red Hat. No other plugins or collections are supported by Red Hat. If you have a subscription to the Red Hat Ansible Automation Platform, you can find more information and resources on the `Red Hat Customer Portal. <https://access.redhat.com/>`_ All plugins that remain in ``ansible-base`` and all collections hosted in Automation Hub are supported by Red Hat. No other plugins or collections are supported by Red Hat. If you have a subscription to the Red Hat Ansible Automation Platform, you can find more information and resources on the `Red Hat Customer Portal. <https://access.redhat.com/>`_
.. seealso:: .. seealso::

@ -3,32 +3,19 @@
Working with playbooks Working with playbooks
====================== ======================
Playbooks are Ansible's configuration, deployment, and orchestration language. They can describe a policy you want your remote systems to enforce, or a set of steps in a general IT process. Playbooks record and execute Ansible's configuration, deployment, and orchestration functions. They can describe a policy you want your remote systems to enforce, or a set of steps in a general IT process.
If Ansible modules are the tools in your workshop, playbooks are your instruction manuals, and your inventory of hosts are your raw material. If Ansible modules are the tools in your workshop, playbooks are your instruction manuals, and your inventory of hosts are your raw material.
At a basic level, playbooks can be used to manage configurations of and deployments to remote machines. At a more advanced level, they can sequence multi-tier rollouts involving rolling updates, and can delegate actions to other hosts, interacting with monitoring servers and load balancers along the way. At a basic level, playbooks can be used to manage configurations of and deployments to remote machines. At a more advanced level, they can sequence multi-tier rollouts involving rolling updates, and can delegate actions to other hosts, interacting with monitoring servers and load balancers along the way.
While there's a lot of information here, there's no need to learn everything at once. You can start small and pick up more features over time as you need them. Playbooks are designed to be human-readable and are developed in a basic text language. There are multiple ways to organize playbooks and the files they include, and we'll offer up some suggestions on that and making the most out of Ansible.
Playbooks are designed to be human-readable and are developed in a basic text language. There are multiple
ways to organize playbooks and the files they include, and we'll offer up some suggestions on that and making the most out of Ansible.
You should look at `Example Playbooks <https://github.com/ansible/ansible-examples>`_ while reading along with the playbook documentation. These illustrate best practices as well as how to put many of the various concepts together. You should look at `Example Playbooks <https://github.com/ansible/ansible-examples>`_ while reading along with the playbook documentation. These illustrate best practices as well as how to put many of the various concepts together.
.. toctree:: .. toctree::
:maxdepth: 2 :maxdepth: 2
playbooks_intro
playbooks_best_practices
playbooks_reuse
playbooks_reuse_roles
playbooks_variables
playbooks_vars_facts
playbooks_templating playbooks_templating
playbooks_conditionals
playbooks_loops
playbooks_blocks
playbooks_special_topics playbooks_special_topics
playbooks_strategies
guide_rolling_upgrade guide_rolling_upgrade

@ -0,0 +1,137 @@
.. _handlers:
Handlers: running operations on change
======================================
Sometimes you want a task to run only when a change is made on a machine. For example, you may want to restart a service if a task updates the configuration of that service, but not if the configuration is unchanged. Ansible uses handlers to address this use case. Handlers are tasks that only run when notified. Each handler should have a globally unique name.
.. contents::
:local:
Handler example
---------------
This playbook, ``verify-apache.yml``, contains a single play with a handler::
---
- name: verify apache installation
hosts: webservers
vars:
http_port: 80
max_clients: 200
remote_user: root
tasks:
- name: ensure apache is at the latest version
yum:
name: httpd
state: latest
- name: write the apache config file
template:
src: /srv/httpd.j2
dest: /etc/httpd.conf
notify:
- restart apache
- name: ensure apache is running
service:
name: httpd
state: started
handlers:
- name: restart apache
service:
name: httpd
state: restarted
In this example playbook, the second task notifies the handler. A single task can notify more than one handler::
- name: template configuration file
template:
src: template.j2
dest: /etc/foo.conf
notify:
- restart memcached
- restart apache
handlers:
- name: restart memcached
service:
name: memcached
state: restarted
- name: restart apache
service:
name: apache
state: restarted
Controlling when handlers run
-----------------------------
By default, handlers run after all the tasks in a particular play have been completed. This approach is efficient, because the handler only runs once, regardless of how many tasks notify it. For example, if multiple tasks update a configuration file and notify a handler to restart Apache, Ansible only bounces Apache once to avoid unnecessary restarts.
If you need handlers to run before the end of the play, add a task to flush them using the :ref:`meta module <meta_module>`, which executes Ansible actions::
tasks:
- shell: some tasks go here
- meta: flush_handlers
- shell: some other tasks
The ``meta: flush_handlers`` task triggers any handlers that have been notified at that point in the play.
Using variables with handlers
-----------------------------
You may want your Ansible handlers to use variables. For example, if the name of a service varies slightly by distribution, you want your output to show the exact name of the restarted service for each target machine. Avoid placing variables in the name of the handler. Since handler names are templated early on, Ansible may not have a value available for a handler name like this::
handlers:
# this handler name may cause your play to fail!
- name: restart "{{ web_service_name }}"
If the variable used in the handler name is not available, the entire play fails. Changing that variable mid-play **will not** result in newly created handler.
Instead, place variables in the task parameters of your handler. You can load the values using ``include_vars`` like this:
.. code-block:: yaml+jinja
tasks:
- name: Set host variables based on distribution
include_vars: "{{ ansible_facts.distribution }}.yml"
handlers:
- name: restart web service
service:
name: "{{ web_service_name | default('httpd') }}"
state: restarted
Handlers can also "listen" to generic topics, and tasks can notify those topics as follows::
handlers:
- name: restart memcached
service:
name: memcached
state: restarted
listen: "restart web services"
- name: restart apache
service:
name: apache
state: restarted
listen: "restart web services"
tasks:
- name: restart everything
command: echo "this task will restart the web services"
notify: "restart web services"
This use makes it much easier to trigger multiple handlers. It also decouples handlers from their names,
making it easier to share handlers among playbooks and roles (especially when using 3rd party roles from
a shared source like Galaxy).
.. note::
* Handlers always run in the order they are defined, not in the order listed in the notify-statement. This is also the case for handlers using `listen`.
* Handler names and `listen` topics live in a global namespace.
* Handler names are templatable and `listen` topics are not.
* Use unique handler names. If you trigger more than one handler with the same name, the first one(s) get overwritten. Only the last one defined will run.
* You can notify a handler defined inside a static include.
* You cannot notify a handler defined inside a dynamic include.
When using handlers within roles, note that:
* handlers notified within ``pre_tasks``, ``tasks``, and ``post_tasks`` sections are automatically flushed in the end of section where they were notified.
* handlers notified within ``roles`` section are automatically flushed in the end of ``tasks`` section, but before any ``tasks`` handlers.
* handlers are play scoped and as such can be used outside of the role they are defined in.

@ -2,7 +2,7 @@
.. _playbooks_intro: .. _playbooks_intro:
****************** ******************
Intro to Playbooks Intro to playbooks
****************** ******************
Ansible Playbooks offer a repeatable, re-usable, simple configuration management and multi-machine deployment system, one that is well suited to deploying complex applications. If you need to execute a task with Ansible more than once, write a playbook and put it under source control. Then you can use the playbook to push out new configuration or confirm the configuration of remote systems. The playbooks in the `ansible-examples repository <https://github.com/ansible/ansible-examples>`_ illustrate many useful techniques. You may want to look at these in another tab as you read the documentation. Ansible Playbooks offer a repeatable, re-usable, simple configuration management and multi-machine deployment system, one that is well suited to deploying complex applications. If you need to execute a task with Ansible more than once, write a playbook and put it under source control. Then you can use the playbook to push out new configuration or confirm the configuration of remote systems. The playbooks in the `ansible-examples repository <https://github.com/ansible/ansible-examples>`_ illustrate many useful techniques. You may want to look at these in another tab as you read the documentation.
@ -93,138 +93,6 @@ To run your playbook, use the :ref:`ansible-playbook` command::
Use the ``--verbose`` flag when running your playbook to see detailed output from successful modules as well as unsuccessful ones. Use the ``--verbose`` flag when running your playbook to see detailed output from successful modules as well as unsuccessful ones.
.. _handlers:
Handlers: running operations on change
======================================
Sometimes you want a task to run only when a change is made on a machine. For example, you may want to restart a service if a task updates the configuration of that service, but not if the configuration is unchanged. Ansible uses handlers to address this use case. Handlers are tasks that only run when notified. Each handler should have a globally unique name.
This playbook, ``verify-apache.yml``, contains a single play with variables, the remote user, and a handler::
---
- name: verify apache installation
hosts: webservers
vars:
http_port: 80
max_clients: 200
remote_user: root
tasks:
- name: ensure apache is at the latest version
yum:
name: httpd
state: latest
- name: write the apache config file
template:
src: /srv/httpd.j2
dest: /etc/httpd.conf
notify:
- restart apache
- name: ensure apache is running
service:
name: httpd
state: started
handlers:
- name: restart apache
service:
name: httpd
state: restarted
In the example above, the second task notifies the handler. A single task can notify more than one handler::
- name: template configuration file
template:
src: template.j2
dest: /etc/foo.conf
notify:
- restart memcached
- restart apache
handlers:
- name: restart memcached
service:
name: memcached
state: restarted
- name: restart apache
service:
name: apache
state: restarted
Controlling when handlers run
-----------------------------
By default, handlers run after all the tasks in a particular play have been completed. This approach is efficient, because the handler only runs once, regardless of how many tasks notify it. For example, if multiple tasks update a configuration file and notify a handler to restart Apache, Ansible only bounces Apache once to avoid unnecessary restarts.
If you need handlers to run before the end of the play, add a task to flush them using the :ref:`meta module <meta_module>`, which executes Ansible actions::
tasks:
- shell: some tasks go here
- meta: flush_handlers
- shell: some other tasks
The ``meta: flush_handlers`` task triggers any handlers that have been notified at that point in the play.
Using variables with handlers
-----------------------------
You may want your Ansible handlers to use variables. For example, if the name of a service varies slightly by distribution, you want your output to show the exact name of the restarted service for each target machine. Avoid placing variables in the name of the handler. Since handler names are templated early on, Ansible may not have a value available for a handler name like this::
handlers:
# this handler name may cause your play to fail!
- name: restart "{{ web_service_name }}"
If the variable used in the handler name is not available, the entire play fails. Changing that variable mid-play **will not** result in newly created handler.
Instead, place variables in the task parameters of your handler. You can load the values using ``include_vars`` like this:
.. code-block:: yaml+jinja
tasks:
- name: Set host variables based on distribution
include_vars: "{{ ansible_facts.distribution }}.yml"
handlers:
- name: restart web service
service:
name: "{{ web_service_name | default('httpd') }}"
state: restarted
Handlers can also "listen" to generic topics, and tasks can notify those topics as follows::
handlers:
- name: restart memcached
service:
name: memcached
state: restarted
listen: "restart web services"
- name: restart apache
service:
name: apache
state: restarted
listen: "restart web services"
tasks:
- name: restart everything
command: echo "this task will restart the web services"
notify: "restart web services"
This use makes it much easier to trigger multiple handlers. It also decouples handlers from their names,
making it easier to share handlers among playbooks and roles (especially when using 3rd party roles from
a shared source like Galaxy).
.. note::
* Handlers always run in the order they are defined, not in the order listed in the notify-statement. This is also the case for handlers using `listen`.
* Handler names and `listen` topics live in a global namespace.
* Handler names are templatable and `listen` topics are not.
* Use unique handler names. If you trigger more than one handler with the same name, the first one(s) get overwritten. Only the last one defined will run.
* You can notify a handler defined inside a static include.
* You cannot notify a handler defined inside a dynamic include.
When using handlers within roles, note that:
* handlers notified within ``pre_tasks``, ``tasks``, and ``post_tasks`` sections are automatically flushed in the end of section where they were notified.
* handlers notified within ``roles`` section are automatically flushed in the end of ``tasks`` section, but before any ``tasks`` handlers.
* handlers are play scoped and as such can be used outside of the role they are defined in.
.. _playbook_ansible-pull: .. _playbook_ansible-pull:
Ansible-Pull Ansible-Pull

@ -1,27 +1,8 @@
:orphan:
.. _playbooks_special_topics: .. _playbooks_special_topics:
Advanced Playbooks Features Advanced playbooks features
=========================== ===========================
As you write more playbooks and roles, you might have some special use cases. For example, you may want to execute "dry runs" of your playbooks (:ref:`check_mode_dry`), ask playbook users to supply information (:ref:`playbooks_prompts`), retrieve information from an external datastore or API (:ref:`lookup_plugins`), or change the way Ansible handles failures (:ref:`playbooks_error_handling`). The topics listed on this page cover these use cases and many more. If you cannot achieve your goals with basic Ansible concepts and actions, browse through these topics for help with your use case. This page is obsolete. Refer to the :ref:`main User Guide index page <user_guide_index>` for links to all playbook-related topics. Please update any links you may have made directly to this page.
.. toctree::
:maxdepth: 1
become
playbooks_async
playbooks_checkmode
playbooks_debugger
playbooks_delegation
playbooks_environment
playbooks_error_handling
playbooks_advanced_syntax
complex_data_manipulation
../plugins/plugins
playbooks_prompts
playbooks_tags
vault
playbooks_startnstep
../reference_appendices/playbooks_keywords
playbooks_lookups
playbooks_module_defaults

@ -1,8 +1,6 @@
With the release of Ansible 2.5, the recommended way to perform loops is the use the new ``loop`` keyword instead of ``with_X`` style loops. In most cases, loops work best with the ``loop`` keyword instead of ``with_X`` style loops. The ``loop`` syntax is usually best expressed using filters instead of more complex use of ``query`` or ``lookup``.
In many cases, ``loop`` syntax is better expressed using filters instead of more complex use of ``query`` or ``lookup``. These examples show how to convert many common ``with_`` style loops to ``loop`` and filters.
The following examples will show how to convert many common ``with_`` style loops to ``loop`` and filters.
with_list with_list
--------- ---------

@ -71,7 +71,7 @@ class VaultCLI(CLI):
vault_id = opt_help.argparse.ArgumentParser(add_help=False) vault_id = opt_help.argparse.ArgumentParser(add_help=False)
vault_id.add_argument('--encrypt-vault-id', default=[], dest='encrypt_vault_id', vault_id.add_argument('--encrypt-vault-id', default=[], dest='encrypt_vault_id',
action='store', type=str, action='store', type=str,
help='the vault id used to encrypt (required if more than vault-id is provided)') help='the vault id used to encrypt (required if more than one vault-id is provided)')
create_parser = subparsers.add_parser('create', help='Create new vault encrypted file', parents=[vault_id, common]) create_parser = subparsers.add_parser('create', help='Create new vault encrypted file', parents=[vault_id, common])
create_parser.set_defaults(func=self.execute_create) create_parser.set_defaults(func=self.execute_create)

Loading…
Cancel
Save