Skip to content

Architecture Overview

Module structure

graph TB
    subgraph core["core"]
        UriUtil
        IriMinting
        TypeMapping
        OutputFormat
        RdfIo
        LinkedArchiVocab
        BaseLinkedArchiEmitter
        ConversionVerifier
        DiagramsIndex
        BaseConvertCommand
        BaseValidateCommand
    end

    subgraph svg-core["svg-core"]
        BaseRenderCommand
    end

    subgraph converters["Notation Converters"]
        subgraph am["converter-archimate"]
            ExchangeParser
            AM_Emitter["LinkedArchiEmitter"]
            AM_Convert["ConvertCommand"]
        end
        subgraph bpmn["converter-bpmn"]
            MetaModel
            BpmnXmlToRdfConverter
            BPMN_Emitter["LinkedArchiEmitter"]
            BpmnSvgRenderer
        end
        subgraph puml["converter-plantuml"]
            PlantUmlParser
            PUML_Emitter["LinkedArchiEmitter"]
            PumlSvgRenderer
        end
    end

    core --> am
    core --> bpmn
    core --> puml
    svg-core --> bpmn
    svg-core --> puml

Data flow

Every converter follows the same pipeline:

flowchart LR
    A["Source file\n(XML / BPMN / .puml)"] --> B["Parser\n(notation-specific)"]
    B --> C["Intermediate model\n(Kotlin data classes)"]
    C --> D["LinkedArchiEmitter\n(extends BaseLinkedArchiEmitter)"]
    D --> E["RDF Model\n(RDF4J in-memory)"]
    E --> F["RdfIo\nserialization"]
    F --> G["Output file\n(TriG / Turtle / JSON-LD)"]

Output dataset structure

Every converter produces four named graphs per model:

Graph Content
{base}{notation}/{modelId}/graph/semantic Facts lifted from an input: elements, relationships, and the arch:View resources themselves — typed with notation-specific and arch: foundational types. Split per input where a model has several: graph/semantic/{repo}/{path}
{base}{notation}/{modelId}/graph/model The curated model: the arch:Model resource, its metamodel conformance, its folders and their ordering, and each concept's folder membership. None of it is lifted from a diagram — its input is the diagram index
{base}{notation}/{modelId}/graph/views Presentation only: archvis:ArchNode, archvis:Link and their geometry for diagram rendering
{base}{notation}/{modelId}/graph/provenance What the author declared about the diagram (title, author, dates, adms:status) in Dublin Core, and how the graph was made — the conversion activity, the container image that ran it, the source file at its commit, and each of the graphs above as a prov:Bundle — in PROV-O. See ADR 0008

The boundary between semantic and views falls around geometry, not around diagrams. A view is a model concept, so the view resource — its name and viewpoint — sits in semantic; only where its boxes are drawn sits in views. That keeps the views graph droppable: shedding geometry, which is most of an ArchiMate artifact, never removes a diagram or its label. No subject and no fact is split across the two, so each graph answers its own questions alone. See the converter development guide.

The boundary between semantic and model falls around where the content came from. That is what lets semantic be attributed to a source: curated content has no source to attribute it to, and while it shared the graph nearly half of a model's triples were attributable to nothing. Every concept carries arch:inModel to its model, so the pieces reassemble from the triples alone — in Turtle as well as in TriG. Splitting semantic by input is what makes "everything this file produced" one GRAPH clause, and what lets a fact two inputs both assert be attributed to each. Only backstage2linkedarchi does that today.

Ontology alignment

Converter Source notation Target ontology Namespace
ArchiMate Exchange xsi:type ArchiMate 3.2 am:
BPMN XML element names (CMOF) BPMN 2.0.2 bpmn:
PlantUML Stereotypes/types UML 2.5.1 uml:

All converters additionally emit arch:Element / arch:QualifiedRelationship from the Core Ontology for notation-agnostic querying.