Skip to content

[6.16.z] Replace library/busybox with lighter container repo - #20858

Merged
lpramuk merged 1 commit into
SatelliteQE:6.16.zfrom
lpramuk:616_replace_busybox_container_repo
Feb 25, 2026
Merged

[6.16.z] Replace library/busybox with lighter container repo#20858
lpramuk merged 1 commit into
SatelliteQE:6.16.zfrom
lpramuk:616_replace_busybox_container_repo

Conversation

@lpramuk

@lpramuk lpramuk commented Feb 24, 2026

Copy link
Copy Markdown
Contributor

Manual cherrypick of PR: #20671
(cherry picked from commit 8ac73bc)

Problem Statement

Gradually over time the library/busybox repo is becoming more and more huge.
The problem with repo sync arises especially in IPv6 environment where the traffic goes over IPv6-to-4 proxy.

Testing revealed that syncing over IPv4 takes approx. 10 min while syncing over IPv6 takes 25 min and tends to time out quite often.

Solution

Find more suitable replacement for testing container repo target

Related Issues

SAT-41831
#20855

Summary by Sourcery

Update container test image configuration and improve container lifecycle handling in CLI tests.

Enhancements:

  • Run test containers in detached mode and guard stop/remove operations by validating container IDs from docker output.

Tests:

  • Adjust CLI container management test to work with the new default test container image and more robustly manage created containers.

Chores:

  • Change the default upstream test container image from the large library/busybox repository to the lighter jmalloc/echo-server repository in configuration and templates.

@lpramuk lpramuk self-assigned this Feb 24, 2026
@lpramuk lpramuk added No-CherryPick PR doesnt need CherryPick to previous branches 6.16.z labels Feb 24, 2026
@sourcery-ai

sourcery-ai Bot commented Feb 24, 2026

Copy link
Copy Markdown
Contributor
Reviewer's guide (collapsed on small PRs)

Reviewer's Guide

Updates container-related tests and configuration to use a lighter container image in place of library/busybox, and adjusts the test to run containers in detached mode while more safely handling container cleanup.

Sequence diagram for updated container test lifecycle

sequenceDiagram
    actor Tester
    participant TestCase as TestCase_container_management
    participant DockerClient as Docker_client

    Tester->>TestCase: run
    TestCase->>DockerClient: pull jmalloc/echo-server
    DockerClient-->>TestCase: image pulled

    TestCase->>DockerClient: run container detached
    DockerClient-->>TestCase: container_id

    TestCase->>DockerClient: perform test operations
    DockerClient-->>TestCase: responses

    TestCase->>DockerClient: stop container
    DockerClient-->>TestCase: stopped

    TestCase->>DockerClient: remove container
    DockerClient-->>TestCase: removed

    TestCase-->>Tester: report test result
Loading

File-Level Changes

Change Details Files
Adjust container management CLI test to run containers in detached mode and make cleanup depend on a valid container ID.
  • Change docker run invocation to use detached mode so the command returns a container ID instead of attaching to the container process.
  • Parse docker run stdout as a hex hash to obtain the container ID rather than grepping docker ps output.
  • Guard stop/remove operations by checking that a valid container ID was captured before issuing docker stop and docker rm commands.
tests/foreman/cli/test_container_management.py
Switch default upstream container image from library/busybox to a lighter echo server image.
  • Update the default value of container.upstream_name from library/busybox to jmalloc/echo-server in configuration validators so tests and tooling use the lighter image by default.
robottelo/config/validators.py

Possibly linked issues

  • #[Failed-AutoCherryPick]: Issue tracks failed auto-cherrypick; this PR is the manual cherrypick of that same change to 6.16.z.

Tips and commands

Interacting with Sourcery

  • Trigger a new review: Comment @sourcery-ai review on the pull request.
  • Continue discussions: Reply directly to Sourcery's review comments.
  • Generate a GitHub issue from a review comment: Ask Sourcery to create an
    issue from a review comment by replying to it. You can also reply to a
    review comment with @sourcery-ai issue to create an issue from it.
  • Generate a pull request title: Write @sourcery-ai anywhere in the pull
    request title to generate a title at any time. You can also comment
    @sourcery-ai title on the pull request to (re-)generate the title at any time.
  • Generate a pull request summary: Write @sourcery-ai summary anywhere in
    the pull request body to generate a PR summary at any time exactly where you
    want it. You can also comment @sourcery-ai summary on the pull request to
    (re-)generate the summary at any time.
  • Generate reviewer's guide: Comment @sourcery-ai guide on the pull
    request to (re-)generate the reviewer's guide at any time.
  • Resolve all Sourcery comments: Comment @sourcery-ai resolve on the
    pull request to resolve all Sourcery comments. Useful if you've already
    addressed all the comments and don't want to see them anymore.
  • Dismiss all Sourcery reviews: Comment @sourcery-ai dismiss on the pull
    request to dismiss all existing Sourcery reviews. Especially useful if you
    want to start fresh with a new review - don't forget to comment
    @sourcery-ai review to trigger a new review!

Customizing Your Experience

Access your dashboard to:

  • Enable or disable review features such as the Sourcery-generated pull request
    summary, the reviewer's guide, and others.
  • Change the review language.
  • Add, remove or edit custom review instructions.
  • Adjust other review settings.

Getting Help

@sourcery-ai sourcery-ai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hey - I've found 1 issue, and left some high level feedback:

  • In test_positive_pull_image, container_id can be referenced in the finally block before assignment if the regex match fails; initialize it (e.g., to None) before the try and guard accordingly.
  • You introduced re.match in test_container_management.py but there is no corresponding import re in the diff; ensure the module is imported in this file.
  • After changing the default container.upstream_name to jmalloc/echo-server, consider whether container.alternative_upstream_names should also be updated to include or align with this new default.
Prompt for AI Agents
Please address the comments from this code review:

## Overall Comments
- In `test_positive_pull_image`, `container_id` can be referenced in the `finally` block before assignment if the regex match fails; initialize it (e.g., to `None`) before the `try` and guard accordingly.
- You introduced `re.match` in `test_container_management.py` but there is no corresponding `import re` in the diff; ensure the module is imported in this file.
- After changing the default `container.upstream_name` to `jmalloc/echo-server`, consider whether `container.alternative_upstream_names` should also be updated to include or align with this new default.

## Individual Comments

### Comment 1
<location path="tests/foreman/cli/test_container_management.py" line_range="97-102" />
<code_context>
             assert result.status == 0
             try:
-                result = module_container_contenthost.execute(f'docker run {repo["published-at"]}')
+                result = module_container_contenthost.execute(
+                    f'docker run -d {repo["published-at"]}'
+                )
                 assert result.status == 0
+                match = re.match(r'^[0-9a-f]+$', result.stdout)
+                if match:
+                    container_id = match.group(0)
             finally:
</code_context>
<issue_to_address>
**issue:** Potential use of uninitialized `container_id` and missing assertion on container ID format in the test

`container_id` is only set inside the `if match:` block but used in `finally`, so if `re.match` returns `None` you’ll hit an `UnboundLocalError` there. Initialize `container_id = None` before the `try:` and have the cleanup check it safely. Also, instead of silently skipping cleanup when `match` is falsy, assert that the output is a valid container ID, e.g.:

```python
container_id = None
...
container_id = result.stdout.strip()
assert re.match(r"^[0-9a-f]+$", container_id), f"Unexpected container id: {container_id!r}"
```

so the test explicitly verifies the expected format and fails if Docker returns something unexpected.
</issue_to_address>

Sourcery is free for open source - if you like our reviews please consider sharing them ✨
Help me be more useful! Please click 👍 or 👎 on each comment and I'll use the feedback to improve your reviews.

Comment on lines +97 to +102
result = module_container_contenthost.execute(
f'docker run -d {repo["published-at"]}'
)
assert result.status == 0
match = re.match(r'^[0-9a-f]+$', result.stdout)
if match:

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

issue: Potential use of uninitialized container_id and missing assertion on container ID format in the test

container_id is only set inside the if match: block but used in finally, so if re.match returns None you’ll hit an UnboundLocalError there. Initialize container_id = None before the try: and have the cleanup check it safely. Also, instead of silently skipping cleanup when match is falsy, assert that the output is a valid container ID, e.g.:

container_id = None
...
container_id = result.stdout.strip()
assert re.match(r"^[0-9a-f]+$", container_id), f"Unexpected container id: {container_id!r}"

so the test explicitly verifies the expected format and fails if Docker returns something unexpected.

@lpramuk

lpramuk commented Feb 25, 2026

Copy link
Copy Markdown
Contributor Author
trigger: test-robottelo
pytest: >-
  -v
  tests/foreman/api/test_capsulecontent.py::TestCapsuleContentManagement::test_positive_content_counts_for_mixed_cv
  tests/foreman/api/test_docker.py::TestDockerRepository
  tests/foreman/api/test_http_proxy.py::test_positive_end_to_end[module_repos_collection_with_manifest0-unauth_http_proxy]
  tests/foreman/api/test_product.py::test_positive_sync_several_repos
  tests/foreman/api/test_repository.py::TestDockerRepository::test_positive_create
  tests/foreman/api/test_repository.py::TestDockerRepository::test_positive_delete_product_with_synced_repo
  tests/foreman/api/test_repository.py::TestDockerRepository::test_positive_synchronize_docker_repo_with_included_tags
  tests/foreman/api/test_repository.py::TestDockerRepository::test_negative_synchronize_docker_repo_with_mix_valid_invalid_tags
  tests/foreman/api/test_repository.py::TestDockerRepository::test_negative_synchronize_docker_repo_with_invalid_tags
  tests/foreman/cli/test_capsulecontent.py::test_positive_repair_artifacts
  tests/foreman/cli/test_capsulecontent.py::test_positive_content_counts_for_mixed_cv
  tests/foreman/cli/test_container_management.py::TestDockerClient::test_positive_pull_image
  tests/foreman/cli/test_container_management.py::TestDockerClient::test_positive_container_admin_end_to_end_search
  tests/foreman/cli/test_container_management.py::TestDockerClient::test_positive_container_admin_end_to_end_pull
  tests/foreman/cli/test_contentview.py::TestContentView::test_positive_remove_cv_version_from_multi_env
  tests/foreman/cli/test_contentview.py::TestContentViewFileRepo::test_promote_ccv_to_lce_with_nondefault_pattern
  tests/foreman/cli/test_docker.py::TestDockerRepository::test_positive_create_with_name
  tests/foreman/cli/test_docker.py::TestDockerRepository::test_positive_create_repos_using_same_product
  tests/foreman/cli/test_docker.py::TestDockerRepository::test_positive_create_repos_using_multiple_products
  tests/foreman/cli/test_docker.py::TestDockerRepository::test_positive_sync
  tests/foreman/cli/test_docker.py::TestDockerRepository::test_positive_delete_random_repo_by_id
  tests/foreman/cli/test_docker.py::TestDockerContentView::test_positive_add_docker_repos_by_id
  tests/foreman/cli/test_repository.py::TestRepository::test_positive_create_docker_repo_with_upstream_name
  tests/foreman/cli/test_repository.py::TestRepository::test_positive_create_docker_repo_with_name
  tests/foreman/cli/test_repository.py::TestRepository::test_positive_synchronize_docker_repo
  tests/foreman/cli/test_repository.py::TestRepository::test_verify_checksum_container_repo
  tests/foreman/cli/test_repository.py::TestRepository::test_positive_synchronize_docker_repo_set_tags_later_additive
  tests/foreman/cli/test_repository.py::TestRepository::test_positive_synchronize_docker_repo_set_tags_later_content_only
  tests/foreman/cli/test_repository.py::TestRepository::test_negative_synchronize_docker_repo_with_mix_valid_invalid_tags
  tests/foreman/cli/test_satellitesync.py::TestRepositoryExport::test_positive_export_repository_docker
  tests/foreman/cli/test_satellitesync.py::TestRepositoryExport::test_positive_export_version_docker
  tests/foreman/ui/test_containerimagetag.py::test_positive_search
network_type: ipv6

@Satellite-QE

Copy link
Copy Markdown
Collaborator

PRT Result

Build Number: 14450
Build Status: UNSTABLE
PRT Comment: pytest -v tests/foreman/api/test_capsulecontent.py::TestCapsuleContentManagement::test_positive_content_counts_for_mixed_cv tests/foreman/api/test_docker.py::TestDockerRepository tests/foreman/api/test_http_proxy.py::test_positive_end_to_end[module_repos_collection_with_manifest0-unauth_http_proxy] tests/foreman/api/test_product.py::test_positive_sync_several_repos tests/foreman/api/test_repository.py::TestDockerRepository::test_positive_create tests/foreman/api/test_repository.py::TestDockerRepository::test_positive_delete_product_with_synced_repo tests/foreman/api/test_repository.py::TestDockerRepository::test_positive_synchronize_docker_repo_with_included_tags tests/foreman/api/test_repository.py::TestDockerRepository::test_negative_synchronize_docker_repo_with_mix_valid_invalid_tags tests/foreman/api/test_repository.py::TestDockerRepository::test_negative_synchronize_docker_repo_with_invalid_tags tests/foreman/cli/test_capsulecontent.py::test_positive_repair_artifacts tests/foreman/cli/test_capsulecontent.py::test_positive_content_counts_for_mixed_cv tests/foreman/cli/test_container_management.py::TestDockerClient::test_positive_pull_image tests/foreman/cli/test_container_management.py::TestDockerClient::test_positive_container_admin_end_to_end_search tests/foreman/cli/test_container_management.py::TestDockerClient::test_positive_container_admin_end_to_end_pull tests/foreman/cli/test_contentview.py::TestContentView::test_positive_remove_cv_version_from_multi_env tests/foreman/cli/test_contentview.py::TestContentViewFileRepo::test_promote_ccv_to_lce_with_nondefault_pattern tests/foreman/cli/test_docker.py::TestDockerRepository::test_positive_create_with_name tests/foreman/cli/test_docker.py::TestDockerRepository::test_positive_create_repos_using_same_product tests/foreman/cli/test_docker.py::TestDockerRepository::test_positive_create_repos_using_multiple_products tests/foreman/cli/test_docker.py::TestDockerRepository::test_positive_sync tests/foreman/cli/test_docker.py::TestDockerRepository::test_positive_delete_random_repo_by_id tests/foreman/cli/test_docker.py::TestDockerContentView::test_positive_add_docker_repos_by_id tests/foreman/cli/test_repository.py::TestRepository::test_positive_create_docker_repo_with_upstream_name tests/foreman/cli/test_repository.py::TestRepository::test_positive_create_docker_repo_with_name tests/foreman/cli/test_repository.py::TestRepository::test_positive_synchronize_docker_repo tests/foreman/cli/test_repository.py::TestRepository::test_verify_checksum_container_repo tests/foreman/cli/test_repository.py::TestRepository::test_positive_synchronize_docker_repo_set_tags_later_additive tests/foreman/cli/test_repository.py::TestRepository::test_positive_synchronize_docker_repo_set_tags_later_content_only tests/foreman/cli/test_repository.py::TestRepository::test_negative_synchronize_docker_repo_with_mix_valid_invalid_tags tests/foreman/cli/test_satellitesync.py::TestRepositoryExport::test_positive_export_repository_docker tests/foreman/cli/test_satellitesync.py::TestRepositoryExport::test_positive_export_version_docker tests/foreman/ui/test_containerimagetag.py::test_positive_search --external-logging
Test Result : ====== 1 failed, 100 passed, 831 warnings, 3 errors in 4575.65s (1:16:15) ======

@Satellite-QE Satellite-QE added the PRT-Failed Indicates that latest PRT run is failed for the PR label Feb 25, 2026
@lpramuk

lpramuk commented Feb 25, 2026

Copy link
Copy Markdown
Contributor Author

PRT failures are caused by the fact we dont use IPv6 for Satellite 6.16

So automation in 6.16.z branch is not IPv6 ready
SAT 6.16 (ipv6) <----- curl failed ----- Client (ipv4 - wrong)

@lpramuk
lpramuk merged commit 5f8720b into SatelliteQE:6.16.z Feb 25, 2026
15 of 16 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

6.16.z No-CherryPick PR doesnt need CherryPick to previous branches PRT-Failed Indicates that latest PRT run is failed for the PR

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants