Class | Sequel::Postgres::PGRange::Parser |
In: |
lib/sequel/extensions/pg_range.rb
|
Parent: | Object |
PARSER | = | /\A(\[|\()("((?:\\"|[^"])*)"|[^"]*),("((?:\\"|[^"])*)"|[^"]*)(\]|\))\z/o | Regexp that parses the full range of PostgreSQL range type output, except for empty ranges. | |
REPLACE_RE | = | /\\(.)/.freeze | ||
REPLACE_WITH | = | '\1'.freeze |
converter | [R] | A callable object to convert the beginning and ending of the range into the appropriate ruby type. |
db_type | [R] | The database range type for this parser (e.g. ‘int4range’), automatically setting the db_type for the returned PGRange instances. |
Set the db_type and converter on initialization.
# File lib/sequel/extensions/pg_range.rb, line 193 193: def initialize(db_type, converter=nil) 194: @db_type = db_type.to_s.dup.freeze if db_type 195: @converter = converter 196: end
Parse the range type input string into a PGRange value.
# File lib/sequel/extensions/pg_range.rb, line 199 199: def call(string) 200: if string == EMPTY 201: return PGRange.empty(db_type) 202: end 203: 204: raise(InvalidValue, "invalid or unhandled range format: #{string.inspect}") unless matches = PARSER.match(string) 205: 206: exclude_begin = matches[1] == '(' 207: exclude_end = matches[6] == ')' 208: 209: # If the input is quoted, it needs to be unescaped. Also, quoted input isn't 210: # checked for emptiness, since the empty quoted string is considered an 211: # element that happens to be the empty string, while an unquoted empty string 212: # is considered unbounded. 213: # 214: # While PostgreSQL allows pure escaping for input (without quoting), it appears 215: # to always use the quoted output form when characters need to be escaped, so 216: # there isn't a need to unescape unquoted output. 217: if beg = matches[3] 218: beg.gsub!(REPLACE_RE, REPLACE_WITH) 219: else 220: beg = matches[2] unless matches[2].empty? 221: end 222: if en = matches[5] 223: en.gsub!(REPLACE_RE, REPLACE_WITH) 224: else 225: en = matches[4] unless matches[4].empty? 226: end 227: 228: if c = converter 229: beg = c.call(beg) if beg 230: en = c.call(en) if en 231: end 232: 233: PGRange.new(beg, en, :exclude_begin=>exclude_begin, :exclude_end=>exclude_end, :db_type=>db_type) 234: end