#!/usr/bin/env python3 # # Copyright (C) 2023 The Android Open Source Project # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at # # http://www.apache.org/licenses/LICENSE-2.0 # # Unless required by applicable law or agreed to in writing, software # distributed under the License is distributed on an "AS IS" BASIS, # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. # See the License for the specific language governing permissions and # limitations under the License.
"""
Serialize objects defined in package sbom_data to SPDX format: tagvalue, JSON. """
import json import sbom_data
SPDX_VER = 'SPDX-2.3'
DATA_LIC = 'CC0-1.0'
class Tags: # Common
SPDXID = 'SPDXID'
SPDX_VERSION = 'SPDXVersion'
DATA_LICENSE = 'DataLicense'
DOCUMENT_NAME = 'DocumentName'
DOCUMENT_NAMESPACE = 'DocumentNamespace'
CREATED = 'Created'
CREATOR = 'Creator'
EXTERNAL_DOCUMENT_REF = 'ExternalDocumentRef'
license = sbom_data.VALUE_NOASSERTION if package.declared_license_ids:
license = ' OR '.join(package.declared_license_ids)
tagvalues.append(f'{Tags.PACKAGE_LICENSE_DECLARED}: {license}')
if package.verification_code:
tagvalues.append(f'{Tags.PACKAGE_VERIFICATION_CODE}: {package.verification_code}') if package.external_refs: for external_ref in package.external_refs:
tagvalues.append(
f'{Tags.PACKAGE_EXTERNAL_REF}: {external_ref.category} {external_ref.type} {external_ref.locator}')
for file in sbom_doc.files: if file.id in package.file_ids:
tagvalues += TagValueWriter.marshal_file(file)
return tagvalues
@staticmethod def marshal_packages(sbom_doc, fragment):
tagvalues = []
marshaled_relationships = []
i = 0
packages = sbom_doc.packages while i < len(packages): if (i + 1 < len(packages) and packages[i].id.startswith('SPDXRef-SOURCE-') and packages[i + 1].id.startswith('SPDXRef-UPSTREAM-')): # Output SOURCE, UPSTREAM packages and their VARIANT_OF relationship together, so they are close to each other # in SBOMs in tagvalue format.
tagvalues += TagValueWriter.marshal_package(sbom_doc, packages[i], fragment)
tagvalues += TagValueWriter.marshal_package(sbom_doc, packages[i + 1], fragment)
rel = next((r for r in sbom_doc.relationships if
r.id1 == packages[i].id and
r.id2 == packages[i + 1].id and
r.relationship == sbom_data.RelationshipType.VARIANT_OF), None) if rel:
marshaled_relationships.append(rel)
tagvalues.append(TagValueWriter.marshal_relationship(rel))
tagvalues.append('')
i += 2 else:
tagvalues += TagValueWriter.marshal_package(sbom_doc, packages[i], fragment)
i += 1
@staticmethod def marshal_files(sbom_doc, fragment):
tagvalues = []
files_in_packages = [] for package in sbom_doc.packages:
files_in_packages += package.file_ids for file in sbom_doc.files: if file.id in files_in_packages: continue
tagvalues += TagValueWriter.marshal_file(file) if file.id == sbom_doc.describes andnot fragment: # Fragment is not a full SBOM document so the relationship DESCRIBES is not applicable.
tagvalues.append(
f'{Tags.RELATIONSHIP}: {sbom_doc.id} {sbom_data.RelationshipType.DESCRIBES} {sbom_doc.describes}')
tagvalues.append('') return tagvalues
@staticmethod def marshal_relationships(sbom_doc, marshaled_rels):
tagvalues = []
sorted_rels = sorted(sbom_doc.relationships, key=lambda r: r.id2 + r.id1) for rel in sorted_rels: if any(r.id1 == rel.id1 and r.id2 == rel.id2 and r.relationship == rel.relationship for r in marshaled_rels): continue
tagvalues.append(TagValueWriter.marshal_relationship(rel))
tagvalues.append('') return tagvalues
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.