Class: Addressable::Template
- Inherits:
-
Object
- Object
- Addressable::Template
- Defined in:
- lib/addressable/template.rb
Overview
This is an implementation of a URI template based on RFC 6570 (tools.ietf.org/html/rfc6570).
Defined Under Namespace
Classes: InvalidTemplateOperatorError, InvalidTemplateValueError, MatchData, TemplateOperatorAbortedError
Constant Summary collapse
- RESERVED =
"(?:[#{anything}]|%[a-fA-F0-9][a-fA-F0-9])"
- UNRESERVED =
"(?:[#{ Addressable::URI::CharacterClasses::UNRESERVED }]|%[a-fA-F0-9][a-fA-F0-9])"
- VARNAME =
/^#{variable}$/
- VARSPEC =
/^#{varspec}$/
- VARIABLE_LIST =
/^#{varspec}(?:,#{varspec})*$/
- EXPRESSION =
/\{([#{operator}])?(#{varspec}(?:,#{varspec})*)\}/
- LEADERS =
{ '?' => '?', '/' => '/', '#' => '#', '.' => '.', ';' => ';', '&' => '&' }
- JOINERS =
{ '?' => '&', '.' => '.', ';' => ';', '&' => '&', '/' => '/' }
Instance Attribute Summary collapse
-
#pattern ⇒ String
readonly
The Template object’s pattern.
Instance Method Summary collapse
-
#==(template) ⇒ TrueClass, FalseClass
(also: #eql?)
Returns
true
if the Template objects are equal. -
#expand(mapping, processor = nil, normalize_values = true) ⇒ Addressable::URI
Expands a URI template into a full URI.
-
#extract(uri, processor = nil) ⇒ Hash, NilClass
Extracts a mapping from the URI using a URI Template pattern.
-
#freeze ⇒ Addressable::URI
Freeze URI, initializing instance variables.
-
#initialize(pattern) ⇒ Addressable::Template
constructor
Creates a new
Addressable::Template
object. -
#inspect ⇒ String
Returns a
String
representation of the Template object’s state. -
#match(uri, processor = nil) ⇒ Hash, NilClass
Extracts match data from the URI using a URI Template pattern.
-
#named_captures ⇒ Hash
private
Returns the named captures of the coerced ‘Regexp`.
-
#partial_expand(mapping, processor = nil, normalize_values = true) ⇒ Addressable::Template
Expands a URI template into another URI template.
-
#source ⇒ String
private
Returns the source of the coerced ‘Regexp`.
-
#to_regexp ⇒ Regexp
Coerces a template into a ‘Regexp` object.
-
#variable_defaults ⇒ Hash
Returns a mapping of variables to their default values specified in the template.
-
#variables ⇒ Array
(also: #keys, #names)
Returns an Array of variables used within the template pattern.
Constructor Details
#initialize(pattern) ⇒ Addressable::Template
Creates a new Addressable::Template
object.
234 235 236 237 238 239 |
# File 'lib/addressable/template.rb', line 234 def initialize(pattern) if !pattern.respond_to?(:to_str) raise TypeError, "Can't convert #{pattern.class} into String." end @pattern = pattern.to_str.dup.freeze end |
Instance Attribute Details
#pattern ⇒ String (readonly)
Returns The Template object’s pattern.
254 255 256 |
# File 'lib/addressable/template.rb', line 254 def pattern @pattern end |
Instance Method Details
#==(template) ⇒ TrueClass, FalseClass Also known as: eql?
Returns true
if the Template objects are equal. This method does NOT normalize either Template before doing the comparison.
274 275 276 277 |
# File 'lib/addressable/template.rb', line 274 def ==(template) return false unless template.kind_of?(Template) return self.pattern == template.pattern end |
#expand(mapping, processor = nil, normalize_values = true) ⇒ Addressable::URI
Expands a URI template into a full URI.
The object should respond to either the validate
or transform
messages or both. Both the validate
and transform
methods should take two parameters: name
and value
. The validate
method should return true
or false
; true
if the value of the variable is valid, false
otherwise. An InvalidTemplateValueError
exception will be raised if the value is invalid. The transform
method should return the transformed variable value as a String
. If a transform
method is used, the value will not be percent encoded automatically. Unicode normalization will be performed both before and after sending the value to the transform method.
591 592 593 594 595 596 597 598 |
# File 'lib/addressable/template.rb', line 591 def (mapping, processor=nil, normalize_values=true) result = self.pattern.dup mapping = normalize_keys(mapping) result.gsub!( EXPRESSION ) do |capture| transform_capture(mapping, capture, processor, normalize_values) end return Addressable::URI.parse(result) end |
#extract(uri, processor = nil) ⇒ Hash, NilClass
Extracts a mapping from the URI using a URI Template pattern.
342 343 344 345 |
# File 'lib/addressable/template.rb', line 342 def extract(uri, processor=nil) match_data = self.match(uri, processor) return (match_data ? match_data.mapping : nil) end |
#freeze ⇒ Addressable::URI
Freeze URI, initializing instance variables.
245 246 247 248 249 250 |
# File 'lib/addressable/template.rb', line 245 def freeze self.variables self.variable_defaults self.named_captures super end |
#inspect ⇒ String
Returns a String
representation of the Template object’s state.
260 261 262 263 |
# File 'lib/addressable/template.rb', line 260 def inspect sprintf("#<%s:%#0x PATTERN:%s>", self.class.to_s, self.object_id, self.pattern) end |
#match(uri, processor = nil) ⇒ Hash, NilClass
Extracts match data from the URI using a URI Template pattern.
413 414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 446 447 448 449 450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 484 |
# File 'lib/addressable/template.rb', line 413 def match(uri, processor=nil) uri = Addressable::URI.parse(uri) unless uri.is_a?(Addressable::URI) mapping = {} # First, we need to process the pattern, and extract the values. expansions, expansion_regexp = parse_template_pattern(pattern, processor) return nil unless uri.to_str.match(expansion_regexp) unparsed_values = uri.to_str.scan(expansion_regexp).flatten if uri.to_str == pattern return Addressable::Template::MatchData.new(uri, self, mapping) elsif expansions.size > 0 index = 0 expansions.each do |expansion| _, operator, varlist = *expansion.match(EXPRESSION) varlist.split(',').each do |varspec| _, name, modifier = *varspec.match(VARSPEC) mapping[name] ||= nil case operator when nil, '+', '#', '/', '.' unparsed_value = unparsed_values[index] name = varspec[VARSPEC, 1] value = unparsed_value value = value.split(JOINERS[operator]) if value && modifier == '*' when ';', '?', '&' if modifier == '*' if unparsed_values[index] value = unparsed_values[index].split(JOINERS[operator]) value = value.inject({}) do |acc, v| key, val = v.split('=') val = "" if val.nil? acc[key] = val acc end end else if (unparsed_values[index]) name, value = unparsed_values[index].split('=') value = "" if value.nil? end end end if processor != nil && processor.respond_to?(:restore) value = processor.restore(name, value) end if processor == nil if value.is_a?(Hash) value = value.inject({}){|acc, (k, v)| acc[Addressable::URI.unencode_component(k)] = Addressable::URI.unencode_component(v) acc } elsif value.is_a?(Array) value = value.map{|v| Addressable::URI.unencode_component(v) } else value = Addressable::URI.unencode_component(value) end end if !mapping.has_key?(name) || mapping[name].nil? # Doesn't exist, set to value (even if value is nil) mapping[name] = value end index = index + 1 end end return Addressable::Template::MatchData.new(uri, self, mapping) else return nil end end |
#named_captures ⇒ Hash
This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.
Returns the named captures of the coerced ‘Regexp`.
651 652 653 |
# File 'lib/addressable/template.rb', line 651 def named_captures self.to_regexp.named_captures end |
#partial_expand(mapping, processor = nil, normalize_values = true) ⇒ Addressable::Template
Expands a URI template into another URI template.
The object should respond to either the validate
or transform
messages or both. Both the validate
and transform
methods should take two parameters: name
and value
. The validate
method should return true
or false
; true
if the value of the variable is valid, false
otherwise. An InvalidTemplateValueError
exception will be raised if the value is invalid. The transform
method should return the transformed variable value as a String
. If a transform
method is used, the value will not be percent encoded automatically. Unicode normalization will be performed both before and after sending the value to the transform method.
524 525 526 527 528 529 530 531 |
# File 'lib/addressable/template.rb', line 524 def (mapping, processor=nil, normalize_values=true) result = self.pattern.dup mapping = normalize_keys(mapping) result.gsub!( EXPRESSION ) do |capture| transform_partial_capture(mapping, capture, processor, normalize_values) end return Addressable::Template.new(result) end |
#source ⇒ String
This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.
Returns the source of the coerced ‘Regexp`.
641 642 643 |
# File 'lib/addressable/template.rb', line 641 def source self.to_regexp.source end |
#to_regexp ⇒ Regexp
Coerces a template into a ‘Regexp` object. This regular expression will behave very similarly to the actual template, and should match the same URI values, but it cannot fully handle, for example, values that would extract to an `Array`.
630 631 632 633 |
# File 'lib/addressable/template.rb', line 630 def to_regexp _, source = parse_template_pattern(pattern) Regexp.new(source) end |
#variable_defaults ⇒ Hash
Returns a mapping of variables to their default values specified in the template. Variables without defaults are not returned.
618 619 620 621 |
# File 'lib/addressable/template.rb', line 618 def variable_defaults @variable_defaults ||= Hash[*ordered_variable_defaults.reject { |k, v| v.nil? }.flatten] end |
#variables ⇒ Array Also known as: keys, names
Returns an Array of variables used within the template pattern. The variables are listed in the Array in the order they appear within the pattern. Multiple occurrences of a variable within a pattern are not represented in this Array.
607 608 609 |
# File 'lib/addressable/template.rb', line 607 def variables @variables ||= ordered_variable_defaults.map { |var, val| var }.uniq end |