UJG / Editor's Draft /
GitHub
Table of Contents
  • 1Overview
  • 2Terminology
  • 3Effect
  • 4EffectResource
  • 5Attachment Model
  • 6Normative Artifacts
    • 6.1Ontology
    • 6.2JSON-LD Context
    • 6.3Validation
  • 7Examples
    • 7.1Minimal Example
    • 7.2Artifact Production And Consumption Example
W3C Community Group Draft Report

Effect

incubating

Status of this Document

This report was published by the User Journal Graph Community Group . It is not a W3C Standard nor is it on the W3C Standards Track. Please note that under the W3C Community Contributor License Agreement (CLA) there is a limited opt-out and other conditions apply. Learn more about W3C Community and Business Groups .

Last Update
2026-07-16
Editors
  • Seva Dolgopolov
Group
User Journal Graph Community Group
Repository
View Source
License
W3C-Software-and-Document

1. Overview

This optional module defines graph-native vocabulary for attaching declared effects to Graph Transition and OutgoingTransition nodes.

Without an effect primitive, implementations tend to hide form submission, API invocation, analytics events, generated data, or navigate-with-payload behavior in opaque extensions. That makes a graph appear to advance while the effect that caused or accompanies the transition remains non-portable.

This first version declares that an effective transition has an associated Effect. It also defines generic produced and consumed resource references so an effect can point to concrete resources from other modules, such as [UJG Artifact] Artifact, without the Effect module owning those resource-specific semantics.

The module does not define transport protocols, API request formats, queues, form libraries, analytics payloads, backend workers, framework event handlers, or resource lifecycle semantics.

2. Terminology

  • Effect: An addressable declaration of a side effect associated with a Graph transition edge.

  • Effect attachment: The relation that assigns a transition to an effect declaration.

  • EffectResource: An abstract superclass for concrete resources that may be produced or consumed by an effect.

  • Produced resource: An EffectResource created, emitted, prepared, exported, generated, or made available by an Effect.

  • Consumed resource: An EffectResource accepted, imported, read, redeemed, or otherwise used by an Effect.

3. Effect

An Effect declares that a transition edge has an associated side effect. The effect is addressable, but this module does not define how the side effect is invoked.

An effect can reference produced or consumed resources through producedRefs and consumedRefs. Those references point to concrete subclasses of EffectResource, not to arbitrary graph nodes.

classDiagram
  class Effect {
    id
    producedRefs
    consumedRefs
  }
  class EffectResource
  Effect --> "0..*" EffectResource : producedRefs
  Effect --> "0..*" EffectResource : consumedRefs

Example JSON node:

json
{
  "@id": "urn:effect:authorize-payment",
  "@type": "Effect"
}
{
  "@id": "urn:effect:authorize-payment",
  "@type": "Effect"
}

4. EffectResource

EffectResource is an abstract superclass for resources that can be produced or consumed by an Effect. It gives the generic producedRefs and consumedRefs properties a shared range while leaving concrete resource semantics to other modules.

Concrete modules specialize EffectResource. For example, [UJG Artifact] defines portable resources.

classDiagram
  class EffectResource
  class Artifact
  EffectResource <|-- Artifact

EffectResource should not be used as the only concrete type of a resource node in interoperable examples. Use a concrete subclass such as Artifact.

5. Attachment Model

The module introduces one transition attachment and two resource references:

  • effect:effectRef links a Graph Transition or OutgoingTransition to an Effect.

  • effect:producedRefs links an Effect to one or more produced EffectResource nodes.

  • effect:consumedRefs links an Effect to one or more consumed EffectResource nodes.

A transition without effectRef remains fully valid and traversable. Consumers MAY ignore this module and still process the graph.

Resource-specific metadata belongs to the referenced resource, not the effect. For example, sourceTouchpointRef and targetTouchpointRefs belong on an Artifact; an effect only declares that it produces or consumes the artifact.

6. Normative Artifacts

This module is published through the following artifacts:

  • effect.ttl: ontology, published at https://ujg.specs.openuji.org/ed/ns/effect

  • effect.context.jsonld: JSON-LD term mappings, published at https://ujg.specs.openuji.org/ed/ns/effect.context.jsonld

  • effect.shape.ttl: SHACL validation rules, published at https://ujg.specs.openuji.org/ed/ns/effect.shape

Examples in this page compose the shared baseline context https://ujg.specs.openuji.org/ed/ns/context.jsonld with the Effect context. Examples that use artifacts also compose the Artifact context; examples that reference touchpoints also compose the Surface context.

6.1. Ontology

The normative Effect ontology is defined below and is published at https://ujg.specs.openuji.org/ed/ns/effect.

turtle
@prefix ujg: <https://ujg.specs.openuji.org/ed/ns/core#> .
@prefix ujggraph: <https://ujg.specs.openuji.org/ed/ns/graph#> .
@prefix ujgeffect: <https://ujg.specs.openuji.org/ed/ns/effect#> .
@prefix owl: <http://www.w3.org/2002/07/owl#> .
@prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#> .
@prefix dct: <http://purl.org/dc/terms/> .

<https://ujg.specs.openuji.org/ed/ns/effect#> a owl:Ontology ;
  rdfs:label "UJG Effect Editor's Draft Vocabulary"@en ;
  dct:description "UJG Effect ontology declaration" .

### Classes

ujgeffect:Effect a owl:Class ;
  rdfs:subClassOf ujg:Node .

ujgeffect:EffectResource a owl:Class ;
  rdfs:subClassOf ujg:Node .

### Properties

ujgeffect:effectRef a owl:ObjectProperty ;
  rdfs:domain [
    a owl:Class ;
    owl:unionOf ( ujggraph:Transition ujggraph:OutgoingTransition )
  ] ;
  rdfs:range ujgeffect:Effect .

ujgeffect:producedRefs a owl:ObjectProperty ;
  rdfs:domain ujgeffect:Effect ;
  rdfs:range ujgeffect:EffectResource .

ujgeffect:consumedRefs a owl:ObjectProperty ;
  rdfs:domain ujgeffect:Effect ;
  rdfs:range ujgeffect:EffectResource .
@prefix ujg: <https://ujg.specs.openuji.org/ed/ns/core#> .
@prefix ujggraph: <https://ujg.specs.openuji.org/ed/ns/graph#> .
@prefix ujgeffect: <https://ujg.specs.openuji.org/ed/ns/effect#> .
@prefix owl: <http://www.w3.org/2002/07/owl#> .
@prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#> .
@prefix dct: <http://purl.org/dc/terms/> .

<https://ujg.specs.openuji.org/ed/ns/effect#> a owl:Ontology ;
  rdfs:label "UJG Effect Editor's Draft Vocabulary"@en ;
  dct:description "UJG Effect ontology declaration" .

### Classes

ujgeffect:Effect a owl:Class ;
  rdfs:subClassOf ujg:Node .

ujgeffect:EffectResource a owl:Class ;
  rdfs:subClassOf ujg:Node .

### Properties

ujgeffect:effectRef a owl:ObjectProperty ;
  rdfs:domain [
    a owl:Class ;
    owl:unionOf ( ujggraph:Transition ujggraph:OutgoingTransition )
  ] ;
  rdfs:range ujgeffect:Effect .

ujgeffect:producedRefs a owl:ObjectProperty ;
  rdfs:domain ujgeffect:Effect ;
  rdfs:range ujgeffect:EffectResource .

ujgeffect:consumedRefs a owl:ObjectProperty ;
  rdfs:domain ujgeffect:Effect ;
  rdfs:range ujgeffect:EffectResource .

6.2. JSON-LD Context

The normative Effect JSON-LD context is defined below and is published at https://ujg.specs.openuji.org/ed/ns/effect.context.jsonld.

json-ld
{
  "@context": {
    "@version": 1.1,

    "ujgeffect": "https://ujg.specs.openuji.org/ed/ns/effect#",
    "effect": "https://ujg.specs.openuji.org/ed/ns/effect#",

    "Effect": "ujgeffect:Effect",
    "EffectResource": "ujgeffect:EffectResource",

    "effectRef": {
      "@id": "ujgeffect:effectRef",
      "@type": "@id"
    },
    "producedRefs": {
      "@id": "ujgeffect:producedRefs",
      "@type": "@id",
      "@container": "@set"
    },
    "consumedRefs": {
      "@id": "ujgeffect:consumedRefs",
      "@type": "@id",
      "@container": "@set"
    }
  }
}
{
  "@context": {
    "@version": 1.1,

    "ujgeffect": "https://ujg.specs.openuji.org/ed/ns/effect#",
    "effect": "https://ujg.specs.openuji.org/ed/ns/effect#",

    "Effect": "ujgeffect:Effect",
    "EffectResource": "ujgeffect:EffectResource",

    "effectRef": {
      "@id": "ujgeffect:effectRef",
      "@type": "@id"
    },
    "producedRefs": {
      "@id": "ujgeffect:producedRefs",
      "@type": "@id",
      "@container": "@set"
    },
    "consumedRefs": {
      "@id": "ujgeffect:consumedRefs",
      "@type": "@id",
      "@container": "@set"
    }
  }
}

6.3. Validation

The normative Effect SHACL shape is defined below and is published at https://ujg.specs.openuji.org/ed/ns/effect.shape.

turtle
@prefix ujggraph: <https://ujg.specs.openuji.org/ed/ns/graph#> .
@prefix ujgeffect: <https://ujg.specs.openuji.org/ed/ns/effect#> .
@prefix ujgeffectshape: <https://ujg.specs.openuji.org/ed/ns/effect.shape#> .
@prefix sh: <http://www.w3.org/ns/shacl#> .

ujgeffectshape:TransitionEffectShape a sh:NodeShape ;
  sh:targetClass ujggraph:Transition, ujggraph:OutgoingTransition ;
  sh:nodeKind sh:IRI ;

  sh:property [
    sh:path ujgeffect:effectRef ;
    sh:class ujgeffect:Effect ;
    sh:nodeKind sh:IRI ;
    sh:maxCount 1 ;
  ] .

ujgeffectshape:EffectShape a sh:NodeShape ;
  sh:targetClass ujgeffect:Effect ;
  sh:nodeKind sh:IRI ;

  sh:property [
    sh:path ujgeffect:producedRefs ;
    sh:class ujgeffect:EffectResource ;
    sh:nodeKind sh:IRI ;
  ] ;

  sh:property [
    sh:path ujgeffect:consumedRefs ;
    sh:class ujgeffect:EffectResource ;
    sh:nodeKind sh:IRI ;
  ] .

ujgeffectshape:EffectResourceShape a sh:NodeShape ;
  sh:targetClass ujgeffect:EffectResource ;
  sh:nodeKind sh:IRI .

ujgeffectshape:EffectReferenceHostShape a sh:NodeShape ;
  sh:targetSubjectsOf ujgeffect:producedRefs ;
  sh:targetSubjectsOf ujgeffect:consumedRefs ;
  sh:class ujgeffect:Effect ;
  sh:nodeKind sh:IRI .
@prefix ujggraph: <https://ujg.specs.openuji.org/ed/ns/graph#> .
@prefix ujgeffect: <https://ujg.specs.openuji.org/ed/ns/effect#> .
@prefix ujgeffectshape: <https://ujg.specs.openuji.org/ed/ns/effect.shape#> .
@prefix sh: <http://www.w3.org/ns/shacl#> .

ujgeffectshape:TransitionEffectShape a sh:NodeShape ;
  sh:targetClass ujggraph:Transition, ujggraph:OutgoingTransition ;
  sh:nodeKind sh:IRI ;

  sh:property [
    sh:path ujgeffect:effectRef ;
    sh:class ujgeffect:Effect ;
    sh:nodeKind sh:IRI ;
    sh:maxCount 1 ;
  ] .

ujgeffectshape:EffectShape a sh:NodeShape ;
  sh:targetClass ujgeffect:Effect ;
  sh:nodeKind sh:IRI ;

  sh:property [
    sh:path ujgeffect:producedRefs ;
    sh:class ujgeffect:EffectResource ;
    sh:nodeKind sh:IRI ;
  ] ;

  sh:property [
    sh:path ujgeffect:consumedRefs ;
    sh:class ujgeffect:EffectResource ;
    sh:nodeKind sh:IRI ;
  ] .

ujgeffectshape:EffectResourceShape a sh:NodeShape ;
  sh:targetClass ujgeffect:EffectResource ;
  sh:nodeKind sh:IRI .

ujgeffectshape:EffectReferenceHostShape a sh:NodeShape ;
  sh:targetSubjectsOf ujgeffect:producedRefs ;
  sh:targetSubjectsOf ujgeffect:consumedRefs ;
  sh:class ujgeffect:Effect ;
  sh:nodeKind sh:IRI .

Effect validation depends on the Effect SHACL shape and the ontology graph for each composed resource module. The producedRefs and consumedRefs sh:class constraints are evaluated against the referenced resource node's concrete class and the resource module's subclass declarations. Processors MUST NOT require documents to serialize EffectResource as an additional @type merely to satisfy these constraints.

The rules below define the remaining module semantics beyond the structural constraints captured by the SHACL shape.

  1. Declaration only: Effect describes that a transition edge has an associated side effect; it does not define how that effect is invoked.

  2. Graph preservation: effectRef MUST NOT create a hidden edge or change the from/to semantics of the host Transition or OutgoingTransition.

  3. Resource boundary: producedRefs and consumedRefs MUST point to concrete resources that are subclasses of EffectResource. They MUST NOT be used to create hidden Graph traversal.

  4. Resource-owned metadata: Metadata about a produced or consumed resource belongs on the referenced resource node. For example, artifact touchpoint metadata belongs on Artifact, not on Effect.

  5. Graceful degradation: Consumers that do not implement this module MAY ignore Effect semantics, but SHOULD preserve recognized JSON-LD data during read-transform-write when possible.

  6. Private contracts: Transport, command, mutation, retry, idempotency, and result-handling details SHOULD remain in Core extensions unless a future optional module defines them as interoperable vocabulary.

7. Examples

7.1. Minimal Example

json
{
  "@context": [
    "https://ujg.specs.openuji.org/ed/ns/context.jsonld",
    "https://ujg.specs.openuji.org/ed/ns/effect.context.jsonld"
  ],
  "@id": "https://example.com/ujg/effect/checkout.jsonld",
  "@type": "UJGDocument",
  "nodes": [
    {
      "@id": "urn:transition:submit-payment",
      "@type": "Transition",
      "from": "urn:state:payment",
      "to": "urn:state:confirmation",
      "effectRef": "urn:effect:authorize-payment"
    },
    {
      "@id": "urn:effect:authorize-payment",
      "@type": "Effect"
    }
  ]
}
{
  "@context": [
    "https://ujg.specs.openuji.org/ed/ns/context.jsonld",
    "https://ujg.specs.openuji.org/ed/ns/effect.context.jsonld"
  ],
  "@id": "https://example.com/ujg/effect/checkout.jsonld",
  "@type": "UJGDocument",
  "nodes": [
    {
      "@id": "urn:transition:submit-payment",
      "@type": "Transition",
      "from": "urn:state:payment",
      "to": "urn:state:confirmation",
      "effectRef": "urn:effect:authorize-payment"
    },
    {
      "@id": "urn:effect:authorize-payment",
      "@type": "Effect"
    }
  ]
}

7.2. Artifact Production And Consumption Example

This example shows a federated share represented as an artifact crossing touchpoints. Effects declare whether they produce or consume the artifact; the artifact declares source and target touchpoints.

json
{
  "@context": [
    "https://ujg.specs.openuji.org/ed/ns/context.jsonld",
    "https://ujg.specs.openuji.org/ed/ns/surface.context.jsonld",
    "https://ujg.specs.openuji.org/ed/ns/effect.context.jsonld",
    "https://ujg.specs.openuji.org/ed/ns/artifact.context.jsonld"
  ],
  "@id": "https://example.com/ujg/effect/federated-share.jsonld",
  "@type": "UJGDocument",
  "nodes": [
    {
      "@id": "urn:touchpoint:nextcloud-a",
      "@type": "Touchpoint",
      "label": "Nextcloud A"
    },
    {
      "@id": "urn:touchpoint:nextcloud-b",
      "@type": "Touchpoint",
      "label": "Nextcloud B"
    },
    {
      "@id": "urn:artifact:federated-share",
      "@type": "Artifact",
      "label": "Federated share for the test file",
      "sourceTouchpointRef": "urn:touchpoint:nextcloud-a",
      "targetTouchpointRefs": [
        "urn:touchpoint:nextcloud-b"
      ]
    },
    {
      "@id": "urn:effect:alice-confirm-share",
      "@type": "Effect",
      "label": "Alice confirms the remote share",
      "producedRefs": [
        "urn:artifact:federated-share"
      ]
    },
    {
      "@id": "urn:effect:bob-accept-share",
      "@type": "Effect",
      "label": "Bob accepts the incoming remote share",
      "consumedRefs": [
        "urn:artifact:federated-share"
      ]
    },
    {
      "@id": "urn:effect:bob-open-accepted-file",
      "@type": "Effect",
      "label": "Bob opens the accepted file",
      "consumedRefs": [
        "urn:artifact:federated-share"
      ]
    }
  ]
}
{
  "@context": [
    "https://ujg.specs.openuji.org/ed/ns/context.jsonld",
    "https://ujg.specs.openuji.org/ed/ns/surface.context.jsonld",
    "https://ujg.specs.openuji.org/ed/ns/effect.context.jsonld",
    "https://ujg.specs.openuji.org/ed/ns/artifact.context.jsonld"
  ],
  "@id": "https://example.com/ujg/effect/federated-share.jsonld",
  "@type": "UJGDocument",
  "nodes": [
    {
      "@id": "urn:touchpoint:nextcloud-a",
      "@type": "Touchpoint",
      "label": "Nextcloud A"
    },
    {
      "@id": "urn:touchpoint:nextcloud-b",
      "@type": "Touchpoint",
      "label": "Nextcloud B"
    },
    {
      "@id": "urn:artifact:federated-share",
      "@type": "Artifact",
      "label": "Federated share for the test file",
      "sourceTouchpointRef": "urn:touchpoint:nextcloud-a",
      "targetTouchpointRefs": [
        "urn:touchpoint:nextcloud-b"
      ]
    },
    {
      "@id": "urn:effect:alice-confirm-share",
      "@type": "Effect",
      "label": "Alice confirms the remote share",
      "producedRefs": [
        "urn:artifact:federated-share"
      ]
    },
    {
      "@id": "urn:effect:bob-accept-share",
      "@type": "Effect",
      "label": "Bob accepts the incoming remote share",
      "consumedRefs": [
        "urn:artifact:federated-share"
      ]
    },
    {
      "@id": "urn:effect:bob-open-accepted-file",
      "@type": "Effect",
      "label": "Bob opens the accepted file",
      "consumedRefs": [
        "urn:artifact:federated-share"
      ]
    }
  ]
}

Copyright © 2026 the Contributors to the ujg/modules/effect, published by the User Journal Graph Community Group under the W3C Community Contributor License Agreement (CLA) . A human-readable summary is available.

generated by Speculator