@ulb-darmstadt/shacl-form 1.10.4 → 2.0.0-rc10

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (62) hide show
  1. package/README.md +6 -13
  2. package/dist/bundle.d.ts +6 -0
  3. package/dist/bundle.js +1163 -0
  4. package/dist/config.d.ts +12 -3
  5. package/dist/constants.d.ts +16 -16
  6. package/dist/constraints.d.ts +2 -2
  7. package/dist/form.d.ts +6 -4
  8. package/dist/index.js +63 -0
  9. package/dist/node-template.d.ts +19 -0
  10. package/dist/node.d.ts +7 -9
  11. package/dist/plugins/assets/plugin-VN3CfgGe.js +1 -0
  12. package/dist/plugins/file-upload.js +1 -0
  13. package/dist/plugins/leaflet.d.ts +8 -2
  14. package/dist/plugins/leaflet.js +5 -708
  15. package/dist/property-template.d.ts +14 -11
  16. package/dist/property.d.ts +5 -4
  17. package/dist/theme.d.ts +2 -0
  18. package/dist/{themes/default.d.ts → theme.default.d.ts} +3 -3
  19. package/package.json +23 -32
  20. package/dist/form-bootstrap.d.ts +0 -5
  21. package/dist/form-bootstrap.js +0 -413
  22. package/dist/form-default.d.ts +0 -5
  23. package/dist/form-default.js +0 -402
  24. package/dist/form-material.d.ts +0 -5
  25. package/dist/form-material.js +0 -722
  26. package/dist/plugins/fixed-list.d.ts +0 -9
  27. package/dist/plugins/map-util.d.ts +0 -5
  28. package/dist/plugins/mapbox.d.ts +0 -19
  29. package/dist/plugins/mapbox.js +0 -2904
  30. package/dist/themes/bootstrap.d.ts +0 -10
  31. package/dist/themes/material.d.ts +0 -15
  32. package/src/config.ts +0 -110
  33. package/src/constants.ts +0 -30
  34. package/src/constraints.ts +0 -149
  35. package/src/exports.ts +0 -7
  36. package/src/form-bootstrap.ts +0 -12
  37. package/src/form-default.ts +0 -12
  38. package/src/form-material.ts +0 -12
  39. package/src/form.ts +0 -319
  40. package/src/globals.d.ts +0 -2
  41. package/src/group.ts +0 -34
  42. package/src/loader.ts +0 -187
  43. package/src/node.ts +0 -192
  44. package/src/plugin.ts +0 -60
  45. package/src/plugins/file-upload.ts +0 -26
  46. package/src/plugins/fixed-list.ts +0 -19
  47. package/src/plugins/leaflet.ts +0 -196
  48. package/src/plugins/map-util.ts +0 -41
  49. package/src/plugins/mapbox.ts +0 -157
  50. package/src/property-template.ts +0 -151
  51. package/src/property.ts +0 -309
  52. package/src/serialize.ts +0 -96
  53. package/src/shacl-engine.d.ts +0 -2
  54. package/src/styles.css +0 -49
  55. package/src/theme.ts +0 -132
  56. package/src/themes/bootstrap.css +0 -6
  57. package/src/themes/bootstrap.ts +0 -44
  58. package/src/themes/default.css +0 -4
  59. package/src/themes/default.ts +0 -258
  60. package/src/themes/material.css +0 -14
  61. package/src/themes/material.ts +0 -253
  62. package/src/util.ts +0 -275
package/dist/config.d.ts CHANGED
@@ -3,6 +3,8 @@ import { Term } from '@rdfjs/types';
3
3
  import { ClassInstanceProvider } from './plugin';
4
4
  import { Loader } from './loader';
5
5
  import { Theme } from './theme';
6
+ import { ShaclNodeTemplate } from './node-template';
7
+ import { ShaclPropertyTemplate } from './property-template';
6
8
  export declare class ElementAttributes {
7
9
  shapes: string | null;
8
10
  shapesUrl: string | null;
@@ -25,6 +27,7 @@ export declare class ElementAttributes {
25
27
  submitButton: string | null;
26
28
  generateNodeShapeReference: string | null;
27
29
  showNodeIds: string | null;
30
+ dense: string;
28
31
  }
29
32
  export declare class Config {
30
33
  attributes: ElementAttributes;
@@ -34,15 +37,21 @@ export declare class Config {
34
37
  editMode: boolean;
35
38
  languages: string[];
36
39
  lists: Record<string, Term[]>;
37
- groups: Array<string>;
38
- theme: Theme;
40
+ groups: string[];
41
+ _theme: Theme;
39
42
  form: HTMLElement;
40
43
  renderedNodes: Set<string>;
41
44
  valuesGraphId: NamedNode | undefined;
45
+ nodeShapes: Record<string, ShaclNodeTemplate>;
46
+ propertyShapes: Record<string, ShaclPropertyTemplate>;
42
47
  private _store;
43
- constructor(theme: Theme, form: HTMLElement);
48
+ validator: any;
49
+ constructor(form: HTMLElement);
50
+ reset(): void;
44
51
  updateAttributes(elem: HTMLElement): void;
45
52
  static dataAttributes(): Array<string>;
53
+ get theme(): Theme;
54
+ set theme(theme: Theme);
46
55
  get store(): Store;
47
56
  set store(store: Store);
48
57
  }
@@ -8,19 +8,19 @@ export declare const PREFIX_OWL = "http://www.w3.org/2002/07/owl#";
8
8
  export declare const PREFIX_OA = "http://www.w3.org/ns/oa#";
9
9
  export declare const PREFIX_DCTERMS = "http://purl.org/dc/terms/";
10
10
  export declare const PREFIX_FOAF = "http://xmlns.com/foaf/0.1/";
11
- export declare const SHAPES_GRAPH: import('n3').NamedNode<"loaded-shapes">;
12
- export declare const DATA_GRAPH: import('n3').NamedNode<"loaded-data">;
13
- export declare const RDF_PREDICATE_TYPE: import('n3').NamedNode<string>;
14
- export declare const DCTERMS_PREDICATE_CONFORMS_TO: import('n3').NamedNode<string>;
15
- export declare const RDFS_PREDICATE_SUBCLASS_OF: import('n3').NamedNode<string>;
16
- export declare const OWL_PREDICATE_IMPORTS: import('n3').NamedNode<string>;
17
- export declare const SKOS_PREDICATE_BROADER: import('n3').NamedNode<string>;
18
- export declare const SKOS_PREDICATE_NARROWER: import('n3').NamedNode<string>;
19
- export declare const SHACL_OBJECT_NODE_SHAPE: import('n3').NamedNode<string>;
20
- export declare const SHACL_OBJECT_IRI: import('n3').NamedNode<string>;
21
- export declare const SHACL_PREDICATE_PROPERTY: import('n3').NamedNode<string>;
22
- export declare const SHACL_PREDICATE_CLASS: import('n3').NamedNode<string>;
23
- export declare const SHACL_PREDICATE_NODE: import('n3').NamedNode<string>;
24
- export declare const SHACL_PREDICATE_TARGET_CLASS: import('n3').NamedNode<string>;
25
- export declare const SHACL_PREDICATE_NODE_KIND: import('n3').NamedNode<string>;
26
- export declare const XSD_DATATYPE_STRING: import('n3').NamedNode<string>;
11
+ export declare const SHAPES_GRAPH: import("n3").NamedNode<"loaded-shapes">;
12
+ export declare const DATA_GRAPH: import("n3").NamedNode<"loaded-data">;
13
+ export declare const RDF_PREDICATE_TYPE: import("n3").NamedNode<string>;
14
+ export declare const DCTERMS_PREDICATE_CONFORMS_TO: import("n3").NamedNode<string>;
15
+ export declare const RDFS_PREDICATE_SUBCLASS_OF: import("n3").NamedNode<string>;
16
+ export declare const OWL_PREDICATE_IMPORTS: import("n3").NamedNode<string>;
17
+ export declare const SKOS_PREDICATE_BROADER: import("n3").NamedNode<string>;
18
+ export declare const SKOS_PREDICATE_NARROWER: import("n3").NamedNode<string>;
19
+ export declare const SHACL_OBJECT_NODE_SHAPE: import("n3").NamedNode<string>;
20
+ export declare const SHACL_OBJECT_IRI: import("n3").NamedNode<string>;
21
+ export declare const SHACL_PREDICATE_PROPERTY: import("n3").NamedNode<string>;
22
+ export declare const SHACL_PREDICATE_CLASS: import("n3").NamedNode<string>;
23
+ export declare const SHACL_PREDICATE_NODE: import("n3").NamedNode<string>;
24
+ export declare const SHACL_PREDICATE_TARGET_CLASS: import("n3").NamedNode<string>;
25
+ export declare const SHACL_PREDICATE_NODE_KIND: import("n3").NamedNode<string>;
26
+ export declare const XSD_DATATYPE_STRING: import("n3").NamedNode<string>;
@@ -1,7 +1,7 @@
1
1
  import { Quad } from 'n3';
2
2
  import { Term } from '@rdfjs/types';
3
- import { ShaclNode } from './node';
4
- import { ShaclProperty } from './property';
3
+ import { ShaclNode } from "./node";
4
+ import { ShaclProperty } from "./property";
5
5
  import { Config } from './config';
6
6
  export declare function createShaclOrConstraint(options: Term[], context: ShaclNode | ShaclProperty, config: Config): HTMLElement;
7
7
  export declare function resolveShaclOrConstraintOnProperty(subjects: Term[], value: Term, config: Config): Quad[];
package/dist/form.d.ts CHANGED
@@ -1,20 +1,22 @@
1
1
  import { ShaclNode } from './node';
2
2
  import { Config } from './config';
3
3
  import { ClassInstanceProvider, Plugin } from './plugin';
4
- import { Store, Quad } from 'n3';
4
+ import { Store } from 'n3';
5
5
  import { Theme } from './theme';
6
+ export * from './exports';
7
+ export declare const initTimeout = 50;
6
8
  export declare class ShaclForm extends HTMLElement {
7
9
  static get observedAttributes(): string[];
8
10
  config: Config;
9
11
  shape: ShaclNode | null;
10
12
  form: HTMLFormElement;
11
13
  initDebounceTimeout: ReturnType<typeof setTimeout> | undefined;
12
- constructor(theme: Theme);
14
+ constructor();
13
15
  connectedCallback(): void;
14
16
  attributeChangedCallback(): void;
15
17
  private initialize;
16
- serialize(format?: string, graph?: Store<import('@rdfjs/types').Quad, Quad, import('@rdfjs/types').Quad, import('@rdfjs/types').Quad>): string;
17
- toRDF(graph?: Store<import('@rdfjs/types').Quad, Quad, import('@rdfjs/types').Quad, import('@rdfjs/types').Quad>): Store;
18
+ serialize(format?: string, graph?: Store<import("@rdfjs/types").Quad, import("n3").Quad, import("@rdfjs/types").Quad, import("@rdfjs/types").Quad>): string;
19
+ toRDF(graph?: Store<import("@rdfjs/types").Quad, import("n3").Quad, import("@rdfjs/types").Quad, import("@rdfjs/types").Quad>): Store;
18
20
  registerPlugin(plugin: Plugin): void;
19
21
  setTheme(theme: Theme): void;
20
22
  setClassInstanceProvider(provider: ClassInstanceProvider): void;
package/dist/index.js ADDED
@@ -0,0 +1,63 @@
1
+ import{DataFactory as f,Literal as C,NamedNode as j,Writer as be,Store as H,StreamParser as me,Quad as ve}from"n3";import{RokitCollapsible as W,RokitSelect as ce,RokitButton as ye,RokitInput as _,RokitTextArea as we}from"@ro-kit/ui-widgets";import{v4 as se}from"uuid";import{RdfXmlParser as Se}from"rdfxml-streaming-parser";import{toRDF as Ee}from"jsonld";import{Validator as ne}from"shacl-engine";const d="http://www.w3.org/ns/shacl#",ie="http://datashapes.org/dash#",E="http://www.w3.org/2001/XMLSchema#",S="http://www.w3.org/1999/02/22-rdf-syntax-ns#",K="http://www.w3.org/2000/01/rdf-schema#",X="http://www.w3.org/2004/02/skos/core#",xe="http://www.w3.org/2002/07/owl#",Ce="http://www.w3.org/ns/oa#",Le="http://purl.org/dc/terms/",Ie="http://xmlns.com/foaf/0.1/",R=f.namedNode("loaded-shapes"),y=f.namedNode("loaded-data"),b=f.namedNode(S+"type"),M=f.namedNode(Le+"conformsTo"),oe=f.namedNode(K+"subClassOf"),J=f.namedNode(xe+"imports"),je=f.namedNode(X+"broader"),Re=f.namedNode(X+"narrower"),P=f.namedNode(d+"NodeShape"),De=f.namedNode(d+"IRI"),B=f.namedNode(d+"property"),Y=f.namedNode(d+"class");f.namedNode(d+"node");const F=f.namedNode(d+"targetClass"),Te=f.namedNode(d+"nodeKind"),$e=f.namedNode(E+"string");function D(s,e,t=d,i){let n="";const o=Oe(s,e,t,i);return o&&(n=o.value),n}function Oe(s,e,t=d,i){let n;const o=t+e;if(i?.length){for(const a of i)for(const r of s)if(r.predicate.value===o){if(r.object.id.endsWith(`@${a}`))return r.object;r.object.id.indexOf("@")<0?n=r.object:n||(n=r.object)}}else for(const a of s)if(a.predicate.value===o)return a.object;return n}function Ae(s){s.querySelector(".editor")?.focus()}function $(s,e){return D(s,"prefLabel",X,e)||D(s,"label",K,e)||D(s,"name",Ie,e)}function de(s,e,t){const i=[];for(const n of s)i.push({value:n,label:$(e.getQuads(n,null,null,null),t),children:[]});return i}function U(s,e){for(const t in e)s=s.replace(e[t],"");return s}function ue(s,e,t,i,n=new Set){for(const o of e.owlImports)n.has(o.id)||(n.add(o.id),i.push(...t.getSubjects(b,s,o)));e.parent&&ue(s,e.parent,t,i,n)}function Z(s,e){if(e.in){const t=e.config.lists[e.in];return de(t?.length?t:[],e.config.store,e.config.languages)}else{const t=e.config.store.getSubjects(b,s,R);t.push(...e.config.store.getSubjects(b,s,y)),ue(s,e,e.config.store,t);const i=new Map,n=new Map;for(const a of t)i.set(a.id,{value:a,label:$(e.config.store.getQuads(a,null,null,null),e.config.languages),children:[]});for(const a of t){for(const r of e.config.store.getObjects(a,je,null))i.has(r.id)&&n.set(a.id,r.id);for(const r of e.config.store.getObjects(a,Re,null))i.has(r.id)&&n.set(r.id,a.id);for(const r of e.config.store.getObjects(a,oe,null))i.has(r.id)&&n.set(a.id,r.id)}for(const[a,r]of n.entries())i.get(r)?.children?.push(i.get(a));const o=[];for(const[a,r]of i.entries())n.has(a)||o.push(r);for(const a of e.config.store.getSubjects(oe,s,null))o.push(...Z(a,e));return o}}function z(s){let e;try{e=new URL(s)}catch{return!1}return e.protocol==="http:"||e.protocol==="https:"}function ae(s,e,t){if(e===void 0)return t;if(t===void 0)return e;const i=s.indexOf(e.language);if(i<0)return t;const n=s.indexOf(t.language);return n<0||n>i?e:t}function Pe(s,{remove:e=!1,ignoreErrors:t=!1}={}){const i={},n=t?(()=>!0):((r,l)=>{throw new Error(`${r.value} ${l}`)}),o=s.getQuads(null,S+"rest",S+"nil",null),a=e?[...o]:[];return o.forEach(r=>{const l=[];let c=!1,u,h;const g=r.graph;let p=r.subject;for(;p&&!c;){const w=s.getQuads(null,null,p,null),x=s.getQuads(p,null,null,null).filter(v=>!v.predicate.equals(b));let m,O=null,te=null,A=null;for(let v=0;v<x.length&&!c;v++)m=x[v],m.graph.equals(g)?u?c=n(p,"has non-list arcs out"):m.predicate.value===S+"first"?O?c=n(p,"has multiple rdf:first arcs"):a.push(O=m):m.predicate.value===S+"rest"?te?c=n(p,"has multiple rdf:rest arcs"):a.push(te=m):w.length?c=n(p,"can't be subject and object"):(u=m,h="subject"):c=n(p,"not confined to single graph");for(let v=0;v<w.length&&!c;++v)m=w[v],u?c=n(p,"can't have coreferences"):m.predicate.value===S+"rest"?A?c=n(p,"has incoming rdf:rest arcs"):A=m:(u=m,h="object");O?l.unshift(O.object):c=n(p,"has no list head"),p=A&&A.subject}c?e=!1:u&&(i[u[h].value]=l)}),e&&s.removeQuads(a),i}const Ne={[`${d}node`]:(s,e)=>{s.extendedShapes.add(s.config.nodeShapes[e.value]||new I(e,s.config,s))},[`${d}and`]:(s,e)=>{for(const t of s.config.lists[e.value])s.extendedShapes.add(s.config.nodeShapes[t.value]||new I(t,s.config,s))},[`${d}property`]:(s,e)=>{const t=s.config.propertyShapes[e.value]||new G(e,s);if(t.path){let i=s.properties[t.path];i||(i=[],s.properties[t.path]=i),i.push(t)}},[`${d}nodeKind`]:(s,e)=>{s.nodeKind=e},[`${d}targetClass`]:(s,e)=>{s.targetClass=e},[`${d}or`]:(s,e)=>{s.or=s.config.lists[e.value]},[`${d}xone`]:(s,e)=>{s.xone=s.config.lists[e.value]},[J.id]:(s,e)=>{s.owlImports.add(e)}};class I{constructor(e,t,i){this.extendedShapes=new Set,this.properties={},this.owlImports=new Set,this.id=e,this.config=t,this.parent=i,t.nodeShapes[e.value]=this,ke(this,t.store.getQuads(e,null,null,null))}}function ke(s,e){for(const t of e)Ne[t.predicate.id]?.call(s,s,t.object);return s}function Fe(s){const e={};he(s,e);for(const[t,i]of Object.entries(e))if(i.length>1){let n=!1,o=!0;for(const a of i)n=n||a.maxCount===1,o=o&&a.qualifiedValueShape===void 0;if(n&&o){const a=i[i.length-1];for(let r=i.length-2;r>=0;r--){const l=i[r];delete l.parent.properties[t],qe(a,l)}}}}function he(s,e,t=new WeakSet){if(!t.has(s.id)){t.add(s.id);for(const[i,n]of Object.entries(s.properties)){let o=e[i];o||(o=[],e[i]=o),o.push(...n)}for(const i of s.extendedShapes)he(i,e,t)}}const _e={[`${d}name`]:(s,e)=>{const t=e;s.name=ae(s.config.languages,s.name,t)},[`${d}description`]:(s,e)=>{const t=e;s.description=ae(s.config.languages,s.description,t)},[`${d}path`]:(s,e)=>{s.path=e.value},[`${d}node`]:(s,e)=>{s.node=e},[`${d}group`]:(s,e)=>{s.group=e.id},[`${d}datatype`]:(s,e)=>{s.datatype=e},[`${d}nodeKind`]:(s,e)=>{s.nodeKind=e},[`${d}minCount`]:(s,e)=>{s.minCount=parseInt(e.value)},[`${d}maxCount`]:(s,e)=>{s.maxCount=parseInt(e.value)},[`${d}minLength`]:(s,e)=>{s.minLength=parseInt(e.value)},[`${d}maxLength`]:(s,e)=>{s.maxLength=parseInt(e.value)},[`${d}minInclusive`]:(s,e)=>{s.minInclusive=parseInt(e.value)},[`${d}maxInclusive`]:(s,e)=>{s.maxInclusive=parseInt(e.value)},[`${d}minExclusive`]:(s,e)=>{s.minExclusive=parseInt(e.value)},[`${d}maxExclusive`]:(s,e)=>{s.maxExclusive=parseInt(e.value)},[`${d}pattern`]:(s,e)=>{s.pattern=e.value},[`${d}order`]:(s,e)=>{s.order=parseInt(e.value)},[`${ie}singleLine`]:(s,e)=>{s.singleLine=e.value==="true"},[`${ie}readonly`]:(s,e)=>{s.readonly=e.value==="true"},[`${Ce}styleClass`]:(s,e)=>{s.cssClass=e.value},[`${d}and`]:(s,e)=>{s.and=e.value},[`${d}in`]:(s,e)=>{s.in=e.value},[`${d}languageIn`]:(s,e)=>{s.languageIn=s.config.lists[e.value],s.datatype=f.namedNode(S+"langString")},[`${d}defaultValue`]:(s,e)=>{s.defaultValue=e},[`${d}hasValue`]:(s,e)=>{s.hasValue=e},[`${d}qualifiedValueShape`]:(s,e)=>{s.qualifiedValueShape=e,s.nodeShapes.add(s.config.nodeShapes[e.value]||new I(e,s.config))},[`${d}qualifiedMinCount`]:(s,e)=>{s.minCount=parseInt(e.value)},[`${d}qualifiedMaxCount`]:(s,e)=>{s.maxCount=parseInt(e.value)},[J.id]:(s,e)=>{s.owlImports.add(e)},[Y.id]:(s,e)=>{s.class=e;const t=s.config.store.getSubjects(F,e,null);t.length>0&&(s.node=t[0])},[`${d}or`]:(s,e)=>{const t=s.config.lists[e.value];t?.length?s.or=t:console.error("list for sh:or not found:",e.value,"existing lists:",s.config.lists)},[`${d}xone`]:(s,e)=>{const t=s.config.lists[e.value];t?.length?s.xone=t:console.error("list for sh:xone not found:",e.value,"existing lists:",s.config.lists)}};class G{constructor(e,t){this.label="",this.nodeShapes=new Set,this.owlImports=new Set,this.id=e,this.parent=t,this.config=t.config,this.config.propertyShapes[e.value]=this,ee(this,this.config.store.getQuads(e,null,null,null))}}function fe(s){const e=Object.assign({},s);return e.nodeShapes=new Set(s.nodeShapes),e.owlImports=new Set(s.owlImports),s.languageIn&&(e.languageIn=[...s.languageIn]),s.or&&(e.or=[...s.or]),s.xone&&(e.xone=[...s.xone]),e}function ee(s,e){for(const t of e)_e[t.predicate.id]?.call(s,s,t.object);if(s.label=s.name?.value||$(e,s.config.languages),!s.label&&!s.and&&(s.label=s.path?U(s.path,s.config.prefixes):"unknown"),s.node&&s.nodeShapes.add(s.config.nodeShapes[s.node.value]||new I(s.node,s.config)),s.and){const t=s.config.lists[s.and];if(t?.length)for(const i of t)s.nodeShapes.add(s.config.nodeShapes[i.value]||new I(i,s.config))}return s}function qe(s,e){const t=e,i=s;for(const n in e)n!=="parent"&&n!=="config"&&n!=="id"&&t[n]!==void 0&&t[n]!==""&&(Array.isArray(t[n])?i[n].push(...t[n]):t[n]instanceof Set&&t[n].size?i[n]=new Set([...i[n],...t[n]]):i[n]=t[n])}function pe(s,e,t){const i=document.createElement("div");i.classList.add("shacl-or-constraint");const n=[];if(e instanceof L){const o=[];let a=!1;s.length&&(a=t.store.countQuads(s[0],B,null,null)>0);for(let c=0;c<s.length;c++)if(a){const u=t.store.getObjects(s[c],B,null),h=[];let g="";for(const p of u){const w=t.propertyShapes[p.value]||new G(p,e.template),x=new k(w,e);h.push(x),g+=(g.length>1?" / ":"")+x.template.label}o.push(h),n.push({label:g,value:c.toString()})}else{const u=s[c],h=t.propertyShapes[u.value]||new G(u,e.template),g=new k(h,e);o.push([g]),n.push({label:g.template.label,value:c.toString()})}const r=t.theme.createListEditor("Please choose",null,!1,n),l=r.querySelector(".editor");l.onchange=()=>{if(l.value){const c=o[parseInt(l.value)];let u;c.length&&(u=c[0],i.replaceWith(c[0]));for(let h=1;h<c.length;h++)u.after(c[h]),u=c[h]}},i.appendChild(r)}else{const o=[];for(let l=0;l<s.length;l++){const c=t.store.getQuads(s[l],null,null,null);c.length&&(o.push(c),n.push({label:$(c,t.languages)||U(c[0].predicate.value,t.prefixes)+" = "+U(c[0].object.value,t.prefixes),value:l.toString()}))}const a=t.theme.createListEditor(e.template.label+"?",null,!1,n,e.template),r=a.querySelector(".editor");r.onchange=()=>{if(r.value){const l=ee(fe(e.template),o[parseInt(r.value)]);i.replaceWith(N(l,void 0,!0))}},i.appendChild(a)}return i}function Qe(s,e,t){if(e instanceof C){const i=e.datatype;for(const n of s){const o=t.store.getQuads(n,null,null,null);for(const a of o)if(a.predicate.value===`${d}datatype`&&a.object.equals(i))return o}}else{const i=t.store.getObjects(e,b,null);for(const n of s){const o=t.store.getQuads(n,null,null,null);for(const a of o)if(i.length>0){if(a.predicate.value===`${d}node`){for(const r of i)if(t.store.getQuads(a.object,F,r,null).length>0)return o}if(a.predicate.equals(Y)){for(const r of i)if(a.object.equals(r))return o}}else if(a.predicate.equals(Te)&&a.object.equals(De))return o}}return console.error("couldn't resolve sh:or/sh:xone on property for value",e),[]}function Ve(s,e,t){for(const i of s){let n=!1;const o=t.store.getObjects(i,B,null);for(const a of o){const r=t.store.getObjects(a,`${d}path`,null);for(const l of r)if(n=t.store.countQuads(e,l,null,null)>0,n)break}if(n)return o}return console.error("couldn't resolve sh:or/sh:xone on node for value",e),[]}const Me=`form { display:block; --label-width: 8em; --caret-size: 10px; }
2
+ form.mode-edit { padding-left: 1em; }
3
+ form, form * { box-sizing: border-box; }
4
+ shacl-node, .collapsible::part(content) { display: flex; flex-direction: column; width: 100%; position: relative; }
5
+ shacl-node .remove-button { margin-left: 4px; margin-top: 1px; }
6
+ shacl-node .add-button { color: #555; background-color: transparent; margin: 4px 24px 0 0; border: 0; }
7
+ shacl-node .add-button:hover { color:#222; }
8
+ shacl-node .add-button:focus { box-shadow: none; }
9
+ shacl-node h1 { font-size: 16px; border-bottom: 1px solid #AAA; margin-top: 4px; color: #555; }
10
+ shacl-property:not(:has(>.collapsible)), shacl-property>.collapsible::part(content) { display: flex; flex-direction: column; align-items: end; position: relative; }
11
+ shacl-property:not(.may-add) > .add-button, shacl-property:not(.may-add) > .collapsible > .add-button { display: none; }
12
+ shacl-property:not(.may-remove) > .property-instance > .remove-button:not(.persistent) { visibility: hidden; }
13
+ shacl-property:not(.may-remove) > .collapsible > .property-instance > .remove-button:not(.persistent) { visibility: hidden; }
14
+ shacl-property:not(.may-remove) > .shacl-or-constraint > .remove-button:not(.persistent) { visibility: hidden; }
15
+ .mode-view .shacl-group:not(:has(shacl-property)) { display: none; }
16
+ .property-instance, .shacl-or-constraint { display: flex; align-items: flex-start; padding: 4px 0; width: 100%; position: relative; }
17
+ .shacl-or-constraint > div { display: flex; flex-grow: 1; align-items: flex-start; }
18
+ .shacl-or-constraint label { display: inline-block; word-break: break-word; width: var(--label-width); line-height: 1em; padding-top: 0.15em; padding-right: 1em; flex-shrink: 0; position: relative; }
19
+ .property-instance label[title] { cursor: help; text-decoration: underline dashed #AAA; }
20
+ .property-instance.linked label:after, label.linked:after { content: '\\1F517'; font-size: 0.6em; padding-left: 6px; }
21
+ .mode-edit .property-instance label.required::before { color: red; content: '\\2736'; font-size: 0.6rem; position: absolute; left: -1.4em; top: 0.15rem; }
22
+ .property-instance.valid::before { content: ''; position: absolute; left: calc(var(--label-width) - 1em); top:0.5em; width: 0.9em; height: 0.9em; background: url('data:image/svg+xml;utf8,<svg viewBox="0 0 1024 1024" fill="green" version="1.1" xmlns="http://www.w3.org/2000/svg"><path d="M866.133333 258.133333L362.666667 761.6l-204.8-204.8L98.133333 618.666667 362.666667 881.066667l563.2-563.2z"/></svg>'); }
23
+ .editor:not([type='checkbox']) { flex-grow: 1; }
24
+ textarea.editor { resize: vertical; }
25
+ .lang-chooser { border: 0; background-color: #e9e9ed; padding: 2px 4px; align-self: flex-start; }
26
+ .validation-error { position: absolute; left: calc(var(--label-width) - 1em); color: red; cursor: help; }
27
+ .validation-error::before { content: '\\26a0' }
28
+ .validation-error.node { left: -1em; }
29
+ .invalid > .editor { border-color: red !important; }
30
+ .ml-0 { margin-left: 0 !important; }
31
+ .pr-0 { padding-right: 0 !important; }
32
+ .mode-view .property-instance:not(:first-child) > label { visibility: hidden; }
33
+ .mode-view .property-instance label { width: var(--label-width); }
34
+
35
+ .d-flex { display: flex; }
36
+ .lang { opacity: 0.65; font-size: 0.6em; }
37
+ a, a:visited { color: inherit; }
38
+
39
+ .fadeIn, .fadeOut { animation: fadeIn 0.2s ease-out; }
40
+ .fadeOut { animation-direction: reverse; animation-timing-function: ease-out;}
41
+ @keyframes fadeIn {
42
+ 0% { opacity: 0; transform: scaleY(0.8); }
43
+ 100% { opacity: 1; transform: scaleY(1); }
44
+ }
45
+ .collapsible::part(label) { font-weight: 600; }
46
+ .collapsible > .property-instance:nth-child(even) { background-color: #F8F8F8; }
47
+ .collapsible > .property-instance > shacl-node > h1 { display: none; }
48
+ .ref-link { cursor: pointer; }
49
+ .ref-link:hover { text-decoration: underline; }
50
+ .node-id-display { color: #999; font-size: 11px; }`;class Be{constructor(e){this.dense=!0;let t=Me;e&&(t+=`
51
+ `+e),this.stylesheet=new CSSStyleSheet,this.stylesheet.replaceSync(t)}apply(e){}setDense(e){this.dense=e}createViewer(e,t,i){const n=document.createElement("div"),o=document.createElement("label");o.innerHTML=e+":",i.description&&o.setAttribute("title",i.description.value),n.appendChild(o);let a=t.value,r=null;if(t instanceof j){const c=i.config.store.getQuads(a,null,null,null);if(c.length){const u=$(c,i.config.languages);u&&(a=u)}}else t instanceof C&&(t.language?(r=document.createElement("span"),r.classList.add("lang"),r.innerText=`@${t.language}`):t.datatype.value===`${E}date`?a=new Date(Date.parse(t.value)).toDateString():t.datatype.value===`${E}dateTime`&&(a=new Date(Date.parse(t.value)).toLocaleString()));let l;return z(t.value)?(l=document.createElement("a"),l.setAttribute("href",t.value)):l=document.createElement("div"),l.classList.add("d-flex"),l.innerText=a,r&&l.appendChild(r),n.appendChild(l),n}}function Ue(s,e,t){if(t){const i=s.minCount!==void 0&&s.minCount>0;if(s.class&&!s.hasValue)return s.config.theme.createListEditor(s.label,e,i,Z(s.class,s),s);if(s.in){const n=s.config.lists[s.in];if(n?.length){const o=de(n,s.config.store,s.config.languages);return s.config.theme.createListEditor(s.label,e,i,o,s)}else console.error("list not found:",s.in,"existing lists:",s.config.lists)}if(s.datatype?.value===`${S}langString`||s.languageIn?.length)return s.config.theme.createLangStringEditor(s.label,e,i,s);switch(s.datatype?.value.replace(E,"")){case"integer":case"float":case"double":case"decimal":return s.config.theme.createNumberEditor(s.label,e,i,s);case"date":case"dateTime":return s.config.theme.createDateEditor(s.label,e,i,s);case"boolean":return s.config.theme.createBooleanEditor(s.label,e,i,s);case"base64Binary":return s.config.theme.createFileEditor(s.label,e,i,s)}return s.config.theme.createTextEditor(s.label,e,i,s)}else{if(e)return s.config.theme.createViewer(s.label,e,s);const i=document.createElement("div");return i.innerHTML="No value",i}}function ze(s,e,t){if(e==="application/ld+json")return Ge(s);{const i=new be({format:e,prefixes:t});i.addQuads(s);let n="";return i.end((o,a)=>{o&&console.error(o),n=a}),n}}function Ge(s){const e=[];for(const t of s){const i={"@id":t.subject.id};if(t.predicate===b)i["@type"]=t.object.id;else{let n=t.object.value;t.object instanceof C?t.object.language?n={"@language":t.object.language,"@value":t.object.value}:t.object.datatype&&t.object.datatype.value!==`${E}#string`&&(n={"@type":t.object.datatype.value,"@value":t.object.value}):n={"@id":t.object.id},i[t.predicate.value]=n}e.push(i)}return JSON.stringify(e)}function He(s){let e=s.shaclDatatype,t=s.value;if(t){if(t.startsWith("<")&&t.endsWith(">")&&t.indexOf(":")>-1)return f.namedNode(t.substring(1,t.length-1));if(s.dataset.class||s.dataset.nodeKind===d+"IRI")return f.namedNode(t);if(s.dataset.link)return JSON.parse(s.dataset.link);if(s.dataset.lang?e=s.dataset.lang:s.type==="number"?t=parseFloat(t):s.type==="file"&&s.binaryData?t=s.binaryData:s.type==="datetime-local"&&(t=new Date(t).toISOString().slice(0,19)),(!e||e instanceof j&&$e.equals(e))&&typeof t=="string"){let i=t.split("^^");i.length===2&&i[0].startsWith('"')&&i[0].endsWith('"')&&i[1].split(":").length===2?(t=i[0].substring(1,i[0].length-1),e=f.namedNode(i[1])):(i=t.split("@"),i.length===2&&i[0].startsWith('"')&&i[0].endsWith('"')?(t=i[0].substring(1,i[0].length-1),e=i[1]):t.startsWith('"')&&t.endsWith('"')&&(t=t.substring(1,t.length-1)))}return f.literal(t,e)}else if((s.type==="checkbox"||s.getAttribute("type")==="checkbox")&&(s.checked||parseInt(s.dataset.minCount||"0")>0))return f.literal(s.checked?"true":"false",e)}const T={};function We(s){s.predicate===void 0&&s.datatype===void 0?console.warn('not registering plugin because it does neither define "predicate" nor "datatype"',s):T[`${s.predicate}^${s.datatype}`]=s}function Ke(){return Object.entries(T).map(s=>s[1])}function Xe(s,e){let t=T[`${s}^${e}`];return t||(t=T[`${s}^undefined`],t)?t:T[`undefined^${e}`]}class ct{constructor(e,t){this.predicate=e.predicate,this.datatype=e.datatype,t&&(this.stylesheet=new CSSStyleSheet,this.stylesheet.replaceSync(t))}createViewer(e,t){return e.config.theme.createViewer(e.label,t,e)}}class k extends HTMLElement{constructor(e,t,i){if(super(),this.template=e,this.parent=t,this.container=this,this.template.nodeShapes.size&&this.template.config.attributes.collapse!==null&&(this.template.maxCount===void 0||this.template.maxCount>1)){const n=new W;n.classList.add("collapsible","shacl-group"),n.open=e.config.attributes.collapse==="open",n.label=this.template.label,this.container=n,this.appendChild(this.container)}this.template.order!==void 0&&(this.style.order=`${this.template.order}`),this.template.cssClass&&this.classList.add(this.template.cssClass),e.config.editMode&&!t.linked&&(this.addButton=this.createAddButton(),this.container.appendChild(this.addButton),this.addEventListener("change",()=>{this.updateControls()})),(async()=>{if(e.path){let n=[];i&&(t.linked?n=e.config.store.getQuads(i,e.path,null,null):n=e.config.store.getQuads(i,e.path,null,y),n=await this.filterValidValues(n,i));let o=!1;for(const a of n)this.addPropertyInstance(a.object),e.hasValue&&a.object.equals(e.hasValue)&&(o=!0);e.config.editMode&&(e.hasValue&&!o&&!t.linked&&this.addPropertyInstance(e.hasValue),this.updateControls())}})()}addPropertyInstance(e){let t;if(this.template.or?.length||this.template.xone?.length){const i=this.template.or?.length?this.template.or:this.template.xone;let n=!1;if(e){const o=Qe(i,e,this.template.config);if(o.length){const a=ee(fe(this.template),o);t=N(a,e,!0),n=!0}}n||(t=pe(i,this,this.template.config),ge(t,"",this.template.config.theme.dense))}else{let i=!1;if(e&&!(e instanceof C)){const n=this.getRdfClassToLinkOrCreate();n&&this.template.config.store.countQuads(e,b,n,y)===0&&(i=!0)}t=N(this.template,e,void 0,i||this.parent.linked)}return this.addButton?this.container.insertBefore(t,this.addButton):this.container.appendChild(t),t}updateControls(){let e=this.instanceCount();e===0&&(this.template.nodeShapes.size===0||this.template.minCount!==void 0&&this.template.minCount>0)&&(this.addPropertyInstance(),e=this.instanceCount());let t;this.template.minCount!==void 0?t=e>this.template.minCount:t=this.template.nodeShapes.size>0||e>1;const i=this.template.maxCount===void 0||e<this.template.maxCount;this.classList.toggle("may-remove",t),this.classList.toggle("may-add",i)}instanceCount(){return this.querySelectorAll(":scope > .property-instance, :scope > .shacl-or-constraint, :scope > shacl-node, :scope > .collapsible > .property-instance").length}toRDF(e,t){const i=f.namedNode(this.template.path);for(const n of this.querySelectorAll(":scope > .property-instance, :scope > .collapsible > .property-instance"))if(n.firstChild instanceof L){const o=n.firstChild.toRDF(e);e.addQuad(t,i,o,this.template.config.valuesGraphId)}else for(const o of n.querySelectorAll(":scope > .editor")){const a=He(o);a&&e.addQuad(t,i,a,this.template.config.valuesGraphId)}}getRdfClassToLinkOrCreate(){if(this.template.class&&this.template.nodeShapes.size)return this.template.class;for(const e of this.template.nodeShapes)if(e.targetClass)return e.targetClass}async filterValidValues(e,t){const i=await this.template.config.validator.validate({dataset:this.template.config.store,terms:[t]},[{terms:[this.template.id]}]),n=[];for(const o of i.results)o.value?.ptrs?.length&&n.push(o.value.ptrs[0]._term.id);return e.filter(o=>n.indexOf(o.object.id)===-1)}createAddButton(){const e=new ce;e.dense=this.template.config.theme.dense,e.label="+ "+this.template.label,e.title="Add "+this.template.label,e.autoGrowLabelWidth=!0,e.classList.add("add-button");let t=[],i=this.getRdfClassToLinkOrCreate();if(i&&(t=Z(i,this.template)),t.length===0)e.emptyMessage="",e.inputMinWidth=0,e.addEventListener("click",n=>{e.blur();const o=this.addPropertyInstance();o.classList.add("fadeIn"),this.updateControls(),setTimeout(()=>{Ae(o),o.classList.remove("fadeIn")},200)});else{const n=document.createElement("ul"),o=document.createElement("li");o.innerHTML="&#xFF0B; Create new "+this.template.label+"...",o.dataset.value="new",o.classList.add("large"),n.appendChild(o);const a=document.createElement("li");a.classList.add("divider"),n.appendChild(a);const r=document.createElement("li");r.classList.add("header"),r.innerText="Or link existing:",n.appendChild(r);for(const l of t){const c=document.createElement("li"),u=typeof l.value=="string"?l.value:l.value.value;c.innerText=l.label?l.label:u,c.dataset.value=JSON.stringify(l.value),n.appendChild(c)}e.appendChild(n),e.collapsibleWidth="250px",e.collapsibleOrientationLeft="",e.addEventListener("change",()=>{if(e.value==="new")this.addPropertyInstance();else{const l=JSON.parse(e.value);this.container.insertBefore(N(this.template,l,!0,!0),e)}e.value=""})}return e}}function N(s,e,t=!1,i=!1){let n;if(s.nodeShapes.size){n=document.createElement("div"),n.classList.add("property-instance");for(const o of s.nodeShapes)n.appendChild(new L(o,e,s.nodeKind,s.label,i))}else{const o=Xe(s.path,s.datatype?.value);o?s.config.editMode&&!i?n=o.createEditor(s,e):n=o.createViewer(s,e):n=Ue(s,e||null,s.config.editMode&&!i),n.classList.add("property-instance"),i&&n.classList.add("linked")}return s.config.editMode&&ge(n,s.label,s.config.theme.dense,t),n.dataset.path=s.path,n}function ge(s,e,t,i=!1){const n=new ye;n.classList.add("remove-button","clear"),n.title="Remove "+e,n.dense=t,n.icon=!0,n.addEventListener("click",o=>{s.classList.remove("fadeIn"),s.classList.add("fadeOut"),setTimeout(()=>{const a=s.parentElement;s.remove(),a?.dispatchEvent(new Event("change",{bubbles:!0,cancelable:!0}))},200)}),i&&n.classList.add("persistent"),s.appendChild(n)}window.customElements.define("shacl-property",k);function Je(s,e){let t=s;const i=e.store.getQuads(s,null,null,null),n=D(i,"label",K,e.languages);n&&(t=n);let o;if(e.attributes.collapse!==null)o=new W,o.classList.add("collapsible"),o.open=e.attributes.collapse==="open",o.label=t;else{o=document.createElement("div");const r=document.createElement("h1");r.innerText=t,o.appendChild(r)}o.dataset.subject=s,o.classList.add("shacl-group");const a=D(i,"order");return a&&(o.style.order=a),o}class L extends HTMLElement{constructor(e,t,i,n,o){super(),this.template=e,this.linked=o||!1;let a=t;a||(!i&&e.nodeKind&&(i=e.nodeKind),i===void 0&&e.config.attributes.valuesNamespace||i?.value===`${d}IRI`?a=f.namedNode(e.config.attributes.valuesNamespace+se()):a=f.blankNode(se())),this.nodeId=a;const r=JSON.stringify([e.id,t]);if(t&&e.config.renderedNodes.has(r)){n=n||"Link";const l=document.createElement("label");l.innerText=n,l.classList.add("linked"),this.appendChild(l);const c=document.createElement("a");let u=t.termType==="BlankNode"?"_:"+t.value:t.value;c.innerText=u,c.classList.add("ref-link"),c.onclick=()=>{this.template.config.form.querySelector(`shacl-node[data-node-id='${u}']`)?.scrollIntoView()},this.appendChild(c),this.style.flexDirection="row"}else{if(t&&e.config.renderedNodes.add(r),this.dataset.nodeId=this.nodeId.id,this.template.config.attributes.showNodeIds!==null){const l=document.createElement("div");l.innerText=`id: ${this.nodeId.id}`,l.classList.add("node-id-display"),this.appendChild(l)}for(const l of this.template.extendedShapes)this.prepend(new L(l,t));this.template.or?.length&&this.tryResolve(this.template.or,t,e.config),this.template.xone?.length&&this.tryResolve(this.template.xone,t,e.config);for(const[l,c]of Object.entries(this.template.properties))for(const u of c)this.addPropertyInstance(u,t);if(n){const l=document.createElement("h1");l.innerText=n,this.prepend(l)}}}toRDF(e,t,i=null){if(t||(t=this.nodeId),!this.linked){for(const n of this.querySelectorAll(":scope > shacl-node, :scope > .shacl-group > shacl-node, :scope > shacl-property, :scope > .shacl-group > shacl-property"))n.toRDF(e,t);this.template.targetClass&&e.addQuad(t,b,this.template.targetClass,this.template.config.valuesGraphId),i&&e.addQuad(t,f.namedNode(i),this.template.id,this.template.config.valuesGraphId)}return t}addPropertyInstance(e,t){let i=this;if(e.group)if(e.config.groups.indexOf(e.group)>-1){let o=this.querySelector(`:scope > .shacl-group[data-subject='${e.group}']`);o||(o=Je(e.group,e.config),this.appendChild(o)),i=o}else console.warn("ignoring unknown group reference",e.group,"existing groups:",e.config.groups);const n=new k(e,this,t);setTimeout(()=>{(e.config.editMode||n.instanceCount()>0)&&i.appendChild(n)})}tryResolve(e,t,i){let n=!1;if(t){const o=Ve(e,t,i);if(o.length){for(const a of o)this.addPropertyInstance(i.propertyShapes[a.value],t);n=!0}}n||this.appendChild(pe(e,this,i))}}window.customElements.define("shacl-node",L);const q={},Q={};class Ye{constructor(e){this.loadedExternalUrls=[],this.loadedClasses=[],this.config=e}async loadGraphs(){this.loadedExternalUrls=[],this.loadedClasses=[];const e=[],t=new H;if(e.push(this.importRDF(this.config.attributes.shapes?this.config.attributes.shapes:this.config.attributes.shapesUrl?this.fetchRDF(this.config.attributes.shapesUrl):"",t,R)),e.push(this.importRDF(this.config.attributes.values?this.config.attributes.values:this.config.attributes.valuesUrl?this.fetchRDF(this.config.attributes.valuesUrl):"",t,y)),await Promise.all(e),t.countQuads(null,null,null,R)===0&&this.config.attributes.valuesSubject){const i=[...t.getObjects(this.config.attributes.valuesSubject,M,y)],n=[];for(const o of i){const a=this.toURL(o.value);a&&this.loadedExternalUrls.indexOf(a)<0&&(this.loadedExternalUrls.push(a),n.push(this.importRDF(this.fetchRDF(a),t,R)))}try{await Promise.allSettled(n)}catch(o){console.warn(o)}}this.config.store=t}async importRDF(e,t,i){const n=async o=>{const a=[];await new Promise((r,l)=>{const c=re(o)==="xml"?new Se:new me;c.on("data",u=>{if(t.add(new ve(u.subject,u.predicate,u.object,i)),this.config.attributes.ignoreOwlImports===null&&J.equals(u.predicate)){const h=this.toURL(u.object.value);h&&this.loadedExternalUrls.indexOf(h)<0&&(this.loadedExternalUrls.push(h),a.push(this.importRDF(this.fetchRDF(h),t,f.namedNode(h))))}if(this.config.classInstanceProvider&&(Y.equals(u.predicate)||F.equals(u.predicate))){const h=u.object.value;if(this.loadedClasses.indexOf(h)<0){let g;h in Q?g=Q[h]:(g=this.config.classInstanceProvider(h),Q[h]=g),this.loadedClasses.push(h),a.push(this.importRDF(g,t,i))}}}).on("error",u=>{console.warn("failed parsing graph",i,u.message),l(u)}).on("prefix",(u,h)=>{u&&(this.config.prefixes[u]=h)}).on("end",()=>{r(null)}),c.write(o),c.end()});try{await Promise.allSettled(a)}catch(r){console.warn(r)}};if(e instanceof Promise&&(e=await e),e){if(re(e)==="json")try{e=await Ee(JSON.parse(e),{format:"application/n-quads"})}catch(o){console.error(o)}await n(e)}}toURL(e){if(z(e))return e;if(this.config.prefixes){const t=e.split(":");if(t.length===2){const i=this.config.prefixes[t[0]];if(i&&(e=e.replace(`${t[0]}:`,i),z(e)))return e}}return null}async fetchRDF(e){if(e in q)return q[e];let t=e;this.config.attributes.proxy&&(t=this.config.attributes.proxy+encodeURIComponent(e));const i=fetch(t,{headers:{Accept:"text/turtle, application/trig, application/n-triples, application/n-quads, text/n3, application/ld+json"}}).then(n=>n.text());return q[e]=i,i}}function re(s){return/^\s*\{/.test(s)?"json":/^\s*<\?xml/.test(s)?"xml":"ttl"}const Ze=`
52
+ .editor:not([type='checkbox']) { border: 1px solid #DDD; }
53
+ .property-instance label { display: inline-flex; word-break: break-word; line-height: 1em; padding-top: 0.15em; padding-right: 1em; flex-shrink: 0; position: relative; }
54
+ .property-instance:not(:first-child) > label:not(.persistent) { visibility: hidden; max-height: 0; }
55
+ .mode-edit .property-instance label { width: var(--label-width); }
56
+ `;class et extends Be{constructor(e){super(e||Ze),this.idCtr=0}createDefaultTemplate(e,t,i,n,o){n.id=`e${this.idCtr++}`,n.classList.add("editor"),o?.datatype?n.shaclDatatype=o.datatype:t instanceof C&&(n.shaclDatatype=t.datatype),o?.minCount!==void 0&&(n.dataset.minCount=String(o.minCount)),o?.class&&(n.dataset.class=o.class.value),o?.nodeKind?n.dataset.nodeKind=o.nodeKind.value:t instanceof j&&(n.dataset.nodeKind=d+"IRI"),(o?.hasValue&&t||o?.readonly)&&(n.disabled=!0),n.value=t?.value||o?.defaultValue?.value||"";const a=document.createElement("label");a.htmlFor=n.id,a.innerText=e,o?.description&&a.setAttribute("title",o.description.value);const r=o?.description?o.description.value:o?.pattern?o.pattern:null;r&&n.setAttribute("placeholder",r),i&&(n.setAttribute("required","true"),a.classList.add("required"));const l=document.createElement("div");return l.appendChild(a),l.appendChild(n),l}createDateEditor(e,t,i,n){const o=new _;n.datatype?.value===E+"dateTime"?(o.type="datetime-local",o.setAttribute("step","1")):o.type="date",o.clearable=!0,o.dense=this.dense,o.classList.add("pr-0");const a=this.createDefaultTemplate(e,null,i,o,n);if(t)try{let r=new Date(t.value).toISOString();n.datatype?.value===E+"dateTime"?r=r.slice(0,19):r=r.slice(0,10),o.value=r}catch(r){console.error(r,t)}return a}createTextEditor(e,t,i,n){let o;return n.singleLine===!1?(o=new we,o.resize="auto"):o=new _,o.dense=this.dense,n.pattern&&(o.pattern=n.pattern),n.minLength&&(o.minLength=n.minLength),n.maxLength&&(o.maxLength=n.maxLength),this.createDefaultTemplate(e,t,i,o,n)}createLangStringEditor(e,t,i,n){const o=this.createTextEditor(e,t,i,n),a=o.querySelector(":scope .editor");let r;if(n.languageIn?.length){r=document.createElement("select");for(const l of n.languageIn){const c=document.createElement("option");c.innerText=l.value,r.appendChild(c)}}else r=document.createElement("input"),r.maxLength=5,r.size=5,r.placeholder="lang?";return r.title="Language of the text",r.classList.add("lang-chooser"),r.slot="suffix",r.addEventListener("change",l=>{l.stopPropagation(),a&&(a.dataset.lang=r.value,a.dispatchEvent(new Event("change",{bubbles:!0})))}),t instanceof C&&(r.value=t.language),a.dataset.lang=r.value,a.appendChild(r),o}createBooleanEditor(e,t,i,n){const o=document.createElement("input");o.type="checkbox",o.classList.add("ml-0");const a=this.createDefaultTemplate(e,null,i,o,n);return o.removeAttribute("required"),a.querySelector(":scope label")?.classList.remove("required"),t instanceof C&&(o.checked=t.value==="true"),a}createFileEditor(e,t,i,n){const o=document.createElement("input");return o.type="file",o.addEventListener("change",a=>{if(o.files?.length){a.stopPropagation();const r=new FileReader;r.readAsDataURL(o.files[0]),r.onload=()=>{o.binaryData=btoa(r.result),o.parentElement?.dispatchEvent(new Event("change",{bubbles:!0}))}}else o.binaryData=void 0}),this.createDefaultTemplate(e,t,i,o,n)}createNumberEditor(e,t,i,n){const o=new _;o.type="number",o.clearable=!0,o.dense=this.dense,o.classList.add("pr-0");const a=n.minInclusive!==void 0?n.minInclusive:n.minExclusive!==void 0?n.minExclusive+1:void 0,r=n.maxInclusive!==void 0?n.maxInclusive:n.maxExclusive!==void 0?n.maxExclusive-1:void 0;return a!==void 0&&(o.min=String(a)),r!==void 0&&(o.max=String(r)),n.datatype?.value!==E+"integer"&&(o.step="0.1"),this.createDefaultTemplate(e,t,i,o,n)}createListEditor(e,t,i,n,o){const a=new ce;a.clearable=!0,a.dense=this.dense;const r=this.createDefaultTemplate(e,null,i,a,o),l=document.createElement("ul");let c=!0;const u=(h,g)=>{const p=document.createElement("li");if(typeof h.value=="string"?(p.dataset.value=h.value,p.innerText=h.label?h.label:h.value):(p.dataset.value=h.value.id,h.value instanceof j&&(p.dataset.value="<"+p.dataset.value+">"),p.innerText=h.label?h.label:h.value.value),g.appendChild(p),h.children?.length){c=!1;const w=document.createElement("ul");p.appendChild(w);for(const x of h.children)u(x,w)}};for(const h of n)u(h,l);return c||(a.collapse=!0),a.appendChild(l),t&&(a.value=t.id,t instanceof j&&(a.value="<"+a.value+">")),r}createButton(e,t){const i=document.createElement("rokit-button");return i.innerHTML=e,i}}class V{constructor(){this.shapes=null,this.shapesUrl=null,this.shapeSubject=null,this.values=null,this.valuesUrl=null,this.valueSubject=null,this.valuesSubject=null,this.valuesNamespace="",this.valuesGraph=null,this.view=null,this.language=null,this.loading="Loading…",this.proxy=null,this.ignoreOwlImports=null,this.collapse=null,this.submitButton=null,this.generateNodeShapeReference=null,this.showNodeIds=null,this.dense="true"}}class le{constructor(e){this.attributes=new V,this.loader=new Ye(this),this.prefixes={},this.editMode=!0,this.lists={},this.groups=[],this.renderedNodes=new Set,this.nodeShapes={},this.propertyShapes={},this._store=new H,this.validator=new ne(this._store,{details:!0,factory:f}),this.form=e,this.theme=new et,this.languages=[...new Set(navigator.languages.flatMap(t=>t.length>2?[t.toLocaleLowerCase(),t.substring(0,2)]:t)),""]}reset(){this.lists={},this.groups=[],this.renderedNodes.clear(),this.nodeShapes={},this.propertyShapes={}}updateAttributes(e){const t=new V;if(Object.keys(t).forEach(i=>{const n=e.dataset[i];n!==void 0&&(t[i]=n)}),this.editMode=t.view===null,this.theme.setDense(t.dense==="true"),this.attributes=t,this.attributes.valueSubject&&!this.attributes.valuesSubject&&(this.attributes.valuesSubject=this.attributes.valueSubject),t.language){const i=this.languages.indexOf(t.language);i>-1&&this.languages.splice(i,1),this.languages.unshift(t.language)}t.valuesGraph&&(this.valuesGraphId=f.namedNode(t.valuesGraph))}static dataAttributes(){const e=new V;return Object.keys(e).map(t=>(t=t.replace(/[A-Z]/g,i=>"-"+i.toLowerCase()),"data-"+t))}get theme(){return this._theme}set theme(e){this._theme=e,e.setDense(this.attributes.dense==="true")}get store(){return this._store}set store(e){this._store=e,this.lists=Pe(e,{ignoreErrors:!0}),this.groups=[],e.forSubjects(t=>{this.groups.push(t.id)},b,`${d}PropertyGroup`,null),this.validator=new ne(e,{details:!0,factory:f})}}const tt=50;class st extends HTMLElement{constructor(){super(),this.shape=null,this.attachShadow({mode:"open"}),this.form=document.createElement("form"),this.config=new le(this.form),this.form.addEventListener("change",e=>{e.stopPropagation(),this.config.editMode&&this.validate(!0).then(t=>{this.dispatchEvent(new CustomEvent("change",{bubbles:!0,cancelable:!1,composed:!0,detail:{valid:t.conforms,report:t}}))}).catch(t=>{console.warn(t)})})}static get observedAttributes(){return le.dataAttributes()}connectedCallback(){this.shadowRoot.prepend(this.form)}attributeChangedCallback(){this.config.updateAttributes(this),this.initialize()}initialize(){clearTimeout(this.initDebounceTimeout),this.setAttribute("loading",""),this.form.replaceChildren(document.createTextNode(this.config.attributes.loading)),this.initDebounceTimeout=setTimeout(async()=>{try{this.config.reset(),await this.config.loader.loadGraphs(),this.form.replaceChildren();const e=this.findRootShaclShapeSubject();if(e){this.form.classList.forEach(n=>{this.form.classList.remove(n)}),this.form.classList.toggle("mode-edit",this.config.editMode),this.form.classList.toggle("mode-view",!this.config.editMode),this.config.theme.apply(this.form);const t=[this.config.theme.stylesheet];for(const n of Ke())n.stylesheet&&t.push(n.stylesheet);this.shadowRoot.adoptedStyleSheets=t;const i=new I(e,this.config);for(const[n,o]of Object.entries(this.config.nodeShapes))Fe(o);if(this.shape=new L(i,this.config.attributes.valuesSubject?f.namedNode(this.config.attributes.valuesSubject):void 0),this.form.appendChild(this.shape),this.config.editMode){if(this.config.attributes.submitButton!==null){const n=this.config.theme.createButton(this.config.attributes.submitButton||"Submit",!0);n.addEventListener("click",o=>{o.preventDefault(),this.form.reportValidity()&&this.validate().then(a=>{if(a?.conforms)this.dispatchEvent(new Event("submit",{bubbles:!0,cancelable:!0}));else{let r=this.form.querySelector(":scope .invalid > .editor");r?r.focus():this.form.querySelector(":scope .invalid")?.scrollIntoView()}})}),this.form.appendChild(n)}setTimeout(()=>{this.config.attributes.valuesSubject&&this.removeFromDataGraph(f.namedNode(this.config.attributes.valuesSubject)),this.validate(!0)})}}else if(this.config.store.countQuads(null,null,null,R)>0)throw new Error("shacl root node shape not found")}catch(e){console.error(e);const t=document.createElement("div");t.innerText=String(e),this.form.replaceChildren(t)}this.removeAttribute("loading")},tt)}serialize(e="text/turtle",t=this.toRDF()){const i=t.getQuads(null,null,null,null);return ze(i,e,this.config.prefixes)}toRDF(e=new H){return this.shape?.toRDF(e,void 0,this.config.attributes.generateNodeShapeReference),e}registerPlugin(e){We(e),this.initialize()}setTheme(e){this.config.theme=e,this.initialize()}setClassInstanceProvider(e){this.config.classInstanceProvider=e,this.initialize()}async validate(e=!1){for(const t of this.form.querySelectorAll(":scope .validation-error"))t.remove();for(const t of this.form.querySelectorAll(":scope .property-instance"))t.classList.remove("invalid"),t.querySelector(":scope > .editor")?.value?t.classList.add("valid"):t.classList.remove("valid");if(this.config.store.deleteGraph(this.config.valuesGraphId||""),!this.shape)return{conforms:!0};this.shape.toRDF(this.config.store,void 0,this.config.attributes.generateNodeShapeReference);try{const t=await this.config.validator.validate({dataset:this.config.store,terms:[this.shape.nodeId]},[{terms:[this.shape.template.id]}]);for(const i of t.results)if(i.focusNode?.ptrs?.length)for(const n of i.focusNode.ptrs){const o=n._term;if(i.path?.length){const a=i.path[0].predicates[0];let r=this.form.querySelectorAll(`
57
+ :scope shacl-node[data-node-id='${o.id}'] > shacl-property > .property-instance[data-path='${a.id}'] > .editor,
58
+ :scope shacl-node[data-node-id='${o.id}'] > shacl-property > .shacl-group > .property-instance[data-path='${a.id}'] > .editor,
59
+ :scope shacl-node[data-node-id='${o.id}'] > .shacl-group > shacl-property > .property-instance[data-path='${a.id}'] > .editor,
60
+ :scope shacl-node[data-node-id='${o.id}'] > .shacl-group > shacl-property > .shacl-group > .property-instance[data-path='${a.id}'] > .editor`);r.length===0&&(r=this.form.querySelectorAll(`
61
+ :scope [data-node-id='${o.id}'] > shacl-property > .property-instance[data-path='${a.id}'],
62
+ :scope [data-node-id='${o.id}'] > shacl-property > .shacl-group > .property-instance[data-path='${a.id}']`));for(const l of r)if(l.classList.contains("editor")){if(!e||l.value){let c=l.parentElement;c.classList.add("invalid"),c.classList.remove("valid"),c.appendChild(this.createValidationErrorDisplay(i));do c instanceof W&&(c.open=!0),c=c.parentElement;while(c)}}else e||(l.classList.add("invalid"),l.classList.remove("valid"),l.appendChild(this.createValidationErrorDisplay(i,"node")))}else e||this.form.querySelector(`:scope [data-node-id='${o.id}']`)?.prepend(this.createValidationErrorDisplay(i,"node"))}return t}catch(t){return console.error(t),!1}}createValidationErrorDisplay(e,t){const i=document.createElement("span");if(i.classList.add("validation-error"),t&&i.classList.add(t),e)if(e.message?.length>0)for(const n of e.message)i.title+=n.value+`
63
+ `;else i.title=e.sourceConstraintComponent?.value;return i}findRootShaclShapeSubject(){let e=null;if(this.config.attributes.shapeSubject){if(e=f.namedNode(this.config.attributes.shapeSubject),this.config.store.getQuads(e,b,P,null).length===0){console.warn(`shapes graph does not contain requested root shape ${this.config.attributes.shapeSubject}`);return}}else if(this.config.attributes.valuesSubject&&this.config.store.countQuads(null,null,null,y)>0){const t=f.namedNode(this.config.attributes.valuesSubject),i=[...this.config.store.getQuads(t,b,null,y),...this.config.store.getQuads(t,M,null,y)];if(i.length===0){console.warn(`value subject '${this.config.attributes.valuesSubject}' has neither ${b.id} nor ${M.id} statement`);return}for(const n of i)if(this.config.store.getQuads(n.object,b,P,null).length>0){e=n.object;break}if(!e){const n=this.config.store.getQuads(null,F,i[0].object,null);if(n.length===0){console.error(`value subject '${this.config.attributes.valuesSubject}' has no shacl shape definition in the shapes graph`);return}if(n.length>1&&console.warn(`value subject '${this.config.attributes.valuesSubject}' has multiple shacl shape definitions in the shapes graph, choosing the first found (${n[0].subject})`),this.config.store.getQuads(n[0].subject,b,P,null).length===0){console.error(`value subject '${this.config.attributes.valuesSubject}' references a shape which is not a NodeShape (${n[0].subject})`);return}e=n[0].subject}}else{const t=this.config.store.getQuads(null,b,P,null);if(t.length==0){console.warn("shapes graph does not contain any root shapes");return}t.length>1&&(console.warn("shapes graph contains",t.length,"root shapes. choosing first found which is",t[0].subject.value),console.info('hint: set the shape to use with attribute "data-shape-subject"')),e=t[0].subject}return e}removeFromDataGraph(e){this.config.attributes.valuesSubject;for(const t of this.config.store.getQuads(e,null,null,y))this.config.store.delete(t),(t.object.termType==="NamedNode"||t.object.termType==="BlankNode")&&this.removeFromDataGraph(t.object)}}window.customElements.define("shacl-form",st);export{le as Config,Ye as Loader,ct as Plugin,st as ShaclForm,G as ShaclPropertyTemplate,Be as Theme,$ as findLabel,tt as initTimeout,We as registerPlugin};
@@ -0,0 +1,19 @@
1
+ import type { NamedNode, Quad } from 'n3';
2
+ import { Term } from '@rdfjs/types';
3
+ import { Config } from './config';
4
+ import { ShaclPropertyTemplate } from './property-template';
5
+ export declare class ShaclNodeTemplate {
6
+ id: Term;
7
+ parent?: ShaclNodeTemplate;
8
+ nodeKind?: NamedNode;
9
+ targetClass?: NamedNode;
10
+ or?: Term[];
11
+ xone?: Term[];
12
+ extendedShapes: Set<ShaclNodeTemplate>;
13
+ properties: Record<string, ShaclPropertyTemplate[]>;
14
+ owlImports: Set<NamedNode>;
15
+ config: Config;
16
+ constructor(id: Term, config: Config, parent?: ShaclNodeTemplate);
17
+ }
18
+ export declare function mergeQuads(template: ShaclNodeTemplate, quads: Quad[]): ShaclNodeTemplate;
19
+ export declare function mergeOverriddenProperties(node: ShaclNodeTemplate): void;
package/dist/node.d.ts CHANGED
@@ -1,16 +1,14 @@
1
1
  import { BlankNode, NamedNode, Store } from 'n3';
2
2
  import { Term } from '@rdfjs/types';
3
3
  import { Config } from './config';
4
+ import { ShaclNodeTemplate } from './node-template';
5
+ import { ShaclPropertyTemplate } from './property-template';
4
6
  export declare class ShaclNode extends HTMLElement {
5
- parent: ShaclNode | undefined;
6
- shaclSubject: NamedNode;
7
7
  nodeId: NamedNode | BlankNode;
8
- targetClass: NamedNode | undefined;
9
- owlImports: NamedNode[];
10
- config: Config;
8
+ template: ShaclNodeTemplate;
11
9
  linked: boolean;
12
- constructor(shaclSubject: NamedNode, config: Config, valueSubject: NamedNode | BlankNode | undefined, parent?: ShaclNode, nodeKind?: NamedNode, label?: string, linked?: boolean);
13
- toRDF(graph: Store, subject?: NamedNode | BlankNode): (NamedNode | BlankNode);
14
- addPropertyInstance(shaclSubject: Term, config: Config, valueSubject: NamedNode | BlankNode | undefined): void;
15
- tryResolve(subject: Term, valueSubject: NamedNode | BlankNode | undefined, config: Config): void;
10
+ constructor(template: ShaclNodeTemplate, valueSubject: NamedNode | BlankNode | undefined, nodeKind?: NamedNode, label?: string, linked?: boolean);
11
+ toRDF(graph: Store, subject?: NamedNode | BlankNode, generateNodeShapeReference?: string | null): (NamedNode | BlankNode);
12
+ addPropertyInstance(template: ShaclPropertyTemplate, valueSubject: NamedNode | BlankNode | undefined): void;
13
+ tryResolve(options: Term[], valueSubject: NamedNode | BlankNode | undefined, config: Config): void;
16
14
  }
@@ -0,0 +1 @@
1
+ class a{constructor(e,t){this.predicate=e.predicate,this.datatype=e.datatype,t&&(this.stylesheet=new CSSStyleSheet,this.stylesheet.replaceSync(t))}createViewer(e,t){return e.config.theme.createViewer(e.label,t,e)}}export{a as P};
@@ -0,0 +1 @@
1
+ import{P as o}from"./assets/plugin-VN3CfgGe.js";class c extends o{constructor(e,t,i){super(e),this.onChange=t,this.fileType=i}createEditor(e){const t=e.minCount!==void 0&&e.minCount>0,i=e.config.theme.createFileEditor(e.label,null,t,e);return i.addEventListener("change",n=>{n.stopPropagation(),this.onChange(n)}),this.fileType&&i.querySelector('input[type="file"]')?.setAttribute("accept",this.fileType),i}}export{c as FileUploadPlugin};
@@ -1,9 +1,11 @@
1
+ import * as L from 'leaflet';
2
+ import 'leaflet-editable/src/Leaflet.Editable.js';
3
+ import 'leaflet.fullscreen/Control.FullScreen.js';
1
4
  import { Term } from '@rdfjs/types';
5
+ import { Point, Polygon } from 'geojson';
2
6
  import { Plugin, PluginOptions } from '../plugin';
3
7
  import { Editor } from '../theme';
4
8
  import { ShaclPropertyTemplate } from '../property-template';
5
- import { Geometry } from './map-util';
6
- import * as L from 'leaflet';
7
9
  export declare class LeafletPlugin extends Plugin {
8
10
  map: L.Map | undefined;
9
11
  currentEditor: Editor | undefined;
@@ -16,3 +18,7 @@ export declare class LeafletPlugin extends Plugin {
16
18
  drawAndZoomToGeometry(geometry: Geometry | undefined, map: L.Map): void;
17
19
  saveChanges(): void;
18
20
  }
21
+ export type Geometry = Point | Polygon;
22
+ export declare const worldBounds: [number, number][];
23
+ export declare function wktToGeometry(wkt: string): Geometry | undefined;
24
+ export declare function geometryToWkt(geometry: Geometry): string;