Workaround bug in jinja2-3.0.0 and 3.0.1 (#74795)

Jinja2-3.0.0 and 3.0.1 has a bug where undefined values cannot be
checked to see if they contain a value: https://github.com/pallets/jinja/issues/1448#issuecomment-846029509

We workaround this in two ways, either of which would be sufficient:
* Normalize the data so that choices is an empty iterable when it isn't
  specified in the documentation.  This is what antsibull-docs (and thus
  documentation builds on 2.10+) do.
* Change the logic in the template to check whether choices exists
  before checking containment.  This better expresses the logic at that
  point in the template (if there is a default value but there is not a
  list of choices, then display the default in its own string) so it's
  a good change to make as well.
This commit is contained in:
Toshio Kuratomi 2021-06-03 13:13:43 -07:00 committed by GitHub
parent d53fb60af3
commit 0691475caf
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
2 changed files with 20 additions and 2 deletions

View file

@ -144,6 +144,7 @@ Parameters
{% elif choice is sameas false %}
{% set choice = 'no' %}
{% endif %}
{# Format default values differently (whenever a choice is one of the default values) #}
{% if (value.default is not list and value.default == choice) or (value.default is list and choice in value.default) %}
<li><div style="color: blue"><b>@{ choice | escape }@</b>&nbsp;&larr;</div></li>
{% else %}
@ -152,8 +153,12 @@ Parameters
{% endfor %}
</ul>
{% endif %}
{# Show default value, when multiple choice or no choices #}
{% if value.default is defined and value.default not in value.choices %}
{# Show default value on a separate line when there is a non-None default (None
is usually a sentinel that shows the user didn't specify it) and there
either are no choices (like a freeform string) or the default does not exist
in choices
#}
{% if value.default is defined and value.default is not none and (not value.choices or value.default not in value.choices) %}
<b>Default:</b><br/><div style="color: blue">@{ value.default | tojson | escape }@</div>
{% endif %}
</td>

View file

@ -380,6 +380,19 @@ def process_options(module, options, full_key=None):
if 'version_added' in v and too_old(v['version_added']):
del v['version_added']
# Set default values so that consumers can count on these being present Should really
# do this for all of the values that are optional but the template may rely on certain
# values being unset rather than falsey. antsibull sets default values and the
# templates were modified to check for falsey rather than existence so 2.10.x will do
# this the right way.
defaults = {
'choices': (),
}
for key, default in defaults.items():
if key not in v:
v[key] = default
if 'suboptions' in v and v['suboptions']:
if isinstance(v['suboptions'], dict):
process_options(module, v['suboptions'], full_key=full_key_k)