rdflib 2.3.0-1c284ee8 → 2.3.0-344dec99
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.
- package/README.md +30 -0
- package/dist/rdflib.min.js +1 -1
- package/dist/rdflib.min.js.map +1 -1
- package/esm/serialize.js +4 -2
- package/esm/serializer.js +41 -10
- package/lib/serialize.js +4 -2
- package/lib/serializer.d.ts +7 -0
- package/lib/serializer.js +41 -10
- package/package.json +2 -1
- package/src/serialize.ts +4 -2
- package/src/serializer.js +41 -10
package/esm/serialize.js
CHANGED
|
@@ -40,7 +40,8 @@ contentType, callback, options) {
|
|
|
40
40
|
return executeCallback(null, documentString);
|
|
41
41
|
case TurtleContentType:
|
|
42
42
|
case TurtleLegacyContentType:
|
|
43
|
-
|
|
43
|
+
// Suppress = for sameAs and => for implies; preserve any user-specified flags (e.g., 'o')
|
|
44
|
+
sz.setFlags('si' + (opts.flags ? ' ' + opts.flags : ''));
|
|
44
45
|
documentString = sz.statementsToN3(newSts);
|
|
45
46
|
return executeCallback(null, documentString);
|
|
46
47
|
case NTriplesContentType:
|
|
@@ -48,7 +49,8 @@ contentType, callback, options) {
|
|
|
48
49
|
documentString = sz.statementsToNTriples(newSts);
|
|
49
50
|
return executeCallback(null, documentString);
|
|
50
51
|
case JSONLDContentType:
|
|
51
|
-
|
|
52
|
+
// turtle + dr (means no default, no relative prefix); preserve user flags
|
|
53
|
+
sz.setFlags('si dr' + (opts.flags ? ' ' + opts.flags : ''));
|
|
52
54
|
documentString = sz.statementsToJsonld(newSts); // convert via turtle
|
|
53
55
|
return executeCallback(null, documentString);
|
|
54
56
|
case NQuadsContentType:
|
package/esm/serializer.js
CHANGED
|
@@ -20,7 +20,7 @@ export default function createSerializer(store) {
|
|
|
20
20
|
;
|
|
21
21
|
export class Serializer {
|
|
22
22
|
constructor(store) {
|
|
23
|
-
_defineProperty(this, "_notQNameChars", '\t\r\n !"#$%&\'()
|
|
23
|
+
_defineProperty(this, "_notQNameChars", '\t\r\n !"#$%&\'()*,+/;<=>?@[\\]^`{|}~');
|
|
24
24
|
// issue#228
|
|
25
25
|
_defineProperty(this, "_notNameChars", this._notQNameChars + ':');
|
|
26
26
|
// stringToN3: String escaping for N3
|
|
@@ -54,6 +54,13 @@ export class Serializer {
|
|
|
54
54
|
this.base = base;
|
|
55
55
|
return this;
|
|
56
56
|
}
|
|
57
|
+
|
|
58
|
+
/**
|
|
59
|
+
* Set serializer behavior flags. Letters can be combined with spaces.
|
|
60
|
+
* Examples: 'si', 'deinprstux', 'si dr', 'o'.
|
|
61
|
+
* Notable flags:
|
|
62
|
+
* - 'o': do not abbreviate to a prefixed name when the local part contains a dot
|
|
63
|
+
*/
|
|
57
64
|
setFlags(flags) {
|
|
58
65
|
this.flags = flags || '';
|
|
59
66
|
return this;
|
|
@@ -244,6 +251,28 @@ export class Serializer {
|
|
|
244
251
|
toN3(f) {
|
|
245
252
|
return this.statementsToN3(f.statements);
|
|
246
253
|
}
|
|
254
|
+
// Validate if a string is a valid PN_LOCAL per Turtle 1.1 spec
|
|
255
|
+
// Allows dots inside the local name but not as trailing character
|
|
256
|
+
// Also allows empty local names (for URIs ending in / or #)
|
|
257
|
+
isValidPNLocal(local) {
|
|
258
|
+
// Empty local name is valid (e.g., ex: for http://example.com/)
|
|
259
|
+
if (local.length === 0) return true;
|
|
260
|
+
|
|
261
|
+
// Cannot end with a dot
|
|
262
|
+
if (local[local.length - 1] === '.') return false;
|
|
263
|
+
|
|
264
|
+
// Check each character (allow dots mid-string)
|
|
265
|
+
for (var i = 0; i < local.length; i++) {
|
|
266
|
+
var ch = local[i];
|
|
267
|
+
// Dot is allowed unless it's the last character (checked above)
|
|
268
|
+
if (ch === '.') continue;
|
|
269
|
+
// Other characters must not be in the blacklist
|
|
270
|
+
if (this._notNameChars.indexOf(ch) >= 0) {
|
|
271
|
+
return false;
|
|
272
|
+
}
|
|
273
|
+
}
|
|
274
|
+
return true;
|
|
275
|
+
}
|
|
247
276
|
explicitURI(uri) {
|
|
248
277
|
if (this.flags.indexOf('r') < 0 && this.base) {
|
|
249
278
|
uri = Uri.refTo(this.base, uri);
|
|
@@ -606,13 +635,17 @@ export class Serializer {
|
|
|
606
635
|
if (j >= 0 && this.flags.indexOf('p') < 0 && (
|
|
607
636
|
// Can split at namespace but only if http[s]: URI or file: or ws[s] (why not others?)
|
|
608
637
|
uri.indexOf('http') === 0 || uri.indexOf('ws') === 0 || uri.indexOf('file') === 0)) {
|
|
609
|
-
var
|
|
610
|
-
|
|
611
|
-
|
|
612
|
-
|
|
613
|
-
|
|
614
|
-
|
|
615
|
-
|
|
638
|
+
var localid = uri.slice(j + 1);
|
|
639
|
+
var namesp = uri.slice(0, j + 1);
|
|
640
|
+
// Don't split if namespace is just the protocol (e.g., https://)
|
|
641
|
+
// A valid namespace should have content after the protocol
|
|
642
|
+
var minNamespaceLength = uri.indexOf('://') + 4; // e.g., "http://x" minimum
|
|
643
|
+
// Also don't split if namespace is the base directory (would serialize as relative URI)
|
|
644
|
+
var baseDir = this.base ? this.base.slice(0, Math.max(this.base.lastIndexOf('/'), this.base.lastIndexOf('#')) + 1) : null;
|
|
645
|
+
var namespaceIsBaseDir = baseDir && namesp === baseDir;
|
|
646
|
+
// If flag 'o' is present, forbid dots in local part when abbreviating
|
|
647
|
+
var forbidDotLocal = this.flags.indexOf('o') >= 0 && localid.indexOf('.') >= 0;
|
|
648
|
+
var canSplit = !namespaceIsBaseDir && !forbidDotLocal && namesp.length > minNamespaceLength && this.isValidPNLocal(localid);
|
|
616
649
|
/*
|
|
617
650
|
if (uri.slice(0, j + 1) === this.base + '#') { // base-relative
|
|
618
651
|
if (canSplit) {
|
|
@@ -623,8 +656,6 @@ export class Serializer {
|
|
|
623
656
|
}
|
|
624
657
|
*/
|
|
625
658
|
if (canSplit) {
|
|
626
|
-
var localid = uri.slice(j + 1);
|
|
627
|
-
var namesp = uri.slice(0, j + 1);
|
|
628
659
|
if (this.defaultNamespace && this.defaultNamespace === namesp && this.flags.indexOf('d') < 0) {
|
|
629
660
|
// d -> suppress default
|
|
630
661
|
if (this.flags.indexOf('k') >= 0 && this.keyords.indexOf(localid) < 0) {
|
package/lib/serialize.js
CHANGED
|
@@ -47,7 +47,8 @@ contentType, callback, options) {
|
|
|
47
47
|
return executeCallback(null, documentString);
|
|
48
48
|
case _types.TurtleContentType:
|
|
49
49
|
case _types.TurtleLegacyContentType:
|
|
50
|
-
|
|
50
|
+
// Suppress = for sameAs and => for implies; preserve any user-specified flags (e.g., 'o')
|
|
51
|
+
sz.setFlags('si' + (opts.flags ? ' ' + opts.flags : ''));
|
|
51
52
|
documentString = sz.statementsToN3(newSts);
|
|
52
53
|
return executeCallback(null, documentString);
|
|
53
54
|
case _types.NTriplesContentType:
|
|
@@ -55,7 +56,8 @@ contentType, callback, options) {
|
|
|
55
56
|
documentString = sz.statementsToNTriples(newSts);
|
|
56
57
|
return executeCallback(null, documentString);
|
|
57
58
|
case _types.JSONLDContentType:
|
|
58
|
-
|
|
59
|
+
// turtle + dr (means no default, no relative prefix); preserve user flags
|
|
60
|
+
sz.setFlags('si dr' + (opts.flags ? ' ' + opts.flags : ''));
|
|
59
61
|
documentString = sz.statementsToJsonld(newSts); // convert via turtle
|
|
60
62
|
return executeCallback(null, documentString);
|
|
61
63
|
case _types.NQuadsContentType:
|
package/lib/serializer.d.ts
CHANGED
|
@@ -22,6 +22,12 @@ export class Serializer {
|
|
|
22
22
|
string: NamedNode;
|
|
23
23
|
};
|
|
24
24
|
setBase(base: any): Serializer;
|
|
25
|
+
/**
|
|
26
|
+
* Set serializer behavior flags. Letters can be combined with spaces.
|
|
27
|
+
* Examples: 'si', 'deinprstux', 'si dr', 'o'.
|
|
28
|
+
* Notable flags:
|
|
29
|
+
* - 'o': do not abbreviate to a prefixed name when the local part contains a dot
|
|
30
|
+
*/
|
|
25
31
|
setFlags(flags: any): Serializer;
|
|
26
32
|
toStr(x: any): any;
|
|
27
33
|
fromStr(s: any): any;
|
|
@@ -51,6 +57,7 @@ export class Serializer {
|
|
|
51
57
|
toN3(f: any): string;
|
|
52
58
|
_notQNameChars: string;
|
|
53
59
|
_notNameChars: string;
|
|
60
|
+
isValidPNLocal(local: any): boolean;
|
|
54
61
|
explicitURI(uri: any): string;
|
|
55
62
|
statementsToNTriples(sts: any): string;
|
|
56
63
|
statementsToN3(sts: any): string;
|
package/lib/serializer.js
CHANGED
|
@@ -30,7 +30,7 @@ function createSerializer(store) {
|
|
|
30
30
|
;
|
|
31
31
|
class Serializer {
|
|
32
32
|
constructor(store) {
|
|
33
|
-
(0, _defineProperty2.default)(this, "_notQNameChars", '\t\r\n !"#$%&\'()
|
|
33
|
+
(0, _defineProperty2.default)(this, "_notQNameChars", '\t\r\n !"#$%&\'()*,+/;<=>?@[\\]^`{|}~');
|
|
34
34
|
// issue#228
|
|
35
35
|
(0, _defineProperty2.default)(this, "_notNameChars", this._notQNameChars + ':');
|
|
36
36
|
// stringToN3: String escaping for N3
|
|
@@ -64,6 +64,13 @@ class Serializer {
|
|
|
64
64
|
this.base = base;
|
|
65
65
|
return this;
|
|
66
66
|
}
|
|
67
|
+
|
|
68
|
+
/**
|
|
69
|
+
* Set serializer behavior flags. Letters can be combined with spaces.
|
|
70
|
+
* Examples: 'si', 'deinprstux', 'si dr', 'o'.
|
|
71
|
+
* Notable flags:
|
|
72
|
+
* - 'o': do not abbreviate to a prefixed name when the local part contains a dot
|
|
73
|
+
*/
|
|
67
74
|
setFlags(flags) {
|
|
68
75
|
this.flags = flags || '';
|
|
69
76
|
return this;
|
|
@@ -254,6 +261,28 @@ class Serializer {
|
|
|
254
261
|
toN3(f) {
|
|
255
262
|
return this.statementsToN3(f.statements);
|
|
256
263
|
}
|
|
264
|
+
// Validate if a string is a valid PN_LOCAL per Turtle 1.1 spec
|
|
265
|
+
// Allows dots inside the local name but not as trailing character
|
|
266
|
+
// Also allows empty local names (for URIs ending in / or #)
|
|
267
|
+
isValidPNLocal(local) {
|
|
268
|
+
// Empty local name is valid (e.g., ex: for http://example.com/)
|
|
269
|
+
if (local.length === 0) return true;
|
|
270
|
+
|
|
271
|
+
// Cannot end with a dot
|
|
272
|
+
if (local[local.length - 1] === '.') return false;
|
|
273
|
+
|
|
274
|
+
// Check each character (allow dots mid-string)
|
|
275
|
+
for (var i = 0; i < local.length; i++) {
|
|
276
|
+
var ch = local[i];
|
|
277
|
+
// Dot is allowed unless it's the last character (checked above)
|
|
278
|
+
if (ch === '.') continue;
|
|
279
|
+
// Other characters must not be in the blacklist
|
|
280
|
+
if (this._notNameChars.indexOf(ch) >= 0) {
|
|
281
|
+
return false;
|
|
282
|
+
}
|
|
283
|
+
}
|
|
284
|
+
return true;
|
|
285
|
+
}
|
|
257
286
|
explicitURI(uri) {
|
|
258
287
|
if (this.flags.indexOf('r') < 0 && this.base) {
|
|
259
288
|
uri = Uri.refTo(this.base, uri);
|
|
@@ -616,13 +645,17 @@ class Serializer {
|
|
|
616
645
|
if (j >= 0 && this.flags.indexOf('p') < 0 && (
|
|
617
646
|
// Can split at namespace but only if http[s]: URI or file: or ws[s] (why not others?)
|
|
618
647
|
uri.indexOf('http') === 0 || uri.indexOf('ws') === 0 || uri.indexOf('file') === 0)) {
|
|
619
|
-
var
|
|
620
|
-
|
|
621
|
-
|
|
622
|
-
|
|
623
|
-
|
|
624
|
-
|
|
625
|
-
|
|
648
|
+
var localid = uri.slice(j + 1);
|
|
649
|
+
var namesp = uri.slice(0, j + 1);
|
|
650
|
+
// Don't split if namespace is just the protocol (e.g., https://)
|
|
651
|
+
// A valid namespace should have content after the protocol
|
|
652
|
+
var minNamespaceLength = uri.indexOf('://') + 4; // e.g., "http://x" minimum
|
|
653
|
+
// Also don't split if namespace is the base directory (would serialize as relative URI)
|
|
654
|
+
var baseDir = this.base ? this.base.slice(0, Math.max(this.base.lastIndexOf('/'), this.base.lastIndexOf('#')) + 1) : null;
|
|
655
|
+
var namespaceIsBaseDir = baseDir && namesp === baseDir;
|
|
656
|
+
// If flag 'o' is present, forbid dots in local part when abbreviating
|
|
657
|
+
var forbidDotLocal = this.flags.indexOf('o') >= 0 && localid.indexOf('.') >= 0;
|
|
658
|
+
var canSplit = !namespaceIsBaseDir && !forbidDotLocal && namesp.length > minNamespaceLength && this.isValidPNLocal(localid);
|
|
626
659
|
/*
|
|
627
660
|
if (uri.slice(0, j + 1) === this.base + '#') { // base-relative
|
|
628
661
|
if (canSplit) {
|
|
@@ -633,8 +666,6 @@ class Serializer {
|
|
|
633
666
|
}
|
|
634
667
|
*/
|
|
635
668
|
if (canSplit) {
|
|
636
|
-
var localid = uri.slice(j + 1);
|
|
637
|
-
var namesp = uri.slice(0, j + 1);
|
|
638
669
|
if (this.defaultNamespace && this.defaultNamespace === namesp && this.flags.indexOf('d') < 0) {
|
|
639
670
|
// d -> suppress default
|
|
640
671
|
if (this.flags.indexOf('k') >= 0 && this.keyords.indexOf(localid) < 0) {
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "rdflib",
|
|
3
3
|
"description": "an RDF library for node.js. Suitable for client and server side.",
|
|
4
|
-
"version": "2.3.0-
|
|
4
|
+
"version": "2.3.0-344dec99",
|
|
5
5
|
"private": false,
|
|
6
6
|
"browserslist": [
|
|
7
7
|
"> 0.5%"
|
|
@@ -117,6 +117,7 @@
|
|
|
117
117
|
"test:serialize:14": "cd ./tests/serialize && node ./data.js -in=t14.html -format=text/turtle -out=,t14.ttl && node diff ,t14.ttl t14-ref.ttl",
|
|
118
118
|
"test:serialize:15": "cd ./tests/serialize && node ./data.js -in=t15.html -format=text/turtle -out=,t15.ttl && node diff ,t15.ttl t15-ref.ttl",
|
|
119
119
|
"test:serialize:16": "cd ./tests/serialize && node ./data.js -in=t1.ttl -format=application/ld+json -out=,t1.jsonld && node diff ,t1.jsonld t16-ref.jsonld",
|
|
120
|
+
"test:serialize:17": "cd ./tests/serialize && node ./data.js -in=t17.ttl -format=application/rdf+xml -out=,t17.xml && node diff ,t17.xml t17-ref.xml",
|
|
120
121
|
"test:types": "tsc --noEmit --target es2019 --moduleResolution node tests/types/*.ts",
|
|
121
122
|
"test:unit": "mocha --growl --require ./tests/babel-register.js tests/unit/**-test.*",
|
|
122
123
|
"test:unit:egp": "mocha --require ./tests/babel-register.js tests/unit/fetcher-egp-test.js",
|
package/src/serialize.ts
CHANGED
|
@@ -72,7 +72,8 @@ export default function serialize (
|
|
|
72
72
|
return executeCallback(null, documentString)
|
|
73
73
|
case TurtleContentType:
|
|
74
74
|
case TurtleLegacyContentType:
|
|
75
|
-
|
|
75
|
+
// Suppress = for sameAs and => for implies; preserve any user-specified flags (e.g., 'o')
|
|
76
|
+
sz.setFlags('si' + (opts.flags ? (' ' + opts.flags) : ''))
|
|
76
77
|
documentString = sz.statementsToN3(newSts)
|
|
77
78
|
return executeCallback(null, documentString)
|
|
78
79
|
case NTriplesContentType:
|
|
@@ -80,7 +81,8 @@ export default function serialize (
|
|
|
80
81
|
documentString = sz.statementsToNTriples(newSts)
|
|
81
82
|
return executeCallback(null, documentString)
|
|
82
83
|
case JSONLDContentType:
|
|
83
|
-
|
|
84
|
+
// turtle + dr (means no default, no relative prefix); preserve user flags
|
|
85
|
+
sz.setFlags('si dr' + (opts.flags ? (' ' + opts.flags) : ''))
|
|
84
86
|
documentString = sz.statementsToJsonld(newSts) // convert via turtle
|
|
85
87
|
return executeCallback(null, documentString)
|
|
86
88
|
case NQuadsContentType:
|
package/src/serializer.js
CHANGED
|
@@ -52,6 +52,12 @@ export class Serializer {
|
|
|
52
52
|
return this
|
|
53
53
|
}
|
|
54
54
|
|
|
55
|
+
/**
|
|
56
|
+
* Set serializer behavior flags. Letters can be combined with spaces.
|
|
57
|
+
* Examples: 'si', 'deinprstux', 'si dr', 'o'.
|
|
58
|
+
* Notable flags:
|
|
59
|
+
* - 'o': do not abbreviate to a prefixed name when the local part contains a dot
|
|
60
|
+
*/
|
|
55
61
|
setFlags(flags) {
|
|
56
62
|
this.flags = flags || '';
|
|
57
63
|
return this
|
|
@@ -251,10 +257,33 @@ export class Serializer {
|
|
|
251
257
|
return this.statementsToN3(f.statements)
|
|
252
258
|
}
|
|
253
259
|
|
|
254
|
-
_notQNameChars = '\t\r\n !"#$%&\'()
|
|
260
|
+
_notQNameChars = '\t\r\n !"#$%&\'()*,+/;<=>?@[\\]^`{|}~' // issue#228
|
|
255
261
|
_notNameChars =
|
|
256
262
|
(this._notQNameChars + ':')
|
|
257
263
|
|
|
264
|
+
// Validate if a string is a valid PN_LOCAL per Turtle 1.1 spec
|
|
265
|
+
// Allows dots inside the local name but not as trailing character
|
|
266
|
+
// Also allows empty local names (for URIs ending in / or #)
|
|
267
|
+
isValidPNLocal(local) {
|
|
268
|
+
// Empty local name is valid (e.g., ex: for http://example.com/)
|
|
269
|
+
if (local.length === 0) return true
|
|
270
|
+
|
|
271
|
+
// Cannot end with a dot
|
|
272
|
+
if (local[local.length - 1] === '.') return false
|
|
273
|
+
|
|
274
|
+
// Check each character (allow dots mid-string)
|
|
275
|
+
for (var i = 0; i < local.length; i++) {
|
|
276
|
+
var ch = local[i]
|
|
277
|
+
// Dot is allowed unless it's the last character (checked above)
|
|
278
|
+
if (ch === '.') continue
|
|
279
|
+
// Other characters must not be in the blacklist
|
|
280
|
+
if (this._notNameChars.indexOf(ch) >= 0) {
|
|
281
|
+
return false
|
|
282
|
+
}
|
|
283
|
+
}
|
|
284
|
+
return true
|
|
285
|
+
}
|
|
286
|
+
|
|
258
287
|
explicitURI(uri) {
|
|
259
288
|
if (this.flags.indexOf('r') < 0 && this.base) {
|
|
260
289
|
uri = Uri.refTo(this.base, uri)
|
|
@@ -628,13 +657,17 @@ export class Serializer {
|
|
|
628
657
|
if (j >= 0 && this.flags.indexOf('p') < 0 &&
|
|
629
658
|
// Can split at namespace but only if http[s]: URI or file: or ws[s] (why not others?)
|
|
630
659
|
(uri.indexOf('http') === 0 || uri.indexOf('ws') === 0 || uri.indexOf('file') === 0)) {
|
|
631
|
-
var
|
|
632
|
-
|
|
633
|
-
|
|
634
|
-
|
|
635
|
-
|
|
636
|
-
|
|
637
|
-
|
|
660
|
+
var localid = uri.slice(j + 1)
|
|
661
|
+
var namesp = uri.slice(0, j + 1)
|
|
662
|
+
// Don't split if namespace is just the protocol (e.g., https://)
|
|
663
|
+
// A valid namespace should have content after the protocol
|
|
664
|
+
var minNamespaceLength = uri.indexOf('://') + 4 // e.g., "http://x" minimum
|
|
665
|
+
// Also don't split if namespace is the base directory (would serialize as relative URI)
|
|
666
|
+
var baseDir = this.base ? this.base.slice(0, Math.max(this.base.lastIndexOf('/'), this.base.lastIndexOf('#')) + 1) : null
|
|
667
|
+
var namespaceIsBaseDir = baseDir && namesp === baseDir
|
|
668
|
+
// If flag 'o' is present, forbid dots in local part when abbreviating
|
|
669
|
+
var forbidDotLocal = this.flags.indexOf('o') >= 0 && localid.indexOf('.') >= 0
|
|
670
|
+
var canSplit = !namespaceIsBaseDir && !forbidDotLocal && namesp.length > minNamespaceLength && this.isValidPNLocal(localid)
|
|
638
671
|
/*
|
|
639
672
|
if (uri.slice(0, j + 1) === this.base + '#') { // base-relative
|
|
640
673
|
if (canSplit) {
|
|
@@ -645,8 +678,6 @@ export class Serializer {
|
|
|
645
678
|
}
|
|
646
679
|
*/
|
|
647
680
|
if (canSplit) {
|
|
648
|
-
var localid = uri.slice(j + 1)
|
|
649
|
-
var namesp = uri.slice(0, j + 1)
|
|
650
681
|
if (this.defaultNamespace && this.defaultNamespace === namesp &&
|
|
651
682
|
this.flags.indexOf('d') < 0) { // d -> suppress default
|
|
652
683
|
if (this.flags.indexOf('k') >= 0 &&
|