Mercurial Hosting > nabble
comparison src/nabble/view/web/util/codemirror/js/parsesparql.js @ 0:7ecd1a4ef557
add content
author | Franklin Schmidt <fschmidt@gmail.com> |
---|---|
date | Thu, 21 Mar 2019 19:15:52 -0600 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
-1:000000000000 | 0:7ecd1a4ef557 |
---|---|
1 var SparqlParser = Editor.Parser = (function() { | |
2 function wordRegexp(words) { | |
3 return new RegExp("^(?:" + words.join("|") + ")$", "i"); | |
4 } | |
5 var ops = wordRegexp(["str", "lang", "langmatches", "datatype", "bound", "sameterm", "isiri", "isuri", | |
6 "isblank", "isliteral", "union", "a"]); | |
7 var keywords = wordRegexp(["base", "prefix", "select", "distinct", "reduced", "construct", "describe", | |
8 "ask", "from", "named", "where", "order", "limit", "offset", "filter", "optional", | |
9 "graph", "by", "asc", "desc"]); | |
10 var operatorChars = /[*+\-<>=&|]/; | |
11 | |
12 var tokenizeSparql = (function() { | |
13 function normal(source, setState) { | |
14 var ch = source.next(); | |
15 if (ch == "$" || ch == "?") { | |
16 source.nextWhileMatches(/[\w\d]/); | |
17 return "sp-var"; | |
18 } | |
19 else if (ch == "<" && !source.matches(/[\s\u00a0=]/)) { | |
20 source.nextWhileMatches(/[^\s\u00a0>]/); | |
21 if (source.equals(">")) source.next(); | |
22 return "sp-uri"; | |
23 } | |
24 else if (ch == "\"" || ch == "'") { | |
25 setState(inLiteral(ch)); | |
26 return null; | |
27 } | |
28 else if (/[{}\(\),\.;\[\]]/.test(ch)) { | |
29 return "sp-punc"; | |
30 } | |
31 else if (ch == "#") { | |
32 while (!source.endOfLine()) source.next(); | |
33 return "sp-comment"; | |
34 } | |
35 else if (operatorChars.test(ch)) { | |
36 source.nextWhileMatches(operatorChars); | |
37 return "sp-operator"; | |
38 } | |
39 else if (ch == ":") { | |
40 source.nextWhileMatches(/[\w\d\._\-]/); | |
41 return "sp-prefixed"; | |
42 } | |
43 else { | |
44 source.nextWhileMatches(/[_\w\d]/); | |
45 if (source.equals(":")) { | |
46 source.next(); | |
47 source.nextWhileMatches(/[\w\d_\-]/); | |
48 return "sp-prefixed"; | |
49 } | |
50 var word = source.get(), type; | |
51 if (ops.test(word)) | |
52 type = "sp-operator"; | |
53 else if (keywords.test(word)) | |
54 type = "sp-keyword"; | |
55 else | |
56 type = "sp-word"; | |
57 return {style: type, content: word}; | |
58 } | |
59 } | |
60 | |
61 function inLiteral(quote) { | |
62 return function(source, setState) { | |
63 var escaped = false; | |
64 while (!source.endOfLine()) { | |
65 var ch = source.next(); | |
66 if (ch == quote && !escaped) { | |
67 setState(normal); | |
68 break; | |
69 } | |
70 escaped = !escaped && ch == "\\"; | |
71 } | |
72 return "sp-literal"; | |
73 }; | |
74 } | |
75 | |
76 return function(source, startState) { | |
77 return tokenizer(source, startState || normal); | |
78 }; | |
79 })(); | |
80 | |
81 function indentSparql(context) { | |
82 return function(nextChars) { | |
83 var firstChar = nextChars && nextChars.charAt(0); | |
84 if (/[\]\}]/.test(firstChar)) | |
85 while (context && context.type == "pattern") context = context.prev; | |
86 | |
87 var closing = context && firstChar == matching[context.type]; | |
88 if (!context) | |
89 return 0; | |
90 else if (context.type == "pattern") | |
91 return context.col; | |
92 else if (context.align) | |
93 return context.col - (closing ? context.width : 0); | |
94 else | |
95 return context.indent + (closing ? 0 : indentUnit); | |
96 } | |
97 } | |
98 | |
99 function parseSparql(source) { | |
100 var tokens = tokenizeSparql(source); | |
101 var context = null, indent = 0, col = 0; | |
102 function pushContext(type, width) { | |
103 context = {prev: context, indent: indent, col: col, type: type, width: width}; | |
104 } | |
105 function popContext() { | |
106 context = context.prev; | |
107 } | |
108 | |
109 var iter = { | |
110 next: function() { | |
111 var token = tokens.next(), type = token.style, content = token.content, width = token.value.length; | |
112 | |
113 if (content == "\n") { | |
114 token.indentation = indentSparql(context); | |
115 indent = col = 0; | |
116 if (context && context.align == null) context.align = false; | |
117 } | |
118 else if (type == "whitespace" && col == 0) { | |
119 indent = width; | |
120 } | |
121 else if (type != "sp-comment" && context && context.align == null) { | |
122 context.align = true; | |
123 } | |
124 | |
125 if (content != "\n") col += width; | |
126 | |
127 if (/[\[\{\(]/.test(content)) { | |
128 pushContext(content, width); | |
129 } | |
130 else if (/[\]\}\)]/.test(content)) { | |
131 while (context && context.type == "pattern") | |
132 popContext(); | |
133 if (context && content == matching[context.type]) | |
134 popContext(); | |
135 } | |
136 else if (content == "." && context && context.type == "pattern") { | |
137 popContext(); | |
138 } | |
139 else if ((type == "sp-word" || type == "sp-prefixed" || type == "sp-uri" || type == "sp-var" || type == "sp-literal") && | |
140 context && /[\{\[]/.test(context.type)) { | |
141 pushContext("pattern", width); | |
142 } | |
143 | |
144 return token; | |
145 }, | |
146 | |
147 copy: function() { | |
148 var _context = context, _indent = indent, _col = col, _tokenState = tokens.state; | |
149 return function(source) { | |
150 tokens = tokenizeSparql(source, _tokenState); | |
151 context = _context; | |
152 indent = _indent; | |
153 col = _col; | |
154 return iter; | |
155 }; | |
156 } | |
157 }; | |
158 return iter; | |
159 } | |
160 | |
161 return {make: parseSparql, electricChars: "}]"}; | |
162 })(); |