Skip to content

Commit

Permalink
tests: move FakeApt fixtures into deb tests (canonical#3025)
Browse files Browse the repository at this point in the history
These are no longer shared for other tests so we can freely
modify without breaking external tests.  We'll move them
into test_deb to discourage further external use.

Signed-off-by: Chris Patterson <chris.patterson@canonical.com>
  • Loading branch information
Chris Patterson committed Apr 10, 2020
1 parent ab892ee commit 1237aa6
Show file tree
Hide file tree
Showing 3 changed files with 198 additions and 202 deletions.
3 changes: 0 additions & 3 deletions tests/fixture_setup/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,6 @@
from ._unix import FakeSnapd # noqa: F401
try:
from ._unittests import ( # noqa: F401
FakeAptBaseDependency,
FakeAptCache,
FakeAptCachePackage,
FakeElf,
FakeExtension,
FakeMetadataExtractor,
Expand Down
190 changes: 0 additions & 190 deletions tests/fixture_setup/_unittests.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.

import collections
import os
import pkgutil
import shutil
Expand All @@ -30,7 +29,6 @@

import snapcraft
from snapcraft.internal import elf
from snapcraft.internal.repo import _deb
from snapcraft.plugins._plugin_finder import get_plugin_for_base
from tests.file_utils import get_snapcraft_path

Expand Down Expand Up @@ -443,194 +441,6 @@ def _fake_snap_command(self, cmd, *args, **kwargs):
return "Downloaded ".encode()


class FakeAptCache(fixtures.Fixture):
class Cache:
def __init__(self):
super().__init__()
self.packages = collections.OrderedDict()

def __enter__(self):
return self

def __exit__(self, *args):
pass

def __setitem__(self, key, item):
package_parts = key.split("=")
package_name = package_parts[0]
version = package_parts[1] if len(package_parts) > 1 else item.version
if package_name in self.packages:
self.packages[package_name].version = version
else:
if version and not item.version:
item.version = version
self.packages[package_name] = item

def __getitem__(self, key):
if "=" in key:
key = key.split("=")[0]
return self.packages[key]

def __contains__(self, key):
return key in self.packages

def __iter__(self):
return iter(self.packages.values())

def open(self):
pass

def close(self):
pass

def update(self, *args, **kwargs):
pass

def get_changes(self):
return [
self.packages[package]
for package in self.packages
if self.packages[package].marked_install
]

def get_providing_packages(self, package_name):
providing_packages = []
for package in self.packages:
if package_name in self.packages[package].provides:
providing_packages.append(self.packages[package])
return providing_packages

def is_virtual_package(self, package_name):
is_virtual = False
if package_name not in self.packages:
for package in self.packages:
if package_name in self.packages[package].provides:
return True
return is_virtual

def __init__(self, packages=None):
super().__init__()
self.packages = packages if packages else []

def setUp(self):
super().setUp()
temp_dir_fixture = fixtures.TempDir()
self.useFixture(temp_dir_fixture)
self.path = temp_dir_fixture.path
patcher = mock.patch("snapcraft.repo._deb.apt.Cache")
self.mock_apt_cache = patcher.start()
self.addCleanup(patcher.stop)

self.cache = self.Cache()
self.mock_apt_cache.return_value = self.cache
for package, version in self.packages:
self.add_package(FakeAptCachePackage(package, version))

# Add all the packages in the manifest.
self.add_packages(_deb._DEFAULT_FILTERED_STAGE_PACKAGES)

def add_package(self, package):
package.temp_dir = self.path
self.cache[package.name] = package

def add_packages(self, package_names):
for name in package_names:
self.cache[name] = FakeAptCachePackage(name)


class FakeAptCachePackage:
def __init__(
self,
name,
version=None,
installed=None,
temp_dir=None,
provides=None,
priority="non-essential",
):
super().__init__()
self.temp_dir = temp_dir
self.name = name
self._version = None
self.versions = {}
self.version = version
self.candidate = self
self.dependencies = []
self.conflicts = []
self.provides = provides if provides else []
if installed:
# XXX The installed attribute requires some values that the fake
# package also requires. The shortest path to do it that I found
# was to get installed to return the same fake package.
self.installed = self
else:
self.installed = None
self.priority = priority
self.marked_install = False
self.is_auto_installed = False

def __str__(self):
if "=" in self.name:
return self.name
else:
return "{}={}".format(self.name, self.version)

@property
def is_auto_removable(self):
return self.marked_install and self.is_auto_installed

@property
def version(self):
return self._version

@version.setter
def version(self, version):
self._version = version
if version is not None:
self.versions.update({version: self})

def fetch_binary(self, cache_dir):
path = os.path.join(cache_dir, f"{self.name}.deb")
open(path, "w").close()
return path

def mark_install(self, *, auto_fix=True, from_user=True):
if not self.installed:
# First, verify dependencies are valid. If not, bail.
for or_set in self.dependencies:
for dep in or_set:
if "broken" in dep.name:
return

for or_set in self.dependencies:
if or_set and or_set[0].target_versions:
# Install the first target version of the first OR
or_set[0].target_versions[0].mark_install(
auto_fix=auto_fix, from_user=from_user
)
for conflict in self.conflicts:
conflict.mark_keep()

self.marked_install = True
self.is_auto_installed = not from_user

def mark_auto(self, auto=True):
self.is_auto_installed = auto

def mark_keep(self):
self.marked_install = False
self.is_auto_installed = False

def get_dependencies(self, _):
return []


class FakeAptBaseDependency:
def __init__(self, name, target_versions):
self.name = name
self.target_versions = target_versions


class FakeSnapcraftctl(fixtures.Fixture):
def _setUp(self):
super()._setUp()
Expand Down
Loading

0 comments on commit 1237aa6

Please sign in to comment.