Skip to content

Custom Linting Rules Examples #4263

@Tompage1994

Description

@Tompage1994
Summary

The example custom linting rules in the docs do not work if you simply copy and paste them.

Issue Type
  • Bug Report
OS / ENVIRONMENT
ansible-lint --version
ansible-lint 24.7.0 using ansible-core:2.17.1 ansible-compat:24.7.0 ruamel-yaml:0.18.6 ruamel-yaml-clib:0.2.8
  • ansible installation method: pip
  • ansible-lint installation method: pip
STEPS TO REPRODUCE
  1. Create the two rules from the documentation and run
Desired Behavior

Should capture correctly any violations of the rule and output.

Actual Behavior
Traceback (most recent call last):
  File "/Users/tpage/Documents/internal/test/custom-ansible-lint/venv/bin/ansible-lint", line 8, in <module>
    sys.exit(_run_cli_entrypoint())
             ^^^^^^^^^^^^^^^^^^^^^
  File "/Users/tpage/Documents/internal/test/custom-ansible-lint/venv/lib/python3.12/site-packages/ansiblelint/__main__.py", line 408, in _run_cli_entrypoint
    sys.exit(main(sys.argv))
             ^^^^^^^^^^^^^^
  File "/Users/tpage/Documents/internal/test/custom-ansible-lint/venv/lib/python3.12/site-packages/ansiblelint/__main__.py", line 348, in main
    rules = RulesCollection(
            ^^^^^^^^^^^^^^^^
  File "/Users/tpage/Documents/internal/test/custom-ansible-lint/venv/lib/python3.12/site-packages/ansiblelint/rules/__init__.py", line 418, in __init__
    for rule in load_plugins(rulesdirs_str):
  File "/Users/tpage/Documents/internal/test/custom-ansible-lint/venv/lib/python3.12/site-packages/ansiblelint/rules/__init__.py", line 355, in load_plugins
    import_module(f"{f.stem}")
  File "/Library/Frameworks/Python.framework/Versions/3.12/lib/python3.12/importlib/__init__.py", line 90, in import_module
    return _bootstrap._gcd_import(name[level:], package, level)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "<frozen importlib._bootstrap>", line 1387, in _gcd_import
  File "<frozen importlib._bootstrap>", line 1360, in _find_and_load
  File "<frozen importlib._bootstrap>", line 1331, in _find_and_load_unlocked
  File "<frozen importlib._bootstrap>", line 935, in _load_unlocked
  File "<frozen importlib._bootstrap_external>", line 995, in exec_module
  File "<frozen importlib._bootstrap>", line 488, in _call_with_frames_removed
  File "/Users/tpage/Documents/internal/test/custom-ansible-lint/lintrules-examples/DeprecatedVariableRule.py", line 3, in <module>
    class DeprecatedVariableRule(AnsibleLintRule):
  File "/Users/tpage/Documents/internal/test/custom-ansible-lint/lintrules-examples/DeprecatedVariableRule.py", line 11, in DeprecatedVariableRule
    def match(self, line: str) -> Union[bool, str]:
                                  ^^^^^
NameError: name 'Union' is not defined

Even when adding an import for the type checking you get the following error if trying to output in JSON format:

$ ansible-lint -R playbook.yml -f json

Traceback (most recent call last):
  File "/Users/tpage/Documents/internal/test/custom-ansible-lint/venv/bin/ansible-lint", line 8, in <module>
    sys.exit(_run_cli_entrypoint())
             ^^^^^^^^^^^^^^^^^^^^^
  File "/Users/tpage/Documents/internal/test/custom-ansible-lint/venv/lib/python3.12/site-packages/ansiblelint/__main__.py", line 408, in _run_cli_entrypoint
    sys.exit(main(sys.argv))
             ^^^^^^^^^^^^^^
  File "/Users/tpage/Documents/internal/test/custom-ansible-lint/venv/lib/python3.12/site-packages/ansiblelint/__main__.py", line 387, in main
    app.render_matches(result.matches)
  File "/Users/tpage/Documents/internal/test/custom-ansible-lint/venv/lib/python3.12/site-packages/ansiblelint/app.py", line 84, in render_matches
    self.formatter.format_result(matches),
    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/tpage/Documents/internal/test/custom-ansible-lint/venv/lib/python3.12/site-packages/ansiblelint/formatters/__init__.py", line 182, in format_result
    return json.dumps(result, sort_keys=False)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Library/Frameworks/Python.framework/Versions/3.12/lib/python3.12/json/__init__.py", line 231, in dumps
    return _default_encoder.encode(obj)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Library/Frameworks/Python.framework/Versions/3.12/lib/python3.12/json/encoder.py", line 200, in encode
    chunks = self.iterencode(o, _one_shot=True)
             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Library/Frameworks/Python.framework/Versions/3.12/lib/python3.12/json/encoder.py", line 258, in iterencode
    return _iterencode(o, 0)
           ^^^^^^^^^^^^^^^^^
  File "/Library/Frameworks/Python.framework/Versions/3.12/lib/python3.12/json/encoder.py", line 180, in default
    raise TypeError(f'Object of type {o.__class__.__name__} '
TypeError: Object of type set is not JSON serializable

After some debugging I've found this is because of the line

    tags = { 'deprecations' }

which should be

    tags = ['deprecations']

The TaskHasTag example also has several errors

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    Status

    Done

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions