From 4195cbb3645d2c3b81101ccbaf7ec80047a1e9b5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?St=C3=A9phane=20Graber?= Date: Mon, 7 Jul 2025 14:52:55 -0400 Subject: [PATCH] incus_connection: Improve error handling (#10349) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Related to #10344 This tweaks the error handling logic to work with more versions of Incus as well as catching some of the project and instance access errors. The full context (instance name, project name and remote name) is now included so that the user can easily diagnose access problems. Signed-off-by: Stéphane Graber --- .../10349-incus_connection-error-handling.yml | 2 ++ plugins/connection/incus.py | 32 ++++++++++++++++--- 2 files changed, 30 insertions(+), 4 deletions(-) create mode 100644 changelogs/fragments/10349-incus_connection-error-handling.yml diff --git a/changelogs/fragments/10349-incus_connection-error-handling.yml b/changelogs/fragments/10349-incus_connection-error-handling.yml new file mode 100644 index 0000000000..b35da354d2 --- /dev/null +++ b/changelogs/fragments/10349-incus_connection-error-handling.yml @@ -0,0 +1,2 @@ +bugfixes: + - incus connection plugin - fix error handling to return more useful Ansible errors to the user (https://github.com/ansible-collections/community.general/issues/10344, https://github.com/ansible-collections/community.general/pull/10349). diff --git a/plugins/connection/incus.py b/plugins/connection/incus.py index 62a958b504..4f73d05532 100644 --- a/plugins/connection/incus.py +++ b/plugins/connection/incus.py @@ -155,11 +155,35 @@ class Connection(ConnectionBase): stdout = to_text(stdout) stderr = to_text(stderr) - if stderr == "Error: Instance is not running.\n": - raise AnsibleConnectionFailure(f"instance not running: {self._instance()}") + if stderr.startswith("Error: ") and stderr.rstrip().endswith( + ": Instance is not running" + ): + raise AnsibleConnectionFailure( + f"instance not running: {self._instance()} (remote={self.get_option('remote')}, project={self.get_option('project')})" + ) - if stderr == "Error: Instance not found\n": - raise AnsibleConnectionFailure(f"instance not found: {self._instance()}") + if stderr.startswith("Error: ") and stderr.rstrip().endswith( + ": Instance not found" + ): + raise AnsibleConnectionFailure( + f"instance not found: {self._instance()} (remote={self.get_option('remote')}, project={self.get_option('project')})" + ) + + if ( + stderr.startswith("Error: ") + and ": User does not have permission " in stderr + ): + raise AnsibleConnectionFailure( + f"instance access denied: {self._instance()} (remote={self.get_option('remote')}, project={self.get_option('project')})" + ) + + if ( + stderr.startswith("Error: ") + and ": User does not have entitlement " in stderr + ): + raise AnsibleConnectionFailure( + f"instance access denied: {self._instance()} (remote={self.get_option('remote')}, project={self.get_option('project')})" + ) return process.returncode, stdout, stderr