@@ -34,6 +34,11 @@ const {
34
34
isAbsolute : _isAbsoluteIri
35
35
} = require ( './url' ) ;
36
36
37
+ const _HEX = '[0-9A-Fa-f]' ;
38
+ const _UCHAR = '\\u' + _HEX + '{4}|\\U' + _HEX + '{8}' ;
39
+ const IRIREF_RE = new RegExp ( '^([^\\x00-\\x20<>"{}|^`\\\\]|' + _UCHAR + ')*$' ) ;
40
+ const LANG_RE = / ^ [ a - z A - Z ] + ( - [ a - z A - Z 0 - 9 ] + ) * $ / ;
41
+
37
42
const api = { } ;
38
43
module . exports = api ;
39
44
@@ -58,6 +63,11 @@ api.toRDF = (input, options) => {
58
63
if ( graphName === '@default' ) {
59
64
graphTerm = { termType : 'DefaultGraph' , value : '' } ;
60
65
} else if ( _isAbsoluteIri ( graphName ) ) {
66
+ // invalid graph IRI
67
+ if ( ! IRIREF_RE . test ( graphName ) ) {
68
+ continue ;
69
+ }
70
+
61
71
if ( graphName . startsWith ( '_:' ) ) {
62
72
graphTerm = { termType : 'BlankNode' } ;
63
73
} else {
@@ -110,6 +120,11 @@ function _graphToRDF(dataset, graph, graphTerm, issuer, options) {
110
120
continue ;
111
121
}
112
122
123
+ // invalid subject IRI
124
+ if ( ! IRIREF_RE . test ( id ) ) {
125
+ continue ;
126
+ }
127
+
113
128
// RDF predicate
114
129
const predicate = {
115
130
termType : property . startsWith ( '_:' ) ? 'BlankNode' : 'NamedNode' ,
@@ -121,6 +136,11 @@ function _graphToRDF(dataset, graph, graphTerm, issuer, options) {
121
136
continue ;
122
137
}
123
138
139
+ // invalid predicate IRI
140
+ if ( ! IRIREF_RE . test ( property ) ) {
141
+ continue ;
142
+ }
143
+
124
144
// skip blank node predicates unless producing generalized RDF
125
145
if ( predicate . termType === 'BlankNode' &&
126
146
! options . produceGeneralizedRdf ) {
@@ -226,6 +246,11 @@ function _objectToRDF(item, issuer, dataset, graphTerm) {
226
246
let value = item [ '@value' ] ;
227
247
const datatype = item [ '@type' ] || null ;
228
248
249
+ // invalid datatype IRI
250
+ if ( datatype && ! IRIREF_RE . test ( datatype ) ) {
251
+ return null ;
252
+ }
253
+
229
254
// convert to XSD/JSON datatypes as appropriate
230
255
if ( datatype === '@json' ) {
231
256
object . value = jsonCanonicalize ( value ) ;
@@ -244,6 +269,9 @@ function _objectToRDF(item, issuer, dataset, graphTerm) {
244
269
object . value = value . toFixed ( 0 ) ;
245
270
object . datatype . value = datatype || XSD_INTEGER ;
246
271
} else if ( '@language' in item ) {
272
+ if ( ! LANG_RE . test ( item [ '@language' ] ) ) {
273
+ return null ;
274
+ }
247
275
object . value = value ;
248
276
object . datatype . value = datatype || RDF_LANGSTRING ;
249
277
object . language = item [ '@language' ] ;
@@ -258,6 +286,12 @@ function _objectToRDF(item, issuer, dataset, graphTerm) {
258
286
} else {
259
287
// convert string/node object to RDF
260
288
const id = types . isObject ( item ) ? item [ '@id' ] : item ;
289
+
290
+ // invalid object IRI
291
+ if ( ! IRIREF_RE . test ( id ) ) {
292
+ return null ;
293
+ }
294
+
261
295
object . termType = id . startsWith ( '_:' ) ? 'BlankNode' : 'NamedNode' ;
262
296
object . value = id ;
263
297
}
0 commit comments