Skip to content

Commit 1e71dc3

Browse files
committed
add .component.cryptoProperties - with test failures for SchemaVersion < 1.6
Signed-off-by: Paul Horton <[email protected]>
1 parent ee80ea3 commit 1e71dc3

File tree

6 files changed

+1902
-7
lines changed

6 files changed

+1902
-7
lines changed

cyclonedx/exception/model.py

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,15 @@ class InvalidLocaleTypeException(CycloneDxModelException):
4545
pass
4646

4747

48+
class InvalidNistQuantumSecurityLevelException(CycloneDxModelException):
49+
"""
50+
Raised when an invalid value is provided for an NIST Quantum Security Level
51+
as defined at https://csrc.nist.gov/projects/post-quantum-cryptography/post-quantum-cryptography-standardization/
52+
evaluation-criteria/security-(evaluation-criteria).
53+
"""
54+
pass
55+
56+
4857
class InvalidOmniBorIdException(CycloneDxModelException):
4958
"""
5059
Raised when a supplied value for an OmniBOR ID does not meet the format requirements
@@ -53,6 +62,13 @@ class InvalidOmniBorIdException(CycloneDxModelException):
5362
pass
5463

5564

65+
class InvalidRelatedCryptoMaterialSizeException(CycloneDxModelException):
66+
"""
67+
Raised when the supplied size of a Related Crypto Material is negative.
68+
"""
69+
pass
70+
71+
5672
class InvalidSwhidException(CycloneDxModelException):
5773
"""
5874
Raised when a supplied value for an Swhid does not meet the format requirements

cyclonedx/model/component.py

Lines changed: 49 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,7 @@
5757
_HashTypeRepositorySerializationHelper,
5858
)
5959
from .bom_ref import BomRef
60+
from .crypto import CryptoProperties
6061
from .dependency import Dependable
6162
from .issue import IssueType
6263
from .license import License, LicenseRepository
@@ -1044,8 +1045,8 @@ def __init__(self, *,
10441045
components: Optional[Iterable['Component']] = None, evidence: Optional[ComponentEvidence] = None,
10451046
modified: bool = False, manufacturer: Optional[OrganizationalEntity] = None,
10461047
authors: Optional[Iterable[OrganizationalContact]] = None,
1047-
omnibor_ids: Optional[Iterable[OmniborId]] = None,
1048-
swhids: Optional[Iterable[Swhid]] = None,
1048+
omnibor_ids: Optional[Iterable[OmniborId]] = None, swhids: Optional[Iterable[Swhid]] = None,
1049+
crypto_properties: Optional[CryptoProperties] = None, tags: Optional[Iterable[str]] = None,
10491050
# Deprecated in v1.6
10501051
author: Optional[str] = None,
10511052
) -> None:
@@ -1058,6 +1059,7 @@ def __init__(self, *,
10581059
self.supplier = supplier
10591060
self.manufacturer = manufacturer
10601061
self.authors = authors or [] # type:ignore[assignment]
1062+
self.author = author
10611063
self.publisher = publisher
10621064
self.group = group
10631065
self.name = name
@@ -1079,13 +1081,15 @@ def __init__(self, *,
10791081
self.components = components or [] # type:ignore[assignment]
10801082
self.evidence = evidence
10811083
self.release_notes = release_notes
1084+
self.crypto_properties = crypto_properties
1085+
self.tags = tags or [] # type:ignore[assignment]
10821086

1083-
self.author = author
1087+
if modified:
1088+
warn('`.component.modified` is deprecated from CycloneDX v1.3 onwards. '
1089+
'Please use `@.pedigree` instead.', DeprecationWarning)
10841090
if author:
1085-
warn(
1086-
'`.component.author` is deprecated from CycloneDX v1.6 onwards. '
1087-
'Please use `@.authors` or `@.manufacturer` instead.',
1088-
DeprecationWarning)
1091+
warn('`.component.author` is deprecated from CycloneDX v1.6 onwards. '
1092+
'Please use `@.authors` or `@.manufacturer` instead.', DeprecationWarning)
10891093

10901094
@property
10911095
@serializable.type_mapping(_ComponentTypeSerializationHelper)
@@ -1632,6 +1636,44 @@ def release_notes(self, release_notes: Optional[ReleaseNotes]) -> None:
16321636
# def data(self, ...) -> None:
16331637
# ... # TODO since CDX1.5
16341638

1639+
@property
1640+
@serializable.view(SchemaVersion1Dot6)
1641+
@serializable.xml_sequence(30)
1642+
def crypto_properties(self) -> Optional[CryptoProperties]:
1643+
"""
1644+
Cryptographic assets have properties that uniquely define them and that make them actionable for further
1645+
reasoning. As an example, it makes a difference if one knows the algorithm family (e.g. AES) or the specific
1646+
variant or instantiation (e.g. AES-128-GCM). This is because the security level and the algorithm primitive
1647+
(authenticated encryption) is only defined by the definition of the algorithm variant. The presence of a weak
1648+
cryptographic algorithm like SHA1 vs. HMAC-SHA1 also makes a difference.
1649+
1650+
Returns:
1651+
`CryptoProperties` or `None`
1652+
"""
1653+
return self._crypto_properties
1654+
1655+
@crypto_properties.setter
1656+
def crypto_properties(self, crypto_properties: Optional[CryptoProperties]) -> None:
1657+
self._crypto_properties = crypto_properties
1658+
1659+
@property
1660+
@serializable.view(SchemaVersion1Dot6)
1661+
@serializable.xml_array(serializable.XmlArraySerializationType.NESTED, 'tag')
1662+
@serializable.xml_sequence(31)
1663+
def tags(self) -> 'SortedSet[str]':
1664+
"""
1665+
Textual strings that aid in discovery, search, and retrieval of the associated object.
1666+
Tags often serve as a way to group or categorize similar or related objects by various attributes.
1667+
1668+
Returns:
1669+
`Iterable[str]`
1670+
"""
1671+
return self._tags
1672+
1673+
@tags.setter
1674+
def tags(self, tags: Iterable[str]) -> None:
1675+
self._tags = SortedSet(tags)
1676+
16351677
def get_all_nested_components(self, include_self: bool = False) -> Set['Component']:
16361678
components = set()
16371679
if include_self:

0 commit comments

Comments
 (0)