sync with Debian
This commit is contained in:
10
debian/lib/python/debian_linux/config_v2.py
vendored
10
debian/lib/python/debian_linux/config_v2.py
vendored
@@ -11,7 +11,6 @@ from pathlib import Path
|
||||
from typing import (
|
||||
Optional,
|
||||
Self,
|
||||
TypeVar,
|
||||
)
|
||||
|
||||
import dacite
|
||||
@@ -157,9 +156,6 @@ class ConfigBase:
|
||||
return config
|
||||
|
||||
|
||||
ConfigT = TypeVar('ConfigT', bound=ConfigBase)
|
||||
|
||||
|
||||
@dataclasses.dataclass
|
||||
class Config(ConfigBase):
|
||||
# Disable basic fields
|
||||
@@ -227,9 +223,9 @@ class Config(ConfigBase):
|
||||
return config
|
||||
|
||||
@classmethod
|
||||
def _read_hierarchy(
|
||||
cls, bases: Iterable[Path], orig: Iterable[ConfigT],
|
||||
) -> Iterable[ConfigT]:
|
||||
def _read_hierarchy[T: ConfigBase](
|
||||
cls, bases: Iterable[Path], orig: Iterable[T],
|
||||
) -> Iterable[T]:
|
||||
for i in orig:
|
||||
try:
|
||||
assert i.path is not None
|
||||
|
@@ -5,22 +5,16 @@ import re
|
||||
from typing import (
|
||||
Any,
|
||||
Callable,
|
||||
Generic,
|
||||
IO,
|
||||
Iterable,
|
||||
Optional,
|
||||
overload,
|
||||
TypeVar,
|
||||
TYPE_CHECKING,
|
||||
)
|
||||
|
||||
_T = TypeVar('_T')
|
||||
|
||||
if TYPE_CHECKING:
|
||||
from dataclasses import _DataclassT
|
||||
else:
|
||||
# We can only get to _DataclassT during type checking, use a generic type during runtime
|
||||
_DataclassT = _T
|
||||
from _typeshed import DataclassInstance as _DataclassInstance
|
||||
|
||||
|
||||
__all__ = [
|
||||
'field_deb822',
|
||||
@@ -30,61 +24,61 @@ __all__ = [
|
||||
]
|
||||
|
||||
|
||||
class Deb822Field(Generic[_T]):
|
||||
class Deb822Field[T]:
|
||||
key: str
|
||||
load: Optional[Callable[[str], _T]]
|
||||
dump: Optional[Callable[[_T], str]]
|
||||
load: Optional[Callable[[str], T]]
|
||||
dump: Optional[Callable[[T], str]]
|
||||
|
||||
def __init__(
|
||||
self, *,
|
||||
key: str,
|
||||
load: Optional[Callable[[str], _T]],
|
||||
dump: Optional[Callable[[_T], str]],
|
||||
load: Optional[Callable[[str], T]],
|
||||
dump: Optional[Callable[[T], str]],
|
||||
) -> None:
|
||||
self.key = key
|
||||
self.load = load
|
||||
self.dump = dump
|
||||
|
||||
|
||||
# The return type _T is technically wrong, but it allows checking if during
|
||||
# The return type T is technically wrong, but it allows checking if during
|
||||
# runtime we get the correct type.
|
||||
@overload
|
||||
def field_deb822(
|
||||
def field_deb822[T](
|
||||
deb822_key: str,
|
||||
/, *,
|
||||
deb822_load: Optional[Callable[[str], _T]] = None,
|
||||
deb822_dump: Optional[Callable[[_T], str]] = str,
|
||||
default: _T,
|
||||
) -> _T:
|
||||
deb822_load: Optional[Callable[[str], T]] = None,
|
||||
deb822_dump: Optional[Callable[[T], str]] = str,
|
||||
default: T,
|
||||
) -> T:
|
||||
...
|
||||
|
||||
|
||||
@overload
|
||||
def field_deb822(
|
||||
def field_deb822[T](
|
||||
deb822_key: str,
|
||||
/, *,
|
||||
deb822_load: Optional[Callable[[str], _T]] = None,
|
||||
deb822_dump: Optional[Callable[[_T], str]] = str,
|
||||
default_factory: Callable[[], _T],
|
||||
) -> _T:
|
||||
deb822_load: Optional[Callable[[str], T]] = None,
|
||||
deb822_dump: Optional[Callable[[T], str]] = str,
|
||||
default_factory: Callable[[], T],
|
||||
) -> T:
|
||||
...
|
||||
|
||||
|
||||
@overload
|
||||
def field_deb822(
|
||||
def field_deb822[T](
|
||||
deb822_key: str,
|
||||
/, *,
|
||||
deb822_load: Optional[Callable[[str], _T]] = None,
|
||||
deb822_dump: Optional[Callable[[_T], str]] = str,
|
||||
) -> _T:
|
||||
deb822_load: Optional[Callable[[str], T]] = None,
|
||||
deb822_dump: Optional[Callable[[T], str]] = str,
|
||||
) -> T:
|
||||
...
|
||||
|
||||
|
||||
def field_deb822(
|
||||
def field_deb822[T](
|
||||
deb822_key: str,
|
||||
/, *,
|
||||
deb822_load: Optional[Callable[[str], _T]] = None,
|
||||
deb822_dump: Optional[Callable[[_T], str]] = str,
|
||||
deb822_load: Optional[Callable[[str], T]] = None,
|
||||
deb822_dump: Optional[Callable[[T], str]] = str,
|
||||
default: Any = dataclasses.MISSING,
|
||||
default_factory: Any = dataclasses.MISSING,
|
||||
) -> Any:
|
||||
@@ -112,8 +106,8 @@ class Deb822DecodeError(ValueError):
|
||||
pass
|
||||
|
||||
|
||||
class Deb822DecodeState(Generic[_DataclassT]):
|
||||
cls: type[_DataclassT]
|
||||
class Deb822DecodeState[T: _DataclassInstance]:
|
||||
cls: type[T]
|
||||
fields: dict[str, dataclasses.Field]
|
||||
ignore_unknown: bool
|
||||
|
||||
@@ -132,7 +126,7 @@ class Deb822DecodeState(Generic[_DataclassT]):
|
||||
|
||||
def __init__(
|
||||
self,
|
||||
cls: type[_DataclassT],
|
||||
cls: type[T],
|
||||
ignore_unknown: bool,
|
||||
) -> None:
|
||||
self.reset()
|
||||
@@ -167,7 +161,7 @@ class Deb822DecodeState(Generic[_DataclassT]):
|
||||
else:
|
||||
raise NotImplementedError
|
||||
|
||||
def generate(self) -> _DataclassT | None:
|
||||
def generate(self) -> T | None:
|
||||
if not self.data:
|
||||
return None
|
||||
|
||||
@@ -192,12 +186,12 @@ class Deb822DecodeState(Generic[_DataclassT]):
|
||||
return self.cls(**r)
|
||||
|
||||
|
||||
def read_deb822(
|
||||
cls: type[_DataclassT],
|
||||
def read_deb822[T: _DataclassInstance](
|
||||
cls: type[T],
|
||||
file: IO[str],
|
||||
/,
|
||||
ignore_unknown: bool = False,
|
||||
) -> Iterable[_DataclassT]:
|
||||
) -> Iterable[T]:
|
||||
state = Deb822DecodeState(cls, ignore_unknown)
|
||||
|
||||
for linenr, line in enumerate(file):
|
||||
@@ -217,8 +211,8 @@ def read_deb822(
|
||||
yield obj
|
||||
|
||||
|
||||
def write_deb822(
|
||||
objs: Iterable[_DataclassT],
|
||||
def write_deb822[T: _DataclassInstance](
|
||||
objs: Iterable[T],
|
||||
file: IO[str],
|
||||
/,
|
||||
) -> None:
|
||||
|
@@ -7,7 +7,6 @@ from dataclasses import (
|
||||
)
|
||||
from typing import (
|
||||
Protocol,
|
||||
TypeVar,
|
||||
TYPE_CHECKING,
|
||||
)
|
||||
|
||||
@@ -17,14 +16,11 @@ if TYPE_CHECKING:
|
||||
class _HasName(Protocol, _DataclassInstance):
|
||||
name: str
|
||||
|
||||
_DataclassT = TypeVar('_DataclassT', bound=_DataclassInstance)
|
||||
_HasNameT = TypeVar('_HasNameT', bound=_HasName)
|
||||
|
||||
|
||||
def default(
|
||||
cls: type[_DataclassT],
|
||||
def default[T: _DataclassInstance](
|
||||
cls: type[T],
|
||||
/,
|
||||
) -> _DataclassT:
|
||||
) -> T:
|
||||
f = {}
|
||||
|
||||
for field in fields(cls):
|
||||
@@ -34,10 +30,10 @@ def default(
|
||||
return cls(**f)
|
||||
|
||||
|
||||
def merge(
|
||||
self: _DataclassT,
|
||||
other: _DataclassT | None, /,
|
||||
) -> _DataclassT:
|
||||
def merge[T: _DataclassInstance](
|
||||
self: T,
|
||||
other: T | None, /,
|
||||
) -> T:
|
||||
if other is None:
|
||||
return self
|
||||
|
||||
@@ -75,22 +71,22 @@ def merge(
|
||||
return replace(self, **f)
|
||||
|
||||
|
||||
def merge_default(
|
||||
cls: type[_DataclassT],
|
||||
def merge_default[T: _DataclassInstance](
|
||||
cls: type[T],
|
||||
/,
|
||||
*others: _DataclassT,
|
||||
) -> _DataclassT:
|
||||
ret: _DataclassT = default(cls)
|
||||
*others: T,
|
||||
) -> T:
|
||||
ret: T = default(cls)
|
||||
for o in others:
|
||||
ret = merge(ret, o)
|
||||
return ret
|
||||
|
||||
|
||||
def _merge_assoclist(
|
||||
self_list: list[_HasNameT],
|
||||
other_list: list[_HasNameT],
|
||||
def _merge_assoclist[T: _HasName](
|
||||
self_list: list[T],
|
||||
other_list: list[T],
|
||||
/,
|
||||
) -> list[_HasNameT]:
|
||||
) -> list[T]:
|
||||
'''
|
||||
Merge lists where each item got a "name" attribute
|
||||
'''
|
||||
@@ -99,7 +95,7 @@ def _merge_assoclist(
|
||||
if not other_list:
|
||||
return self_list
|
||||
|
||||
ret: list[_HasNameT] = []
|
||||
ret: list[T] = []
|
||||
other_dict = {
|
||||
i.name: i
|
||||
for i in other_list
|
||||
|
25
debian/lib/python/debian_linux/debian.py
vendored
25
debian/lib/python/debian_linux/debian.py
vendored
@@ -370,9 +370,8 @@ class PackageRelationEntry:
|
||||
ret.append(f'({self.operator} {self.version})')
|
||||
if self.arches:
|
||||
ret.append(f'[{self.arches}]')
|
||||
if self.restrictions:
|
||||
ret.append(str(self.restrictions))
|
||||
return ' '.join(ret)
|
||||
ret.append(str(self.restrictions))
|
||||
return ' '.join(i for i in ret if i)
|
||||
|
||||
|
||||
class PackageRelationGroup(list[PackageRelationEntry]):
|
||||
@@ -443,8 +442,6 @@ class PackageBuildprofileEntry:
|
||||
pos: set[str] = dataclasses.field(default_factory=set)
|
||||
neg: set[str] = dataclasses.field(default_factory=set)
|
||||
|
||||
__re = re.compile(r'^<(?P<profiles>[a-z0-9. !-]+)>$')
|
||||
|
||||
def copy(self) -> Self:
|
||||
return self.__class__(
|
||||
pos=set(self.pos),
|
||||
@@ -453,12 +450,8 @@ class PackageBuildprofileEntry:
|
||||
|
||||
@classmethod
|
||||
def parse(cls, v: str, /) -> Self:
|
||||
match = cls.__re.match(v)
|
||||
if not match:
|
||||
raise RuntimeError('Unable to parse build profile "%s"' % v)
|
||||
|
||||
ret = cls()
|
||||
for i in re.split(r' ', match.group('profiles')):
|
||||
for i in re.split(r' ', v):
|
||||
if i:
|
||||
if i[0] == '!':
|
||||
ret.neg.add(i[1:])
|
||||
@@ -506,16 +499,18 @@ class PackageBuildprofileEntry:
|
||||
self.neg &= other.neg - diff
|
||||
__ior__ = update
|
||||
|
||||
def __len__(self) -> int:
|
||||
return len(self.pos) + len(self.neg)
|
||||
|
||||
def __str__(self) -> str:
|
||||
s = ' '.join(itertools.chain(
|
||||
return ' '.join(itertools.chain(
|
||||
sorted(self.pos),
|
||||
(f'!{i}' for i in sorted(self.neg)),
|
||||
))
|
||||
return f'<{s}>'
|
||||
|
||||
|
||||
class PackageBuildprofile(list[PackageBuildprofileEntry]):
|
||||
__re = re.compile(r' *(<[^>]+>)(?: +|$)')
|
||||
__re = re.compile(r' *<(?P<entry>[a-z0-9. !-]+)>(?: +|$)')
|
||||
|
||||
def copy(self) -> Self:
|
||||
return self.__class__(i.copy() for i in self)
|
||||
@@ -524,7 +519,7 @@ class PackageBuildprofile(list[PackageBuildprofileEntry]):
|
||||
def parse(cls, v: str, /) -> Self:
|
||||
ret = cls()
|
||||
for match in cls.__re.finditer(v):
|
||||
ret.append(PackageBuildprofileEntry.parse(match.group(1)))
|
||||
ret.append(PackageBuildprofileEntry.parse(match.group('entry')))
|
||||
return ret
|
||||
|
||||
def update(self, v: Self, /) -> None:
|
||||
@@ -538,7 +533,7 @@ class PackageBuildprofile(list[PackageBuildprofileEntry]):
|
||||
__ior__ = update
|
||||
|
||||
def __str__(self) -> str:
|
||||
return ' '.join(str(i) for i in self)
|
||||
return ' '.join(f'<{str(i)}>' for i in self if i)
|
||||
|
||||
|
||||
@dataclasses.dataclass
|
||||
|
7
debian/lib/python/debian_linux/gencontrol.py
vendored
7
debian/lib/python/debian_linux/gencontrol.py
vendored
@@ -189,6 +189,7 @@ class PackagesBundle:
|
||||
package.meta_rules_check_packages = check_packages
|
||||
|
||||
for name in (
|
||||
'NEWS',
|
||||
'lintian-overrides',
|
||||
'maintscript',
|
||||
'postinst',
|
||||
@@ -202,7 +203,11 @@ class PackagesBundle:
|
||||
except KeyError:
|
||||
pass
|
||||
else:
|
||||
with self.open(f'{package_name}.{name}') as f:
|
||||
if arch:
|
||||
out = f'{package_name}.{name}.{arch}'
|
||||
else:
|
||||
out = f'{package_name}.{name}'
|
||||
with self.open(out) as f:
|
||||
f.write(template)
|
||||
|
||||
return ret
|
||||
|
424
debian/lib/python/debian_linux/test_debian.py
vendored
424
debian/lib/python/debian_linux/test_debian.py
vendored
@@ -1,424 +0,0 @@
|
||||
import pytest
|
||||
|
||||
from .debian import (
|
||||
Version,
|
||||
VersionLinux,
|
||||
PackageArchitecture,
|
||||
PackageDescription,
|
||||
PackageRelationEntry,
|
||||
PackageRelationGroup,
|
||||
PackageRelation,
|
||||
PackageBuildprofileEntry,
|
||||
PackageBuildprofile,
|
||||
)
|
||||
|
||||
|
||||
class TestVersion:
|
||||
def test_native(self) -> None:
|
||||
v = Version('1.2+c~4')
|
||||
assert v.epoch is None
|
||||
assert v.upstream == '1.2+c~4'
|
||||
assert v.revision is None
|
||||
assert v.complete == '1.2+c~4'
|
||||
assert v.complete_noepoch == '1.2+c~4'
|
||||
|
||||
def test_nonnative(self) -> None:
|
||||
v = Version('1-2+d~3')
|
||||
assert v.epoch is None
|
||||
assert v.upstream == '1'
|
||||
assert v.revision == '2+d~3'
|
||||
assert v.complete == '1-2+d~3'
|
||||
assert v.complete_noepoch == '1-2+d~3'
|
||||
|
||||
def test_native_epoch(self) -> None:
|
||||
v = Version('5:1.2.3')
|
||||
assert v.epoch == 5
|
||||
assert v.upstream == '1.2.3'
|
||||
assert v.revision is None
|
||||
assert v.complete == '5:1.2.3'
|
||||
assert v.complete_noepoch == '1.2.3'
|
||||
|
||||
def test_nonnative_epoch(self) -> None:
|
||||
v = Version('5:1.2.3-4')
|
||||
assert v.epoch == 5
|
||||
assert v.upstream == '1.2.3'
|
||||
assert v.revision == '4'
|
||||
assert v.complete == '5:1.2.3-4'
|
||||
assert v.complete_noepoch == '1.2.3-4'
|
||||
|
||||
def test_multi_hyphen(self) -> None:
|
||||
v = Version('1-2-3')
|
||||
assert v.epoch is None
|
||||
assert v.upstream == '1-2'
|
||||
assert v.revision == '3'
|
||||
assert v.complete == '1-2-3'
|
||||
|
||||
def test_multi_colon(self) -> None:
|
||||
v = Version('1:2:3')
|
||||
assert v.epoch == 1
|
||||
assert v.upstream == '2:3'
|
||||
assert v.revision is None
|
||||
|
||||
def test_invalid_epoch(self) -> None:
|
||||
with pytest.raises(RuntimeError):
|
||||
Version('a:1')
|
||||
with pytest.raises(RuntimeError):
|
||||
Version('-1:1')
|
||||
with pytest.raises(RuntimeError):
|
||||
Version('1a:1')
|
||||
|
||||
def test_invalid_upstream(self) -> None:
|
||||
with pytest.raises(RuntimeError):
|
||||
Version('1_2')
|
||||
with pytest.raises(RuntimeError):
|
||||
Version('1/2')
|
||||
with pytest.raises(RuntimeError):
|
||||
Version('a1')
|
||||
with pytest.raises(RuntimeError):
|
||||
Version('1 2')
|
||||
|
||||
def test_invalid_revision(self) -> None:
|
||||
with pytest.raises(RuntimeError):
|
||||
Version('1-2_3')
|
||||
with pytest.raises(RuntimeError):
|
||||
Version('1-2/3')
|
||||
with pytest.raises(RuntimeError):
|
||||
Version('1-2:3')
|
||||
|
||||
|
||||
class TestVersionLinux:
|
||||
def test_stable(self) -> None:
|
||||
v = VersionLinux('1.2.3-4')
|
||||
assert v.linux_version == '1.2'
|
||||
assert v.linux_upstream == '1.2'
|
||||
assert v.linux_upstream_full == '1.2.3'
|
||||
assert v.linux_modifier is None
|
||||
assert v.linux_dfsg is None
|
||||
assert not v.linux_revision_experimental
|
||||
assert not v.linux_revision_security
|
||||
assert not v.linux_revision_backports
|
||||
assert not v.linux_revision_other
|
||||
|
||||
def test_rc(self) -> None:
|
||||
v = VersionLinux('1.2~rc3-4')
|
||||
assert v.linux_version == '1.2'
|
||||
assert v.linux_upstream == '1.2-rc3'
|
||||
assert v.linux_upstream_full == '1.2-rc3'
|
||||
assert v.linux_modifier == 'rc3'
|
||||
assert v.linux_dfsg is None
|
||||
assert not v.linux_revision_experimental
|
||||
assert not v.linux_revision_security
|
||||
assert not v.linux_revision_backports
|
||||
assert not v.linux_revision_other
|
||||
|
||||
def test_dfsg(self) -> None:
|
||||
v = VersionLinux('1.2~rc3.dfsg.1-4')
|
||||
assert v.linux_version == '1.2'
|
||||
assert v.linux_upstream == '1.2-rc3'
|
||||
assert v.linux_upstream_full == '1.2-rc3'
|
||||
assert v.linux_modifier == 'rc3'
|
||||
assert v.linux_dfsg == '1'
|
||||
assert not v.linux_revision_experimental
|
||||
assert not v.linux_revision_security
|
||||
assert not v.linux_revision_backports
|
||||
assert not v.linux_revision_other
|
||||
|
||||
def test_experimental(self) -> None:
|
||||
v = VersionLinux('1.2~rc3-4~exp5')
|
||||
assert v.linux_upstream_full == '1.2-rc3'
|
||||
assert v.linux_revision_experimental
|
||||
assert not v.linux_revision_security
|
||||
assert not v.linux_revision_backports
|
||||
assert not v.linux_revision_other
|
||||
|
||||
def test_security(self) -> None:
|
||||
v = VersionLinux('1.2.3-4+deb10u1')
|
||||
assert v.linux_upstream_full == '1.2.3'
|
||||
assert not v.linux_revision_experimental
|
||||
assert v.linux_revision_security
|
||||
assert not v.linux_revision_backports
|
||||
assert not v.linux_revision_other
|
||||
|
||||
def test_backports(self) -> None:
|
||||
v = VersionLinux('1.2.3-4~bpo9+10')
|
||||
assert v.linux_upstream_full == '1.2.3'
|
||||
assert not v.linux_revision_experimental
|
||||
assert not v.linux_revision_security
|
||||
assert v.linux_revision_backports
|
||||
assert not v.linux_revision_other
|
||||
|
||||
def test_security_backports(self) -> None:
|
||||
v = VersionLinux('1.2.3-4+deb10u1~bpo9+10')
|
||||
assert v.linux_upstream_full == '1.2.3'
|
||||
assert not v.linux_revision_experimental
|
||||
assert v.linux_revision_security
|
||||
assert v.linux_revision_backports
|
||||
assert not v.linux_revision_other
|
||||
|
||||
def test_lts_backports(self) -> None:
|
||||
# Backport during LTS, as an extra package in the -security
|
||||
# suite. Since this is not part of a -backports suite it
|
||||
# shouldn't get the linux_revision_backports flag.
|
||||
v = VersionLinux('1.2.3-4~deb9u10')
|
||||
assert v.linux_upstream_full == '1.2.3'
|
||||
assert not v.linux_revision_experimental
|
||||
assert v.linux_revision_security
|
||||
assert not v.linux_revision_backports
|
||||
assert not v.linux_revision_other
|
||||
|
||||
def test_lts_backports_2(self) -> None:
|
||||
# Same but with two security extensions in the revision.
|
||||
v = VersionLinux('1.2.3-4+deb10u1~deb9u10')
|
||||
assert v.linux_upstream_full == '1.2.3'
|
||||
assert not v.linux_revision_experimental
|
||||
assert v.linux_revision_security
|
||||
assert not v.linux_revision_backports
|
||||
assert not v.linux_revision_other
|
||||
|
||||
def test_binnmu(self) -> None:
|
||||
v = VersionLinux('1.2.3-4+b1')
|
||||
assert not v.linux_revision_experimental
|
||||
assert not v.linux_revision_security
|
||||
assert not v.linux_revision_backports
|
||||
assert not v.linux_revision_other
|
||||
|
||||
def test_other_revision(self) -> None:
|
||||
v = VersionLinux('4.16.5-1+revert+crng+ready') # from #898087
|
||||
assert not v.linux_revision_experimental
|
||||
assert not v.linux_revision_security
|
||||
assert not v.linux_revision_backports
|
||||
assert v.linux_revision_other
|
||||
|
||||
def test_other_revision_binnmu(self) -> None:
|
||||
v = VersionLinux('4.16.5-1+revert+crng+ready+b1')
|
||||
assert not v.linux_revision_experimental
|
||||
assert not v.linux_revision_security
|
||||
assert not v.linux_revision_backports
|
||||
assert v.linux_revision_other
|
||||
|
||||
|
||||
class TestPackageArchitecture:
|
||||
def test_init(self) -> None:
|
||||
a = PackageArchitecture()
|
||||
assert a == set()
|
||||
|
||||
def test_init_str(self) -> None:
|
||||
a = PackageArchitecture(' foo bar\tbaz ')
|
||||
assert a == {'foo', 'bar', 'baz'}
|
||||
|
||||
def test_init_iter(self) -> None:
|
||||
a = PackageArchitecture(('foo', 'bar'))
|
||||
assert a == {'foo', 'bar'}
|
||||
|
||||
def test_init_self(self) -> None:
|
||||
a = PackageArchitecture(PackageArchitecture(('foo', 'bar')))
|
||||
assert a == {'foo', 'bar'}
|
||||
|
||||
def test_str(self) -> None:
|
||||
a = PackageArchitecture(('foo', 'bar'))
|
||||
assert str(a) == 'bar foo'
|
||||
|
||||
|
||||
class TestPackageDescription:
|
||||
def test_init(self) -> None:
|
||||
a = PackageDescription()
|
||||
assert a.short == []
|
||||
assert a.long == []
|
||||
|
||||
def test_init_str(self) -> None:
|
||||
a = PackageDescription('Short\nLong1\n.\nLong2')
|
||||
assert a.short == ['Short']
|
||||
assert a.long == ['Long1', 'Long2']
|
||||
|
||||
def test_init_self(self) -> None:
|
||||
a = PackageDescription(PackageDescription('Short\nLong1\n.\nLong2'))
|
||||
assert a.short == ['Short']
|
||||
assert a.long == ['Long1', 'Long2']
|
||||
|
||||
def test_str(self) -> None:
|
||||
a = PackageDescription('Short\nLong1\n.\nLong2')
|
||||
assert str(a) == 'Short\nLong1\n.\nLong2'
|
||||
|
||||
|
||||
class TestPackageRelationEntry:
|
||||
def test_init_str(self) -> None:
|
||||
a = PackageRelationEntry('package (>=version) [arch2 arch1] <profile1 >')
|
||||
assert a.name == 'package'
|
||||
assert a.version == 'version'
|
||||
assert a.arches == {'arch1', 'arch2'}
|
||||
# TODO: assert a.profiles
|
||||
assert str(a) == 'package (>= version) [arch1 arch2] <profile1>'
|
||||
|
||||
def test_init_self(self) -> None:
|
||||
a = PackageRelationEntry(PackageRelationEntry('package [arch2 arch1]'))
|
||||
assert a.name == 'package'
|
||||
assert a.arches == {'arch1', 'arch2'}
|
||||
assert str(a) == 'package [arch1 arch2]'
|
||||
|
||||
|
||||
class TestPackageRelationGroup:
|
||||
def test_init(self) -> None:
|
||||
a = PackageRelationGroup()
|
||||
assert a == []
|
||||
|
||||
def test_init_str(self) -> None:
|
||||
a = PackageRelationGroup('foo | bar')
|
||||
assert len(a) == 2
|
||||
assert a[0].name == 'foo'
|
||||
assert a[1].name == 'bar'
|
||||
|
||||
def test_init_iter_entry(self) -> None:
|
||||
a = PackageRelationGroup((PackageRelationEntry('foo'), PackageRelationEntry('bar')))
|
||||
assert len(a) == 2
|
||||
assert a[0].name == 'foo'
|
||||
assert a[1].name == 'bar'
|
||||
|
||||
def test_init_iter_str(self) -> None:
|
||||
a = PackageRelationGroup(('foo', 'bar'))
|
||||
assert len(a) == 2
|
||||
assert a[0].name == 'foo'
|
||||
assert a[1].name == 'bar'
|
||||
|
||||
def test_init_self(self) -> None:
|
||||
a = PackageRelationGroup(PackageRelationGroup(['foo', 'bar']))
|
||||
assert len(a) == 2
|
||||
assert a[0].name == 'foo'
|
||||
assert a[1].name == 'bar'
|
||||
|
||||
def test_str(self) -> None:
|
||||
a = PackageRelationGroup('foo| bar')
|
||||
assert str(a) == 'foo | bar'
|
||||
|
||||
|
||||
class TestPackageRelation:
|
||||
def test_init(self) -> None:
|
||||
a = PackageRelation()
|
||||
assert a == []
|
||||
|
||||
def test_init_str(self) -> None:
|
||||
a = PackageRelation('foo1 | foo2, bar')
|
||||
assert len(a) == 2
|
||||
assert len(a[0]) == 2
|
||||
assert a[0][0].name == 'foo1'
|
||||
assert a[0][1].name == 'foo2'
|
||||
assert len(a[1]) == 1
|
||||
assert a[1][0].name == 'bar'
|
||||
|
||||
def test_init_iter_entry(self) -> None:
|
||||
a = PackageRelation([[PackageRelationEntry('foo')], [PackageRelationEntry('bar')]])
|
||||
assert len(a) == 2
|
||||
assert len(a[0]) == 1
|
||||
assert a[0][0].name == 'foo'
|
||||
assert len(a[1]) == 1
|
||||
assert a[1][0].name == 'bar'
|
||||
|
||||
def test_init_iter_str(self) -> None:
|
||||
a = PackageRelation(('foo', 'bar'))
|
||||
assert len(a) == 2
|
||||
assert len(a[0]) == 1
|
||||
assert a[0][0].name == 'foo'
|
||||
assert len(a[1]) == 1
|
||||
assert a[1][0].name == 'bar'
|
||||
|
||||
def test_init_self(self) -> None:
|
||||
a = PackageRelation(PackageRelation(('foo', 'bar')))
|
||||
assert len(a) == 2
|
||||
assert len(a[0]) == 1
|
||||
assert a[0][0].name == 'foo'
|
||||
assert len(a[1]) == 1
|
||||
assert a[1][0].name == 'bar'
|
||||
|
||||
def test_str(self) -> None:
|
||||
a = PackageRelation('foo ,bar')
|
||||
assert str(a) == 'foo, bar'
|
||||
|
||||
|
||||
class TestPackageBuildprofileEntry:
|
||||
def test_parse(self) -> None:
|
||||
a = PackageBuildprofileEntry.parse('<profile1 !profile2 profile3 !profile4>')
|
||||
assert a.pos == {'profile1', 'profile3'}
|
||||
assert a.neg == {'profile2', 'profile4'}
|
||||
assert str(a) == '<profile1 profile3 !profile2 !profile4>'
|
||||
|
||||
def test_eq(self) -> None:
|
||||
a = PackageBuildprofileEntry.parse('<profile1 !profile2>')
|
||||
b = PackageBuildprofileEntry(pos={'profile1'}, neg={'profile2'})
|
||||
assert a == b
|
||||
|
||||
def test_isdisjoint(self) -> None:
|
||||
a = PackageBuildprofileEntry.parse('<profile1 profile2>')
|
||||
b = PackageBuildprofileEntry.parse('<profile1 profile3>')
|
||||
assert a.isdisjoint(b)
|
||||
|
||||
def test_issubset_empty(self) -> None:
|
||||
a = PackageBuildprofileEntry.parse('<profile1 profile2>')
|
||||
b = PackageBuildprofileEntry()
|
||||
assert a.issubset(b)
|
||||
|
||||
def test_issubset_pos(self) -> None:
|
||||
a = PackageBuildprofileEntry.parse('<profile1 profile2>')
|
||||
b = PackageBuildprofileEntry.parse('<profile1>')
|
||||
assert a.issubset(b)
|
||||
|
||||
def test_issubset_neg(self) -> None:
|
||||
a = PackageBuildprofileEntry.parse('<!profile1>')
|
||||
b = PackageBuildprofileEntry.parse('<!profile1 !profile2>')
|
||||
assert a.issubset(b)
|
||||
|
||||
def test_issubset_both(self) -> None:
|
||||
a = PackageBuildprofileEntry.parse('<!profile1 !profile2 profile3>')
|
||||
b = PackageBuildprofileEntry.parse('<!profile1 !profile2 !profile3>')
|
||||
assert a.issubset(b)
|
||||
|
||||
def test_issuperset_empty(self) -> None:
|
||||
a = PackageBuildprofileEntry.parse('<profile1 profile2>')
|
||||
b = PackageBuildprofileEntry()
|
||||
assert b.issuperset(a)
|
||||
|
||||
def test_issuperset_pos(self) -> None:
|
||||
a = PackageBuildprofileEntry.parse('<profile1 profile2>')
|
||||
b = PackageBuildprofileEntry.parse('<profile1>')
|
||||
assert b.issuperset(a)
|
||||
|
||||
def test_issuperset_neg(self) -> None:
|
||||
a = PackageBuildprofileEntry.parse('<!profile1>')
|
||||
b = PackageBuildprofileEntry.parse('<!profile1 !profile2>')
|
||||
assert b.issuperset(a)
|
||||
|
||||
def test_issuperset_both(self) -> None:
|
||||
a = PackageBuildprofileEntry.parse('<!profile1 !profile2 profile3>')
|
||||
b = PackageBuildprofileEntry.parse('<!profile1 !profile2 !profile3>')
|
||||
assert b.issuperset(a)
|
||||
|
||||
def test_update_pos(self) -> None:
|
||||
a = PackageBuildprofileEntry.parse('<profile1 profile2>')
|
||||
b = PackageBuildprofileEntry.parse('<profile1>')
|
||||
a.update(b)
|
||||
assert a.pos == {'profile1'}
|
||||
assert a.neg == set()
|
||||
|
||||
def test_update_neg(self) -> None:
|
||||
a = PackageBuildprofileEntry.parse('<!profile1 !profile2>')
|
||||
b = PackageBuildprofileEntry.parse('<!profile1>')
|
||||
a.update(b)
|
||||
assert a.pos == set()
|
||||
assert a.neg == {'profile1'}
|
||||
|
||||
def test_update_both(self) -> None:
|
||||
a = PackageBuildprofileEntry.parse('<profile1 !profile2 profile3>')
|
||||
b = PackageBuildprofileEntry.parse('<profile1 !profile2 !profile3>')
|
||||
a.update(b)
|
||||
assert a.pos == {'profile1'}
|
||||
assert a.neg == {'profile2'}
|
||||
|
||||
|
||||
class TestPackageBuildprofile:
|
||||
def test_parse(self) -> None:
|
||||
a = PackageBuildprofile.parse('<profile1> <!profile2> <profile3> <!profile4>')
|
||||
assert str(a) == '<profile1> <!profile2> <profile3> <!profile4>'
|
||||
|
||||
def test_update(self) -> None:
|
||||
a = PackageBuildprofile.parse('<profile1 profile2> <profile2>')
|
||||
b = PackageBuildprofile.parse('<profile1> <profile2 !profile3> <profile3>')
|
||||
a.update(b)
|
||||
assert str(a) == '<profile1> <profile2> <profile3>'
|
Reference in New Issue
Block a user