def test_copy_requires_rpm_signature(controller):
    copy_sig = CopyOptions(require_signed_rpms=True)
    copy_nosig = CopyOptions(require_signed_rpms=False)

    src = YumRepository(id="src-repo")
    dest = YumRepository(id="dest-repo")
    controller.insert_repository(src)
    controller.insert_repository(dest)

    src_units = [
        # A signed RPM
        RpmUnit(
            name="bash",
            version="4.0",
            release="1",
            arch="x86_64",
            filename="bash-4.0-1.x86_64.rpm",
            signing_key="a1b2c3",
        ),
        # An unsigned RPM
        RpmUnit(
            name="ksh",
            version="5.0",
            release="1",
            arch="x86_64",
            filename="ksh-5.0-1.x86_64.rpm",
        ),
    ]
    controller.insert_units(src, src_units)

    client = controller.client

    # Repos are initially detached, re-fetch them via client
    src = client.get_repository(src.id).result()
    dest = client.get_repository(dest.id).result()

    # First, try a copy with default behavior.
    assert client.copy_content(src, dest).result()

    # It should have copied only the signed RPM into the dest repo.
    assert sorted([u.name for u in dest.search_content()]) == ["bash"]

    # Try again with the requires sig flag as true.
    assert client.copy_content(src, dest, options=copy_sig).result()

    # That shouldn't make any difference since the fake always uses
    # true as the default anyway.
    assert sorted([u.name for u in dest.search_content()]) == ["bash"]

    # Try again with the requires sig flag as false.
    assert client.copy_content(src, dest, options=copy_nosig).result()

    # This time we should finally see the unsigned RPM show up as well.
    assert sorted([u.name for u in dest.search_content()]) == ["bash", "ksh"]
def test_copy_content_all(controller):
    """copy_content with no criteria copies all units from a repo"""
    src = YumRepository(id="src-repo")
    dest = YumRepository(id="dest-repo")
    other = YumRepository(id="other-repo")
    controller.insert_repository(src)
    controller.insert_repository(dest)
    controller.insert_repository(other)

    # Set up that both 'src' and 'other' contain some units.
    # The units in 'other' are there to ensure that copying only
    # happens from the given source repo and not other repos unexpectedly.
    src_units = [
        ErratumUnit(id="RHSA-1111:22", summary="Fixes bad things"),
        ModulemdUnit(
            name="module1",
            stream="s1",
            version=1234,
            context="a1b2",
            arch="x86_64",
            repository_memberships=["repoA", "repoB"],
        ),
        RpmUnit(
            name="bash",
            version="4.0",
            release="1",
            arch="x86_64",
            # Note: the next two fields aren't part of the unit key on RPM units.
            # We put these here specifically to verify they'll be filtered out
            # on the copy response (as a real Pulp server does).
            filename="bash-4.0-1.x86_64.rpm",
            signing_key="a1b2c3",
        ),
    ]
    controller.insert_units(src, src_units)
    controller.insert_units(
        other,
        [
            RpmUnit(
                name="glibc",
                version="5.0",
                release="1",
                arch="x86_64",
                sourcerpm="glibc-5.0-1.el5_11.1.src.rpm",
            )
        ],
    )

    client = controller.client

    # Repos are initially detached, re-fetch them via client
    src = client.get_repository(src.id).result()
    dest = client.get_repository(dest.id).result()

    # It should succeed
    copy_tasks = list(client.copy_content(src, dest))

    # Gather all units apparently copied
    units = sum([t.units for t in copy_tasks], [])

    # It should copy just the units we expect, from src.
    # Note that these are incomplete views of the units, as (just like real pulp)
    # the fake will only return fields present in the unit_key after a copy.
    assert sorted(units, key=repr) == [
        ErratumUnit(id="RHSA-1111:22"),
        ModulemdUnit(name="module1",
                     stream="s1",
                     version=1234,
                     context="a1b2",
                     arch="x86_64"),
        RpmUnit(name="bash",
                version="4.0",
                release="1",
                arch="x86_64",
                epoch="0"),
    ]

    # The copy should also impact subsequent content searches.
    dest_units = list(dest.search_content())

    # The units we get from the search are not *precisely* the same as src_units,
    # because repository_memberships has been updated.
    assert sorted(dest_units, key=repr) == [
        ErratumUnit(
            unit_id="e3e70682-c209-4cac-629f-6fbed82c07cd",
            id="RHSA-1111:22",
            summary="Fixes bad things",
            content_type_id="erratum",
            repository_memberships=["src-repo", "dest-repo"],
        ),
        ModulemdUnit(
            unit_id="82e2e662-f728-b4fa-4248-5e3a0a5d2f34",
            name="module1",
            stream="s1",
            version=1234,
            context="a1b2",
            arch="x86_64",
            content_type_id="modulemd",
            repository_memberships=["src-repo", "dest-repo", "repoA", "repoB"],
        ),
        RpmUnit(
            unit_id="d4713d60-c8a7-0639-eb11-67b367a9c378",
            name="bash",
            version="4.0",
            release="1",
            arch="x86_64",
            epoch="0",
            signing_key="a1b2c3",
            filename="bash-4.0-1.x86_64.rpm",
            content_type_id="rpm",
            repository_memberships=["src-repo", "dest-repo"],
        ),
    ]
def test_copy_content_with_criteria(controller):
    """copy_content can filter copied units by field values"""

    src = YumRepository(id="src-repo")
    dest = YumRepository(id="dest-repo")
    controller.insert_repository(src)
    controller.insert_repository(dest)

    src_units = [
        RpmUnit(name="bash", version="4.0", release="1", arch="x86_64"),
        RpmUnit(name="bash", version="4.0", release="2", arch="x86_64"),
        RpmUnit(name="bash", version="4.1", release="3", arch="x86_64"),
        RpmUnit(name="glibc", version="5.0", release="1", arch="x86_64"),
    ]
    controller.insert_units(src, src_units)

    client = controller.client

    # Repos are initially detached, re-fetch them via client
    src = client.get_repository(src.id).result()
    dest = client.get_repository(dest.id).result()

    # This is what we want to copy...
    crit = Criteria.and_(
        Criteria.with_field("name", "bash"),
        Criteria.with_field("release", Matcher.in_(["1", "3"])),
    )

    # Copy should succeed
    copy_tasks = list(
        client.copy_content(src,
                            dest,
                            crit,
                            options=CopyOptions(require_signed_rpms=False)))

    # It should have copied only those units matching the criteria
    units = sum([t.units for t in copy_tasks], [])
    assert sorted(units, key=repr) == [
        RpmUnit(name="bash",
                version="4.0",
                release="1",
                arch="x86_64",
                epoch="0"),
        RpmUnit(name="bash",
                version="4.1",
                release="3",
                arch="x86_64",
                epoch="0"),
    ]

    # The copy should also impact subsequent content searches.
    dest_units = list(dest.search_content())
    assert sorted(dest_units, key=repr) == [
        RpmUnit(
            unit_id="e3e70682-c209-4cac-629f-6fbed82c07cd",
            name="bash",
            version="4.0",
            release="1",
            arch="x86_64",
            epoch="0",
            repository_memberships=["src-repo", "dest-repo"],
        ),
        RpmUnit(
            unit_id="d4713d60-c8a7-0639-eb11-67b367a9c378",
            name="bash",
            version="4.1",
            release="3",
            arch="x86_64",
            epoch="0",
            repository_memberships=["src-repo", "dest-repo"],
        ),
    ]
def test_delete_modules(command_tester, fake_collector, monkeypatch):
    """Deleting modules and it's artifacts from repos succeeds"""

    repo = YumRepository(
        id="some-yumrepo", relative_url="some/publish/url", mutable_urls=["repomd.xml"]
    )

    files = [
        RpmUnit(
            name="bash",
            version="1.23",
            release="1.test8",
            arch="x86_64",
            filename="bash-1.23-1.test8_x86_64.rpm",
            sha256sum="a" * 64,
            md5sum="b" * 32,
            signing_key="aabbcc",
            provides=[],
            requires=[],
            unit_id="rpm1",
        ),
        RpmUnit(
            name="dash",
            version="1.23",
            release="1.test8",
            arch="x86_64",
            filename="dash-1.23-1.test8_x86_64.rpm",
            sha256sum="a" * 64,
            md5sum="b" * 32,
            signing_key="aabbcc",
            provides=[],
            requires=[],
            unit_id="rpm2",
        ),
        ModulemdUnit(
            name="mymod",
            stream="s1",
            version=123,
            context="a1c2",
            arch="s390x",
            artifacts=["bash-0:1.23-1.test8_x86_64", "dash-0:1.23-1.test8_x86_64"],
            unit_id="module1",
        ),
    ]

    with FakeDeletePackages() as task_instance:

        task_instance.pulp_client_controller.insert_repository(repo)
        task_instance.pulp_client_controller.insert_units(repo, files)

        # Let's try setting the cache flush root via env.
        monkeypatch.setenv("FASTPURGE_ROOT_URL", "https://cdn.example2.com/")

        # It should run with expected output.
        command_tester.test(
            task_instance.main,
            [
                "test-delete",
                "--pulp-url",
                "https://pulp.example.com/",
                "--fastpurge-host",
                "fakehost-xxx.example.net",
                "--fastpurge-client-secret",
                "abcdef",
                "--fastpurge-client-token",
                "efg",
                "--fastpurge-access-token",
                "tok",
                "--repo",
                "some-yumrepo",
                "--file",
                "mymod:s1:123:a1c2:s390x",
                "--signing-key",
                "aabbcc",
            ],
        )

        assert sorted(fake_collector.items, key=lambda pi: pi["filename"]) == [
            {
                "origin": "pulp",
                "src": None,
                "state": "DELETED",
                "build": None,
                "dest": "some-yumrepo",
                "checksums": {"sha256": "a" * 64},
                "signing_key": None,
                "filename": "bash-1.23-1.test8.x86_64.rpm",
            },
            {
                "origin": "pulp",
                "src": None,
                "state": "DELETED",
                "build": None,
                "dest": "some-yumrepo",
                "checksums": {"sha256": "a" * 64},
                "signing_key": None,
                "filename": "dash-1.23-1.test8.x86_64.rpm",
            },
            {
                "origin": "pulp",
                "src": None,
                "state": "DELETED",
                "build": None,
                "dest": "some-yumrepo",
                "checksums": None,
                "signing_key": None,
                "filename": "mymod:s1:123:a1c2:s390x",
            },
        ]

        # verify whether files were deleted on Pulp
        client = task_instance.pulp_client

        # get the repo where the files were deleted
        repos = list(
            client.search_repository(Criteria.with_id("some-yumrepo")).result()
        )
        assert len(repos) == 1
        repo = repos[0]

        # criteria with the unit_ids
        unit_ids = []
        for f in files:
            unit_ids.append(f.unit_id)
        criteria = Criteria.with_field("unit_id", Matcher.in_(unit_ids))

        # deleted files are not in the repo
        files = list(repo.search_content(criteria).result())
        assert len(files) == 0

        # same files exist on Pulp as orphans
        files_search = list(client.search_content(criteria).result())
        assert len(files_search) == 3
def test_delete_unsigned_rpms(command_tester, fake_collector, monkeypatch):
    """Deleting unsigned RPMs from repos succeeds"""

    repo = YumRepository(
        id="some-yumrepo", relative_url="some/publish/url", mutable_urls=["repomd.xml"]
    )

    files = [
        RpmUnit(
            name="signed",
            version="1.23",
            release="1.test8",
            arch="x86_64",
            filename="signed-1.23-1.test8_x86_64.rpm",
            sha256sum="a" * 64,
            md5sum="b" * 32,
            signing_key="aabbcc",
            unit_id="signed_rpm",
        ),
        RpmUnit(
            name="unsigned",
            version="2.25",
            release="1.test8",
            arch="x86_64",
            filename="unsigned-2.25-1.test8_x86_64.rpm",
            sha256sum="a" * 64,
            md5sum="b" * 32,
            signing_key=None,
            unit_id="unsigned_rpm",
        ),
    ]

    with FakeDeletePackages() as task_instance:

        task_instance.pulp_client_controller.insert_repository(repo)
        task_instance.pulp_client_controller.insert_units(repo, files)

        # Let's try setting the cache flush root via env.
        monkeypatch.setenv("FASTPURGE_ROOT_URL", "https://cdn.example2.com/")

        # It should run with expected output.
        command_tester.test(
            task_instance.main,
            [
                "test-delete",
                "--pulp-url",
                "https://pulp.example.com/",
                "--fastpurge-host",
                "fakehost-xxx.example.net",
                "--fastpurge-client-secret",
                "abcdef",
                "--fastpurge-client-token",
                "efg",
                "--fastpurge-access-token",
                "tok",
                "--repo",
                "some-yumrepo",
                "--file",
                "unsigned-2.25-1.test8_x86_64.rpm,signed-1.23-1.test8_x86_64.rpm",
                "--allow-unsigned",
            ],
        )

        # It should record that it removed these push items:
        assert sorted(fake_collector.items, key=lambda pi: pi["filename"]) == [
            {
                "origin": "pulp",
                "src": None,
                "dest": "some-yumrepo",
                "signing_key": None,
                "filename": "unsigned-2.25-1.test8.x86_64.rpm",
                "state": "DELETED",
                "build": None,
                "checksums": {"sha256": "a" * 64},
            }
        ]

        # verify whether files were deleted on Pulp
        client = task_instance.pulp_client

        # get the repo where the files were deleted
        repos = list(
            client.search_repository(Criteria.with_id("some-yumrepo")).result()
        )
        assert len(repos) == 1
        repo = repos[0]

        # criteria with the unit_ids
        unit_ids = []
        for f in files:
            unit_ids.append(f.unit_id)
        criteria = Criteria.with_field("unit_id", Matcher.in_(unit_ids))

        # unsigned RPM is deleted, only signed RPM left in the repo
        result_files = list(repo.search_content(criteria).result())
        assert len(result_files) == 1
        assert files[0].filename == "signed-1.23-1.test8_x86_64.rpm"
Пример #6
0
def test_delete_advisory_no_repos_provided(command_tester, fake_collector,
                                           monkeypatch):
    """Deletion of packages succeeds in all the repos when the same advisory is
    present in multiple repos and repos are not provided in the request"""

    repo1 = YumRepository(id="some-yumrepo",
                          relative_url="some/publish/url",
                          mutable_urls=["repomd.xml"])
    repo2 = YumRepository(
        id="other-yumrepo",
        relative_url="other/publish/url",
        mutable_urls=["repomd.xml"],
    )

    pkglist = [
        ErratumPackageCollection(
            name="collection-1",
            packages=[
                ErratumPackage(
                    name="bash",
                    version="1.23",
                    release="1.test8",
                    arch="x86_64",
                    filename="bash-1.23-1.test8_x86_64.rpm",
                    sha256sum="a" * 64,
                    md5sum="b" * 32,
                ),
                ErratumPackage(
                    name="dash",
                    version="1.23",
                    release="1.test8",
                    arch="x86_64",
                    filename="dash-1.23-1.test8_x86_64.rpm",
                    sha256sum="a" * 64,
                    md5sum="b" * 32,
                ),
            ],
            short="",
            module=None,
        ),
    ]

    files = [
        RpmUnit(
            name="bash",
            version="1.23",
            release="1.test8",
            arch="x86_64",
            filename="bash-1.23-1.test8_x86_64.rpm",
            sha256sum="a" * 64,
            md5sum="b" * 32,
            signing_key="aabbcc",
            unit_id="files1_rpm1",
        ),
        RpmUnit(
            name="dash",
            version="1.23",
            release="1.test8",
            arch="x86_64",
            filename="dash-1.23-1.test8_x86_64.rpm",
            sha256sum="a" * 64,
            md5sum="b" * 32,
            signing_key="aabbcc",
            unit_id="files1_rpm2",
        ),
        RpmUnit(
            name="crash",
            version="1.23",
            release="1.test8",
            arch="x86_64",
            filename=
            "crash-1.23-1.test8.module+el8.0.0+3049+59fd2bba.x86_64.rpm",
            sha256sum="a" * 64,
            md5sum="b" * 32,
            signing_key="aabbcc",
            unit_id="files1_rpm3",
        ),
        ErratumUnit(
            unit_id="x4e73262-e239-44ac-629f-6fbed82c07cd",
            id="RHBA-1001:22",
            summary="Other erratum",
            content_type_id="erratum",
            repository_memberships=["some-yumrepo", "other-yumrepo"],
            pkglist=pkglist,
        ),
    ]

    with FakeDeleteAdvisory() as task_instance:

        task_instance.pulp_client_controller.insert_repository(repo1)
        task_instance.pulp_client_controller.insert_repository(repo2)
        task_instance.pulp_client_controller.insert_units(repo1, files)
        task_instance.pulp_client_controller.insert_units(repo2, files)

        # Let's try setting the cache flush root via env.
        monkeypatch.setenv("FASTPURGE_ROOT_URL", "https://cdn.example2.com/")

        # It should run with expected output.
        command_tester.test(
            task_instance.main,
            [
                "test-delete",
                "--pulp-url",
                "https://pulp.example.com/",
                "--fastpurge-host",
                "fakehost-xxx.example.net",
                "--fastpurge-client-secret",
                "abcdef",
                "--fastpurge-client-token",
                "efg",
                "--fastpurge-access-token",
                "tok",
                "--advisory",
                "RHBA-1001:22",
            ],
        )

        assert sorted(fake_collector.items,
                      key=lambda pi: (pi["filename"], pi["dest"])) == [
                          {
                              "build": None,
                              "checksums": {
                                  "sha256": "a" * 64
                              },
                              "dest": "other-yumrepo",
                              "filename": "bash-1.23-1.test8.x86_64.rpm",
                              "origin": "pulp",
                              "signing_key": None,
                              "src": None,
                              "state": "DELETED",
                          },
                          {
                              "build": None,
                              "checksums": {
                                  "sha256": "a" * 64
                              },
                              "dest": "some-yumrepo",
                              "filename": "bash-1.23-1.test8.x86_64.rpm",
                              "origin": "pulp",
                              "signing_key": None,
                              "src": None,
                              "state": "DELETED",
                          },
                          {
                              "build": None,
                              "checksums": {
                                  "sha256": "a" * 64
                              },
                              "dest": "other-yumrepo",
                              "filename": "dash-1.23-1.test8.x86_64.rpm",
                              "origin": "pulp",
                              "signing_key": None,
                              "src": None,
                              "state": "DELETED",
                          },
                          {
                              "build": None,
                              "checksums": {
                                  "sha256": "a" * 64
                              },
                              "dest": "some-yumrepo",
                              "filename": "dash-1.23-1.test8.x86_64.rpm",
                              "origin": "pulp",
                              "signing_key": None,
                              "src": None,
                              "state": "DELETED",
                          },
                      ]

        # verify whether the rpms were deleted from the repo on Pulp
        client = task_instance.pulp_client

        # get all the repos
        repos = list(
            client.search_repository(
                Criteria.with_id("some-yumrepo")).result())
        assert len(repos) == 1
        repo1 = repos[0]

        repos = list(
            client.search_repository(
                Criteria.with_id("other-yumrepo")).result())
        assert len(repos) == 1
        repo2 = repos[0]

        # list the removed unit's unit_id
        # RPMs from the erratum package list
        unit_ids = ["files1_rpm1", "files1_rpm2"]
        criteria = Criteria.with_field("unit_id", Matcher.in_(unit_ids))

        # deleted packages from the advisory are not in both the repos
        files = list(repo1.search_content(criteria).result())
        assert len(files) == 0

        files = list(repo2.search_content(criteria).result())
        assert len(files) == 0

        # same files exist on Pulp as orphans
        files_search = list(client.search_content(criteria).result())
        assert len(files_search) == 2