@prefix ex: <https://example.com/scoped-statements/> .
@prefix rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#> .
@prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#> .
@prefix spdx-core: <https://spdx.org/rdf/3.0.1/terms/Core/> .
@prefix spdx-sw: <https://spdx.org/rdf/3.0.1/terms/Software/> .
@prefix ver: <https://ontology.inferal.com/modules/versioning/> .
@prefix ss: <https://ontology.inferal.com/modules/scoped-statements/> .
@prefix xsd: <http://www.w3.org/2001/XMLSchema#> .

################################################################################
# Ordering setup
#
# Authors can state adjacent ordering edges directly, or they can provide
# normalized numeric components and let the SWRL rule templates in the
# versioning module infer ver:greaterThanVersion. The component convention is:
#
# - X.Y means major X, minor Y, patch 0
# - X.Y.Z means major X, minor Y, patch Z
# - X.Y-suffix and X.Y.Z-suffix keep the suffix for display/provenance, but the
#   ordering rules ignore it
#
# Once any direct or SWRL-derived greater-than edges exist, the OWL transitive
# property declaration can materialize the complete ordering closure.
################################################################################

ex:semver
    a ver:NumericComponentOrdering ;
    rdfs:label "Numeric component order with ignored suffixes" .

ex:v1-0
    a ver:ComponentVersionIdentifier ;
    ver:versionText "1.0" ;
    ver:versionMajor 1 ;
    ver:versionMinor 0 ;
    ver:versionPatch 0 ;
    ver:inVersionOrdering ex:semver .

ex:v1-5-alpha
    a ver:ComponentVersionIdentifier ;
    ver:versionText "1.5-alpha" ;
    ver:versionMajor 1 ;
    ver:versionMinor 5 ;
    ver:versionPatch 0 ;
    ver:versionSuffix "alpha" ;
    ver:inVersionOrdering ex:semver ;
    ver:greaterThanVersion ex:v1-0 .

ex:v2-0-0
    a ver:ComponentVersionIdentifier ;
    ver:versionText "2.0.0" ;
    ver:versionMajor 2 ;
    ver:versionMinor 0 ;
    ver:versionPatch 0 ;
    ver:inVersionOrdering ex:semver ;
    ver:greaterThanVersion ex:v1-5-alpha .

ex:v2-1-0-build-7
    a ver:ComponentVersionIdentifier ;
    ver:versionText "2.1.0-build.7" ;
    ver:versionMajor 2 ;
    ver:versionMinor 1 ;
    ver:versionPatch 0 ;
    ver:versionSuffix "build.7" ;
    ver:inVersionOrdering ex:semver ;
    ver:greaterThanVersion ex:v2-0-0 .

################################################################################
# Ranges
#
# A missing bound means that side is open-ended. Inclusivity flags are present
# only on the bounded side they describe.
################################################################################

# Applies to the 1.x line: [1.0, 2.0.0).
ex:range-1-x
    a ver:VersionRange ;
    ver:lowerBound ex:v1-0 ;
    ver:lowerInclusive true ;
    ver:upperBound ex:v2-0-0 ;
    ver:upperInclusive false .

# Applies to all versions before 2.0.0: (-infinity, 2.0.0).
ex:range-before-2
    a ver:VersionRange ;
    ver:upperBound ex:v2-0-0 ;
    ver:upperInclusive false .

# Applies from 2.0.0 onward: [2.0.0, +infinity).
ex:range-2-plus
    a ver:VersionRange ;
    ver:lowerBound ex:v2-0-0 ;
    ver:lowerInclusive true .

################################################################################
# SPDX example resource
#
# The claims below target RDF statements about an SPDX package. SPDX remains
# ordinary source vocabulary in the example, not a dependency of the scoped
# statements ontology.
################################################################################

ex:package
    a spdx-core:Element, spdx-sw:Package ;
    spdx-sw:packageVersion "1.5-alpha" ;
    rdfs:label "Example runtime package" .

################################################################################
# Exact quad targets
#
# Quad targets identify the fact being discussed. The fact may have a resource
# object or a literal object, so the model keeps those object forms separate.
################################################################################

# Claim type: reviewed license statement.
# The target is a resource-object quad: "the package declares Apache-2.0".
ex:license-quad
    a ss:QuadTarget, ss:ScopedTarget ;
    ss:subjectTerm ex:package ;
    ss:predicateTerm spdx-core:declaredLicense ;
    ss:objectResourceTerm ex:Apache-2.0 ;
    ss:graphTerm ex:sbom-graph .

# Claim type: notice text applies only to the 1.x line.
# The target is a literal-object quad.
ex:notice-quad
    a ss:QuadTarget, ss:ScopedTarget ;
    ss:subjectTerm ex:package ;
    ss:predicateTerm rdfs:comment ;
    ss:objectLiteralValue "Package notice applies to the 1.x line." ;
    ss:graphTerm ex:sbom-graph .

# RDF 1.2 also permits a blank node as a graph name. Its identity remains local
# to the RDF dataset in which this target is interpreted.
ex:local-graph-quad
    a ss:QuadTarget, ss:ScopedTarget ;
    ss:subjectTerm ex:package ;
    ss:predicateTerm ex:reviewState ;
    ss:objectResourceTerm ex:reviewed ;
    ss:graphTerm _:local-review-graph .

# Claim type: a vulnerability assertion is true before a fixed version.
# The target is the vulnerability fact, and the claim range says when it is true.
ex:vulnerability-quad
    a ss:QuadTarget, ss:ScopedTarget ;
    ss:subjectTerm ex:package ;
    ss:predicateTerm ex:hasKnownVulnerability ;
    ss:objectResourceTerm ex:CVE-2099-0001 ;
    ss:graphTerm ex:security-advisory-graph .

# Claim type: a deprecated API endpoint remains present during 1.x.
# Consumers can distinguish "the quad exists" from "the quad is deprecated" by
# putting the interpretation in the claim value rather than in the target.
ex:deprecated-endpoint-quad
    a ss:QuadTarget, ss:ScopedTarget ;
    ss:subjectTerm ex:package ;
    ss:predicateTerm ex:exposesEndpoint ;
    ss:objectResourceTerm ex:v1-api-endpoint ;
    ss:graphTerm ex:api-compatibility-graph .

# Claim type: a replacement endpoint is authoritative from 2.0.0 onward.
ex:replacement-endpoint-quad
    a ss:QuadTarget, ss:ScopedTarget ;
    ss:subjectTerm ex:package ;
    ss:predicateTerm ex:exposesEndpoint ;
    ss:objectResourceTerm ex:v2-api-endpoint ;
    ss:graphTerm ex:api-compatibility-graph .

################################################################################
# Quad groups
#
# Use a group when a claim applies to a set of related facts as one reviewed
# unit. Each member remains a concrete QuadTarget for auditability.
################################################################################

ex:metadata-group
    a ss:QuadGroup, ss:ScopedTarget ;
    ss:hasQuad ex:license-quad ;
    ss:hasQuad ex:notice-quad .

ex:production-environment
    rdfs:label "Production environment" .

ex:production-metadata-claim
    a ss:ScopedClaim ;
    ss:claimTarget ex:metadata-group ;
    ss:scope ex:production-environment ;
    ss:claimValue ex:metadata-reviewed-for-production .

ex:api-transition-group
    a ss:QuadGroup, ss:ScopedTarget ;
    ss:hasQuad ex:deprecated-endpoint-quad ;
    ss:hasQuad ex:replacement-endpoint-quad .

################################################################################
# Version-scoped claims
#
# Each claim connects a target, a range, and a claim value. The claim value is a
# resource so projects can later give it richer structure, provenance, evidence,
# approval workflow state, or links to tickets and advisories.
################################################################################

# The license quad has been reviewed for the 1.x line.
ex:license-claim
    a ss:ScopedClaim ;
    ss:claimTarget ex:license-quad ;
    ss:scope ex:range-1-x ;
    ss:claimValue ex:license-reviewed .

# The notice text should be interpreted as applying only to 1.x releases.
ex:notice-claim
    a ss:ScopedClaim ;
    ss:claimTarget ex:notice-quad ;
    ss:scope ex:range-1-x ;
    ss:claimValue ex:notice-applies-to-1-x .

# The license and notice facts are stable as a reviewed metadata group for 1.x.
ex:metadata-group-claim
    a ss:ScopedClaim ;
    ss:claimTarget ex:metadata-group ;
    ss:scope ex:range-1-x ;
    ss:claimValue ex:metadata-stable .

# A known vulnerability applies before 2.0.0 and is intentionally not stated for
# later versions. This is a range-specific statement about the vulnerability
# fact, not a permanent fact about the package.
ex:vulnerability-claim
    a ss:ScopedClaim ;
    ss:claimTarget ex:vulnerability-quad ;
    ss:scope ex:range-before-2 ;
    ss:claimValue ex:vulnerability-present .

# The old endpoint remains present but deprecated during 1.x.
ex:deprecated-endpoint-claim
    a ss:ScopedClaim ;
    ss:claimTarget ex:deprecated-endpoint-quad ;
    ss:scope ex:range-1-x ;
    ss:claimValue ex:deprecated-but-supported .

# The new endpoint is authoritative starting at 2.0.0.
ex:replacement-endpoint-claim
    a ss:ScopedClaim ;
    ss:claimTarget ex:replacement-endpoint-quad ;
    ss:scope ex:range-2-plus ;
    ss:claimValue ex:authoritative-replacement .

# The endpoint transition can be reviewed as a group that spans both the old and
# new facts. The group claim applies from 2.0.0 onward because that is when the
# replacement becomes authoritative.
ex:api-transition-claim
    a ss:ScopedClaim ;
    ss:claimTarget ex:api-transition-group ;
    ss:scope ex:range-2-plus ;
    ss:claimValue ex:api-transition-reviewed .

################################################################################
# Versioning groups
#
# Sometimes the thing that changes between versions is not one fact but a bundle
# of related facts. The group itself can be treated as a versioned subject by
# targeting a quad that says "this package has this group". This lets consumers
# ask which group applies to a package at a version without flattening the group
# into one opaque claim.
################################################################################

# During 1.x, the package's relevant metadata group is the license+notice group.
ex:metadata-group-version-record
    a ss:QuadTarget, ss:ScopedTarget ;
    ss:subjectTerm ex:package ;
    ss:predicateTerm ex:hasVersionedStatementGroup ;
    ss:objectResourceTerm ex:metadata-group ;
    ss:graphTerm ex:group-versioning-graph .

ex:metadataGroupVersionClaim
    a ss:ScopedClaim ;
    ss:claimTarget ex:metadata-group-version-record ;
    ss:scope ex:range-1-x ;
    ss:claimValue ex:metadata-group-applies .

# From 2.0.0 onward, the package's relevant transition group is the old+new API
# pair. The group membership remains explicit through ss:hasQuad, while this
# claim says when that group should be selected for the package.
ex:api-transition-group-version-record
    a ss:QuadTarget, ss:ScopedTarget ;
    ss:subjectTerm ex:package ;
    ss:predicateTerm ex:hasVersionedStatementGroup ;
    ss:objectResourceTerm ex:api-transition-group ;
    ss:graphTerm ex:group-versioning-graph .

ex:apiTransitionGroupVersionClaim
    a ss:ScopedClaim ;
    ss:claimTarget ex:api-transition-group-version-record ;
    ss:scope ex:range-2-plus ;
    ss:claimValue ex:api-transition-group-applies .

################################################################################
# Claim values
#
# These are deliberately lightweight resources in the example. A production
# graph can make them instances of richer local policy, security, compatibility,
# or review ontologies.
################################################################################

ex:license-reviewed
    rdfs:label "Declared license reviewed" .

ex:notice-applies-to-1-x
    rdfs:label "Notice applies to the 1.x line" .

ex:metadata-stable
    rdfs:label "Metadata group stable for range" .

ex:vulnerability-present
    rdfs:label "Known vulnerability present before fixed version" .

ex:deprecated-but-supported
    rdfs:label "Deprecated but supported" .

ex:authoritative-replacement
    rdfs:label "Authoritative replacement" .

ex:api-transition-reviewed
    rdfs:label "API transition reviewed" .

ex:metadata-group-applies
    rdfs:label "Metadata group applies to package version range" .

ex:metadata-reviewed-for-production
    rdfs:label "Metadata reviewed for production environment" .

ex:api-transition-group-applies
    rdfs:label "API transition group applies to package version range" .
