diff --git a/pkgmeta/repository.py b/pkgmeta/repository.py index dad6445..76d1bbd 100644 --- a/pkgmeta/repository.py +++ b/pkgmeta/repository.py @@ -1,6 +1,6 @@ # -*- coding: utf-8 -*- import os -from collections import Mapping +from collections import MutableMapping from pkgmeta.exceptions import ReleaseNotFound from pkgmeta.config import RepositoryConfig @@ -10,14 +10,14 @@ __all__ = ('Repository',) -class Repository(Mapping): +class Repository(MutableMapping): """A repository of Python distribution metadata. The structure is organized by package name then by release (version).""" def __init__(self, config): if not isinstance(config, RepositoryConfig): raise TypeError("Expected a " - "pkgmeta.config.RepositoryConfig object.") + ", pkgmeta.config.RepositoryConfig object.") self.config = config self.storage = self.config.storage # For convenience @@ -37,6 +37,16 @@ def __iter__(self): def __len__(self): return len(self.storage) + def __setitem__(self, key, value): + if not isinstance(value, ReleaseSet): + raise TypeError("Expected a pkgmeta.releases.ReleaseSet, " + "received '%s'" % type(value)) + self.storage[key] = value + + def __delitem__(self, key): + raise Exception("Can't remove items from a read-only repository") + + # ############## # # Public API # # ############## # diff --git a/pkgmeta/tests/test_repository.py b/pkgmeta/tests/test_repository.py index 6e0fdd0..be40ec5 100644 --- a/pkgmeta/tests/test_repository.py +++ b/pkgmeta/tests/test_repository.py @@ -3,7 +3,7 @@ from pkgmeta.tests import unittest from pkgmeta.tests.base import BaseTestCase from pkgmeta.tests.mock_metadata import ALL_DISTS, SOLARCAL -from pkgmeta.tests.utils import populate_repo +from pkgmeta.tests.utils import make_metadata, populate_repo class RepositoryTestCase(BaseTestCase): @@ -31,7 +31,8 @@ def make_one(self, location=None): location = self.repo_directory from pkgmeta.config import RepositoryConfig from pkgmeta.storage import FS_STORAGE_TYPE - config = RepositoryConfig('', type=FS_STORAGE_TYPE, location=location) + config = RepositoryConfig('repo', type=FS_STORAGE_TYPE, + location=location) return self.target_cls(config) def test_init_without_config(self): @@ -78,3 +79,44 @@ def test_iteration(self): def test_len(self): repo = self.make_one() self.assertEqual(len(repo), len(ALL_DISTS)) + + +class RepositoryMutationTestCase(unittest.TestCase): + """Test for the mutation of a repository. Specifically checking for + addition and deletion.""" + + @property + def target_cls(self): + from pkgmeta.repository import Repository + return Repository + + def make_releaseset(self, common, versions, extras={}): + from pkgmeta.metadata import Metadata + from pkgmeta.releases import ReleaseSet + return ReleaseSet(make_metadata(common, versions, extras, cls=Metadata)) + + def make_one(self): + from pkgmeta.config import RepositoryConfig + from pkgmeta.storage import RUNTIME_STORAGE_TYPE + config = RepositoryConfig('repo') + return self.target_cls(config) + + def test_setting_releaseset(self): + repo = self.make_one() + #: Make sure the repo is empty to start + self.assertEqual(len(repo), 0) + #: Set a releaseset + release = self.make_releaseset(*SOLARCAL) + repo[release.name] = release + self.assertEqual(len(repo), 1) + self.assertIn(SOLARCAL[0]['name'], repo) + + def test_setting_with_invalid_type(self): + repo = self.make_one() + #: Make sure the repo is empty to start + self.assertEqual(len(repo), 0) + #: Set a releaseset + release = self.make_releaseset(*SOLARCAL) + repo[release.name] = release + self.assertEqual(len(repo), 1) + self.assertIn(SOLARCAL[0]['name'], repo)