Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
25 changes: 24 additions & 1 deletion src/spdx_tools/spdx/validation/package_validator.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,10 @@

from beartype.typing import List, Optional

from spdx_tools.spdx.model import Document, File, Package, Relationship, RelationshipType
from spdx_tools.spdx.model import Actor, ActorType, Document, File, Package, Relationship, RelationshipType
from spdx_tools.spdx.model.relationship_filters import filter_by_type_and_origin, filter_by_type_and_target
from spdx_tools.spdx.spdx_element_utils import get_element_type_from_spdx_id
from spdx_tools.spdx.validation.actor_validator import validate_actor
from spdx_tools.spdx.validation.checksum_validator import validate_checksums
from spdx_tools.spdx.validation.external_package_ref_validator import validate_external_package_refs
from spdx_tools.spdx.validation.license_expression_validator import (
Expand Down Expand Up @@ -121,6 +122,28 @@ def validate_package(
for message in validate_url(homepage):
validation_messages.append(ValidationMessage("homepage " + message, context))

if isinstance(package.supplier, Actor):
if package.supplier.actor_type == ActorType.TOOL:
validation_messages.append(
ValidationMessage(
f"package supplier must not be of actor type TOOL, but is: {package.supplier}",
context,
)
)
else:
validation_messages.extend(validate_actor(package.supplier, package.spdx_id))

if isinstance(package.originator, Actor):
if package.originator.actor_type == ActorType.TOOL:
validation_messages.append(
ValidationMessage(
f"package originator must not be of actor type TOOL, but is: {package.originator}",
context,
)
)
else:
validation_messages.extend(validate_actor(package.originator, package.spdx_id))

verification_code = package.verification_code
if verification_code:
if not package.files_analyzed:
Expand Down
41 changes: 40 additions & 1 deletion tests/spdx/validation/test_package_validator.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@

from spdx_tools.common.spdx_licensing import spdx_licensing
from spdx_tools.spdx.constants import DOCUMENT_SPDX_ID
from spdx_tools.spdx.model import Relationship, RelationshipType, SpdxNoAssertion, SpdxNone
from spdx_tools.spdx.model import Actor, ActorType, Relationship, RelationshipType, SpdxNoAssertion, SpdxNone
from spdx_tools.spdx.validation.package_validator import validate_package, validate_package_within_document
from spdx_tools.spdx.validation.validation_message import SpdxElementType, ValidationContext, ValidationMessage
from tests.spdx.fixtures import document_fixture, file_fixture, package_fixture, package_verification_code_fixture
Expand Down Expand Up @@ -154,3 +154,42 @@ def test_v2_2mandatory_fields():
expected = [ValidationMessage(f"{field} is mandatory in SPDX-2.2", context) for field in mandatory_fields]

TestCase().assertCountEqual(validation_messages, expected)


@pytest.mark.parametrize(
"actor_field, actor_type_name",
[
("supplier", "supplier"),
("originator", "originator"),
],
)
def test_invalid_package_actor_tool(actor_field, actor_type_name):
tool_actor = Actor(actor_type=ActorType.TOOL, name="ToolName")
package = package_fixture(**{actor_field: tool_actor})
validation_messages = validate_package(package, "SPDX-2.3")

context = ValidationContext(spdx_id=package.spdx_id, element_type=SpdxElementType.PACKAGE, full_element=package)
expected = [
ValidationMessage(
f"package {actor_type_name} must not be of actor type TOOL, but is: Tool: ToolName",
context,
)
]

assert validation_messages == expected


@pytest.mark.parametrize(
"actor",
[
Actor(actor_type=ActorType.PERSON, name="Jane Doe", email="jane@example.com"),
Actor(actor_type=ActorType.ORGANIZATION, name="Acme Corp"),
SpdxNoAssertion(),
None,
],
)
def test_valid_package_supplier_and_originator(actor):
package = package_fixture(supplier=actor, originator=actor)
validation_messages = validate_package(package, "SPDX-2.3")

assert validation_messages == []