[ { "@id": "https://w3id.org/np/RArXnUQf2dQguqlteWMwKVWxIpnk5xzF4ppAokGkpuOn8/provenance", "@graph": [ { "@id": "https://w3id.org/np/RArXnUQf2dQguqlteWMwKVWxIpnk5xzF4ppAokGkpuOn8/assertion", "http://www.w3.org/ns/prov#wasAttributedTo": [ { "@id": "https://orcid.org/0000-0002-1267-0234" } ] } ] }, { "@id": "https://w3id.org/np/RArXnUQf2dQguqlteWMwKVWxIpnk5xzF4ppAokGkpuOn8/Head", "@graph": [ { "@id": "https://w3id.org/np/RArXnUQf2dQguqlteWMwKVWxIpnk5xzF4ppAokGkpuOn8", "http://www.nanopub.org/nschema#hasAssertion": [ { "@id": "https://w3id.org/np/RArXnUQf2dQguqlteWMwKVWxIpnk5xzF4ppAokGkpuOn8/assertion" } ], "http://www.nanopub.org/nschema#hasProvenance": [ { "@id": "https://w3id.org/np/RArXnUQf2dQguqlteWMwKVWxIpnk5xzF4ppAokGkpuOn8/provenance" } ], "http://www.nanopub.org/nschema#hasPublicationInfo": [ { "@id": "https://w3id.org/np/RArXnUQf2dQguqlteWMwKVWxIpnk5xzF4ppAokGkpuOn8/pubinfo" } ], "@type": [ "http://www.nanopub.org/nschema#Nanopublication" ] } ] }, { "@id": "https://w3id.org/np/RArXnUQf2dQguqlteWMwKVWxIpnk5xzF4ppAokGkpuOn8/pubinfo", "@graph": [ { "@id": "https://orcid.org/0000-0002-1267-0234", "http://xmlns.com/foaf/0.1/name": [ { "@value": "Tobias Kuhn" } ] }, { "@id": "https://w3id.org/np/RArXnUQf2dQguqlteWMwKVWxIpnk5xzF4ppAokGkpuOn8", "http://purl.org/dc/terms/created": [ { "@value": "2026-09-09T08:02:41Z", "@type": "http://www.w3.org/2001/XMLSchema#dateTime" } ], "http://purl.org/dc/terms/creator": [ { "@id": "https://orcid.org/0000-0002-1267-0234" } ], "http://purl.org/dc/terms/license": [ { "@id": "https://creativecommons.org/licenses/by/4.0/" } ], "http://purl.org/nanopub/x/embeds": [ { "@id": "https://w3id.org/np/RArXnUQf2dQguqlteWMwKVWxIpnk5xzF4ppAokGkpuOn8/list-preset-assignments" } ], "http://purl.org/nanopub/x/supersedes": [ { "@id": "https://w3id.org/np/RArC6iR-Bwm8e1RP9PPClwJuzVEKJYX0agMZaQIc9Ln0s" } ], "https://w3id.org/np/o/ntemplate/wasCreatedFromProvenanceTemplate": [ { "@id": "https://w3id.org/np/RA7lSq6MuK_TIC6JMSHvLtee3lpLoZDOqLJCLXevnrPoU" } ], "https://w3id.org/np/o/ntemplate/wasCreatedFromPubinfoTemplate": [ { "@id": "https://w3id.org/np/RA0J4vUn_dekg-U1kK3AOEt02p9mT2WO03uGxLDec1jLw" } ], "https://w3id.org/np/o/ntemplate/wasCreatedFromTemplate": [ { "@id": "https://w3id.org/np/RAEFAt-QcFK0ZhqfvlsmS10BnzGJA0xwOICZXkO-ai87k" } ] }, { "@id": "https://w3id.org/np/RArXnUQf2dQguqlteWMwKVWxIpnk5xzF4ppAokGkpuOn8/sig", "http://purl.org/nanopub/x/hasAlgorithm": [ { "@value": "RSA" } ], "http://purl.org/nanopub/x/hasPublicKey": [ { "@value": "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCwUtewGCpT5vIfXYE1bmf/Uqu1ojqnWdYxv+ySO80ul8Gu7m8KoyPAwuvaPj0lvPtHrg000qMmkxzKhYknEjq8v7EerxZNYp5B3/3+5ZpuWOYAs78UnQVjbHSmDdmryr4D4VvvNIiUmd0yxci47dTFUj4DvfHnGd6hVe5+goqdcwIDAQAB" } ], "http://purl.org/nanopub/x/hasSignature": [ { "@value": "MenzIwJebvOw7XcISSI2Zxf0H8xibQPoVb+YFca4UhMvLOcqPJJ96H5HadDSzdxUlBGLA9e0pqvCpkZdU+J5F9dKUReqWwn0uh9ih71V+zTIxLH5zwCAweJ9w8pLbQZ5n+legzAb4FjbxxKAwTADlxQyMj6x8Z2crlgk2wnciLA=" } ], "http://purl.org/nanopub/x/hasSignatureTarget": [ { "@id": "https://w3id.org/np/RArXnUQf2dQguqlteWMwKVWxIpnk5xzF4ppAokGkpuOn8" } ], "http://purl.org/nanopub/x/signedBy": [ { "@id": "https://orcid.org/0000-0002-1267-0234" } ] } ] }, { "@id": "https://w3id.org/np/RArXnUQf2dQguqlteWMwKVWxIpnk5xzF4ppAokGkpuOn8/assertion", "@graph": [ { "@id": "https://w3id.org/np/RArXnUQf2dQguqlteWMwKVWxIpnk5xzF4ppAokGkpuOn8/list-preset-assignments", "http://purl.org/dc/terms/description": [ { "@value": "Lists the presets assigned in a given space ref (space IRI + root definition). Pass the ref's root nanopub (root_np); the query resolves the ref via npa:rootNanopub and reads the server-materialised npa:PresetAssignment rows scoped by npa:forSpaceRef from the trust-validated current space-state graph (only admin-authored assignments are materialised, so this is authorisation-scoped). An assignment is identified by the assigned preset's stable KIND (dct:isVersionOf) and the resource, mirroring view displays, which the client dedups by view kind (nanodash issue #607): among the assignments of one preset kind for one resource only the latest by dct:created counts, so assigning another version of the same preset replaces the earlier assignment instead of adding a second, competing row; a version declaring no kind keys on itself, and the preset listed is the version that assignment pinned. The preset is listed only when that latest row is still activated (npa:isActivated true) -- a deactivation is a newer admin-authored row with npa:isActivated false. The version column reports whether the assigned version is still current: version_label is what the cell shows (latest, or an up-arrow plus update available) and version carries the dates behind it as the hover tooltip -- that way round because the renderer displays a literal column's _label companion and puts the principal value in the tooltip. updatePreset holds the version the update action pre-fills. All three are derived from the newest non-invalidated version of the same kind, restricted to versions published by the same agent as the assigned version, so an unrelated agent cannot advertise a version of someone else's preset here. Presets never auto-update -- adopting the newer version stays an explicit, admin-signed act. Columns match the IRI-keyed list-preset-assignments (preset, preset_label, deactivatePreset, added_by, date_added, update_noheader, update_label, updatePreset, np, np_label) so it drives the existing Preset assignments view unchanged. Ref-scoped variant: shows only that one ref's assignments rather than merging all refs claiming the IRI." } ], "http://purl.org/dc/terms/license": [ { "@id": "http://www.apache.org/licenses/LICENSE-2.0" } ], "@type": [ "https://w3id.org/kpxl/grlc/grlc-query" ], "http://www.w3.org/2000/01/rdf-schema#label": [ { "@value": "List preset assignments (ref-scoped)" } ], "https://w3id.org/kpxl/grlc/endpoint": [ { "@id": "https://w3id.org/np/l/nanopub-query-1.1/repo/spaces" } ], "https://w3id.org/kpxl/grlc/sparql": [ { "@value": "prefix rdfs: \nprefix dct: \nprefix np: \nprefix npa: \nprefix npx: \nprefix gen: \n\nselect ?preset (sample(?lbl) as ?preset_label)\n (sample(?detail) as ?version) (sample(?verdict) as ?version_label)\n (str(?preset) as ?deactivatePreset)\n (sample(?user) as ?added_by) (?date as ?date_added)\n (sample(?updateTarget) as ?updatePreset)\n ?np (\"^\" as ?np_label)\nwhere {\n values ?_root_np_multi_iri {}\n graph npa:spacesGraph { ?ref npa:rootNanopub ?_root_np_multi_iri . }\n graph npa:graph { npa:thisRepo npa:hasCurrentSpaceState ?g . }\n graph ?g {\n ?paRef a npa:PresetAssignment ; npa:forSpaceRef ?ref ; npa:ofPreset ?preset ; npa:forResource ?resource ;\n npa:isActivated ?activated ; npa:viaNanopub ?np ; dct:created ?date .\n }\n # The assigned preset version: its label, its stable kind, its author and its date.\n optional {\n ?pnp npx:embeds ?preset ; np:hasAssertion ?pa .\n optional { graph npa:graph { ?pnp npx:signedBy ?presetSigner } }\n optional { graph npa:graph { ?pnp dct:created ?presetDate } }\n graph ?pa {\n optional { ?preset rdfs:label ?lbl }\n optional { ?preset dct:isVersionOf ?presetKindOptional }\n }\n }\n # Assignment identity is (preset KIND, resource) -- as for view displays, where the\n # client dedups by view kind -- so assigning another version of the same preset\n # replaces the earlier assignment instead of adding a second, competing one. A\n # version that declares no kind keys on itself.\n bind(coalesce(?presetKindOptional, ?preset) as ?presetKey)\n filter(?activated = true)\n filter not exists {\n graph ?g { ?pa2 a npa:PresetAssignment ; npa:forSpaceRef ?ref ; npa:ofPreset ?preset2 ;\n npa:forResource ?resource ; npa:viaNanopub ?np2 ; dct:created ?date2 . }\n optional {\n ?pnp2 npx:embeds ?preset2 ; np:hasAssertion ?pa2Assertion .\n graph ?pa2Assertion { ?preset2 dct:isVersionOf ?presetKind2 }\n }\n filter(coalesce(?presetKind2, ?preset2) = ?presetKey)\n filter(?date2 > ?date || (?date2 = ?date && str(?np2) > str(?np)))\n }\n # Newest version of the assigned preset's kind, restricted to versions published by\n # the same agent as the assigned version, so an unrelated agent cannot advertise a\n # version of someone else's preset here (issue #607). Presets never auto-update:\n # this only surfaces the newer version and pre-fills the update action with it.\n optional {\n { select (?versionKind as ?presetKey) (?versionSigner as ?presetSigner)\n (iri(strafter(max(concat(str(?vDate), \">\", str(?vPreset))), \">\")) as ?latestVersion)\n (max(?vDate) as ?latestDate) where {\n graph npa:graph {\n ?vNp npx:hasNanopubType gen:Preset ;\n npa:hasValidSignatureForPublicKeyHash ?vPubkey ;\n dct:created ?vDate ;\n npx:signedBy ?versionSigner ;\n npx:embeds ?vPreset ;\n np:hasAssertion ?vA .\n filter not exists { ?vInv npx:invalidates ?vNp ; npa:hasValidSignatureForPublicKeyHash ?vPubkey . }\n }\n graph ?vA { ?vPreset a gen:Preset ; dct:isVersionOf ?versionKind . }\n } group by ?versionKind ?versionSigner }\n }\n bind(bound(?latestVersion) && ?latestVersion != ?preset && ?latestDate > ?presetDate as ?hasUpdate)\n # See the IRI-keyed twin: for a literal column with an \"x_label\" companion the LABEL\n # is displayed and the principal value becomes the hover tooltip, so the short verdict\n # is the label and the dates are the principal.\n bind(if(?hasUpdate, \"⬆️ update available\", \"latest\") as ?rawVerdict)\n bind(if(?hasUpdate,\n concat(\"Assigned version of \", substr(str(?presetDate), 1, 10),\n \"; version of \", substr(str(?latestDate), 1, 10), \" is newer\"),\n concat(\"Assigned version of \", substr(str(?presetDate), 1, 10))) as ?rawDetail)\n bind(if(bound(?presetDate), ?rawVerdict, \"\") as ?verdict)\n bind(if(bound(?presetDate), ?rawDetail, \"\") as ?detail)\n bind(if(?hasUpdate, str(?latestVersion), \"\") as ?updateTarget)\n optional { graph npa:graph { ?np npx:signedBy ?user } }\n}\ngroup by ?preset ?date ?np\norder by desc(?date)\n" } ] } ] } ]