Conversation
…it code 7) Zypper exits with code 7 (ZYPPER_EXIT_ERR_ZYPP) when another process holds the system management lock. This is a transient condition, but add_repository(), _install_packages(), and _uninstall_packages() all treated it as a hard failure. Add retry logic (up to 5 attempts with 10s delay) that detects exit code 7, waits for the competing zypper process to finish, then retries the command.
Contributor
There was a problem hiding this comment.
Pull request overview
This PR improves SUSE package management robustness by retrying zypper operations when they fail due to transient lock contention (exit code 7), instead of treating it as a hard failure.
Changes:
- Add SUSE-specific constants for zypper lock exit code, max retries, and retry delay.
- Wrap
zypper ar,zypper rm, andzypper inexecutions with retry logic that waits for competingzypperprocesses and then retries.
Comments suppressed due to low confidence (1)
lisa/operating_system.py:2496
- After the retry loop, if zypper still returns exit code 7, the code falls into the generic “Unexpected exit_code” path. Consider handling the “lock contention after max retries” case explicitly to produce a clearer, actionable error (include retry count/delay and indicate it was zypper lock contention).
if install_result.exit_code == self._ZYPPER_EXIT_LOCK:
self._log.debug(
f"zypper lock contention (exit code 7), "
f"retry {retry_num + 1}/{self._ZYPPER_LOCK_MAX_RETRIES}"
)
self.wait_running_process("zypper")
time.sleep(self._ZYPPER_LOCK_RETRY_DELAY)
continue
break
# zypper exit codes that indicate dependency/resolution issues:
# 1: ZYPPER_EXIT_ERR_BUG - Unexpected situation
# 4: ZYPPER_EXIT_INF_CAP_NOT_FOUND - Capability not found or dependency problem
# 100: ZYPPER_EXIT_INF_UPDATE_NEEDED - Updates available
# If installation failed due to dependency conflicts, retry with
# --force-resolution to allow zypper to automatically resolve conflicts
if install_result.exit_code in (1, 4, 100):
self._log.debug(
f"Installation failed with exit code {install_result.exit_code}, "
"retrying with --force-resolution to resolve dependency conflicts."
)
command_with_force = f"zypper --non-interactive {add_args}"
if not signed:
command_with_force += " --no-gpg-checks "
command_with_force += f" in --force-resolution {' '.join(packages)}"
install_result = self._node.execute(
command_with_force, shell=True, sudo=True, timeout=timeout
)
if install_result.exit_code in (1, 4, 100):
raise LisaException(
f"Failed to install {packages}. exit_code: {install_result.exit_code}, "
f"stdout: {install_result.stdout}, stderr: {install_result.stderr}"
)
elif install_result.exit_code == 0:
self._log.debug(f"{packages} is/are installed successfully.")
else:
raise LisaException(
LiliDeng
reviewed
Mar 28, 2026
…dundancy Agent-Logs-Url: https://github.com/microsoft/lisa/sessions/811dfb5e-4db6-4f05-9a68-e0260c0c1053 Co-authored-by: LiliDeng <10083705+LiliDeng@users.noreply.github.com>
Collaborator
|
@copilot no need to change the code format, it brings below CI check error. |
…I failures Agent-Logs-Url: https://github.com/microsoft/lisa/sessions/07c59752-aa2e-4bbf-8697-f7a3559478fb Co-authored-by: LiliDeng <10083705+LiliDeng@users.noreply.github.com>
Contributor
... Fixed in commit e4194d4. Reverted the four pre-existing lines that Black reformatted (lines 230, 740, 761, 1611) back to their original multi-line form, so those flake8 errors (E704/E701/BLK100) are gone. The actual code changes are untouched. |
- Move wait_running_process into retry wrapper (before every attempt) - Wrap _initialize_package_installation refresh with retry - Wrap _update_packages with retry - Wrap --force-resolution install path with retry - Elevate lock contention log from debug to warning - Remove dead code after exhaustion raise
Zypper exits with code 8 (ZYPPER_EXIT_ERR_COMMIT) when the RPM transaction fails because another process holds .rpm.lock. The previous retry logic only caught exit code 7 (zypper-level lock) but missed this RPM-level lock that occurs during the transaction phase. Add _is_zypper_lock_error() helper that detects both: - Exit code 7: zypper management lock - Exit code 8 + 'can't create transaction lock on ...rpm.lock': RPM transaction lock
LiliDeng
approved these changes
Apr 2, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Zypper exits with code 7 (ZYPPER_EXIT_ERR_ZYPP) when another process holds the system management lock. This is a transient condition, but
add_repository(),_install_packages(), and_uninstall_packages()in theSuseclass all treated it as a hard failure.Adds retry logic (up to 5 attempts with 10s delay +
wait_running_process) that detects exit code 7, waits for the competing zypper process to finish, then retries the command.Validation Results