Class: SPARQL::Grammar::Parser
- Inherits:
-
Object
- Object
- SPARQL::Grammar::Parser
- Includes:
- Meta
- Defined in:
- lib/sparql/grammar/parser.rb
Overview
A parser for the SPARQL 1.0 grammar.
Defined Under Namespace
Classes: Error
Constant Summary
- START =
SPARQL_GRAMMAR.Query
- RDF_TYPE =
(a = RDF.type.dup; a.lexical = 'a'; a).freeze
Constants included from Meta
Instance Attribute Summary (collapse)
-
- (String) input
The current input string being processed.
-
- (Hash) options
readonly
Any additional options for the parser.
-
- (Array) result
The internal representation of the result using hierarch of RDF objects and SPARQL::Algebra::Operator objects.
-
- (Array<Token>) tokens
readonly
The current input tokens being processed.
Instance Method Summary (collapse)
-
- (HRDF::URI) base_uri
Returns the Base URI defined for the parser, as specified or when parsing a BASE prologue element.
-
- (RDF::URI) base_uri=(uri)
Set the Base URI to use for this parser.
-
- (SPARQL::Grammar::Parser) initialize(input = nil, options = {})
constructor
Initializes a new parser instance.
-
- (Array) parse(prod = START)
Parse query.
-
- (RDF::URI) prefix(name, uri = nil)
Defines the given named URI prefix for this parser.
-
- (Hash{Symbol => RDF::URI}) prefixes
Returns the URI prefixes currently defined for this parser.
-
- (Hash{Symbol => RDF::URI}) prefixes=(prefixes)
Defines the given URI prefixes for this parser.
- - (Object) to_s
- - (String) to_sse
-
- (Boolean) valid?
Returns `true` if the input string is syntactically valid.
-
- (Boolean) validate?
Returns `true` if parsed statements and values should be validated.
Constructor Details
- (SPARQL::Grammar::Parser) initialize(input = nil, options = {})
Initializes a new parser instance.
37 38 39 40 41 42 43 |
# File 'lib/sparql/grammar/parser.rb', line 37 def initialize(input = nil, = {}) @options = {:anon_base => "b0", :validate => false}.merge() self.input = input if input @productions = [] @vars = {} @nd_var_gen = "0" end |
Instance Attribute Details
- (String) input
The current input string being processed.
55 56 57 |
# File 'lib/sparql/grammar/parser.rb', line 55 def input @input end |
- (Hash) options (readonly)
Any additional options for the parser.
49 50 51 |
# File 'lib/sparql/grammar/parser.rb', line 49 def @options end |
- (Array) result
The internal representation of the result using hierarch of RDF objects and SPARQL::Algebra::Operator objects.
68 69 70 |
# File 'lib/sparql/grammar/parser.rb', line 68 def result @result end |
- (Array<Token>) tokens (readonly)
The current input tokens being processed.
61 62 63 |
# File 'lib/sparql/grammar/parser.rb', line 61 def tokens @tokens end |
Instance Method Details
- (HRDF::URI) base_uri
Returns the Base URI defined for the parser, as specified or when parsing a BASE prologue element.
256 257 258 |
# File 'lib/sparql/grammar/parser.rb', line 256 def base_uri @options[:base_uri] end |
- (RDF::URI) base_uri=(uri)
Set the Base URI to use for this parser.
269 270 271 |
# File 'lib/sparql/grammar/parser.rb', line 269 def base_uri=(uri) @options[:base_uri] = RDF::URI(uri) end |
- (Array) parse(prod = START)
Parse query
The result is a SPARQL Algebra S-List. Productions return an array such as the following:
(prefix ((: <http://example/>))
(union
(bgp (triple ?s ?p ?o))
(graph ?g
(bgp (triple ?s ?p ?o)))))
Algebra is based on the SPARQL Algebra notes
120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 |
# File 'lib/sparql/grammar/parser.rb', line 120 def parse(prod = START) @prod_data = [{}] prod = prod.to_s.split("#").last.to_sym unless prod.is_a?(Symbol) todo_stack = [{:prod => prod, :terms => nil}] while !todo_stack.empty? pushed = false if todo_stack.last[:terms].nil? todo_stack.last[:terms] = [] token = tokens.first @lineno = token.lineno if token debug("parse(token)", "#{token.inspect}, prod #{todo_stack.last[:prod]}, depth #{todo_stack.length}") # Got an opened production onStart(abbr(todo_stack.last[:prod])) break if token.nil? cur_prod = todo_stack.last[:prod] prod_branch = BRANCHES[cur_prod.to_sym] error("parse", "No branches found for '#{abbr(cur_prod)}'", :production => cur_prod, :token => token) if prod_branch.nil? sequence = prod_branch[token.representation] debug("parse(production)", "cur_prod #{cur_prod}, token #{token.representation.inspect} prod_branch #{prod_branch.keys.inspect}, sequence #{sequence.inspect}") if sequence.nil? expected = prod_branch.values.uniq.map {|u| u.map {|v| abbr(v).inspect}.join(",")} error("parse", "Found '#{token.inspect}' when parsing a #{abbr(cur_prod)}. expected #{expected.join(' | ')}", :production => cur_prod, :token => token) end todo_stack.last[:terms] += sequence end debug("parse(terms)", "stack #{todo_stack.last.inspect}, depth #{todo_stack.length}") while !todo_stack.last[:terms].to_a.empty? term = todo_stack.last[:terms].shift debug("parse tokens(#{term})", tokens.inspect) if tokens.map(&:representation).include?(term) token = accept(term) @lineno = token.lineno if token debug("parse", "term(#{token.inspect}): #{term}") if token onToken(abbr(term), token.value) else error("parse", "Found '#{word}...'; #{term} expected", :production => todo_stack.last[:prod], :token => tokens.first) end else todo_stack << {:prod => term, :terms => nil} debug("parse(push)", "stack #{term}, depth #{todo_stack.length}") pushed = true break end end while !pushed && !todo_stack.empty? && todo_stack.last[:terms].to_a.empty? debug("parse(pop)", "stack #{todo_stack.last.inspect}, depth #{todo_stack.length}") todo_stack.pop onFinish end end while !todo_stack.empty? debug("parse(pop)", "stack #{todo_stack.last.inspect}, depth #{todo_stack.length}") todo_stack.pop onFinish end # The last thing on the @prod_data stack is the result @result = case when !prod_data.is_a?(Hash) prod_data when prod_data.empty? nil when prod_data[:query] prod_data[:query].to_a.length == 1 ? prod_data[:query].first : prod_data[:query] else key = prod_data.keys.first [key] + prod_data[key] # Creates [:key, [:triple], ...] end end |
- (Object) prefix(name, uri) - (Object) prefix(name)
Defines the given named URI prefix for this parser.
243 244 245 246 |
# File 'lib/sparql/grammar/parser.rb', line 243 def prefix(name, uri = nil) name = name.to_s.empty? ? nil : (name.respond_to?(:to_sym) ? name.to_sym : name.to_s.to_sym) uri.nil? ? prefixes[name] : prefixes[name] = uri end |
- (Hash{Symbol => RDF::URI}) prefixes
Returns the URI prefixes currently defined for this parser.
207 208 209 |
# File 'lib/sparql/grammar/parser.rb', line 207 def prefixes @options[:prefixes] ||= {} end |
- (Hash{Symbol => RDF::URI}) prefixes=(prefixes)
Defines the given URI prefixes for this parser.
222 223 224 |
# File 'lib/sparql/grammar/parser.rb', line 222 def prefixes=(prefixes) @options[:prefixes] = prefixes end |
- (Object) to_s
100 101 102 |
# File 'lib/sparql/grammar/parser.rb', line 100 def to_s @result.to_sxp end |
- (String) to_sse
96 97 98 |
# File 'lib/sparql/grammar/parser.rb', line 96 def to_sse @result end |
- (Boolean) valid?
Returns `true` if the input string is syntactically valid.
89 90 91 92 93 |
# File 'lib/sparql/grammar/parser.rb', line 89 def valid? parse rescue Error false end |
- (Boolean) validate?
Returns `true` if parsed statements and values should be validated.
278 279 280 |
# File 'lib/sparql/grammar/parser.rb', line 278 def validate? @options[:validate] end |