Class: KDL::Types::Email::Tokenizer

Inherits:
Object
  • Object
show all
Defined in:
lib/kdl/types/email/parser.rb

Constant Summary collapse

LOCAL_PART_ASCII =
%r{[a-zA-Z0-9!#$%&'*+\-/=?^_`{|}~]}.freeze
LOCAL_PART_IDN =
/[^\x00-\x1f ".@]/.freeze

Instance Method Summary collapse

Constructor Details

#initialize(string, idn: false) ⇒ Tokenizer

Returns a new instance of Tokenizer.



76
77
78
79
80
81
# File 'lib/kdl/types/email/parser.rb', line 76

def initialize(string, idn: false)
  @string = string
  @idn = idn
  @index = 0
  @after_at = false
end

Instance Method Details

#local_part_charsObject



145
146
147
# File 'lib/kdl/types/email/parser.rb', line 145

def local_part_chars
  @idn ? LOCAL_PART_IDN : LOCAL_PART_ASCII
end

#next_tokenObject



83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
# File 'lib/kdl/types/email/parser.rb', line 83

def next_token
  if @after_at
    if @index < @string.size
      domain_start = @index
      @index = @string.size
      return [:domain, @string[domain_start..-1]]
    else
      return [:end, nil]
    end
  end
  @context = nil
  @buffer = ''
  loop do
    c = @string[@index]
    return [:end, nil] if c.nil?

    case @context
    when nil
      case c
      when '.'
        @index += 1
        return [:dot, '.']
      when '@'
        @after_at = true
        @index += 1
        return [:at, '@']
      when '"'
        @context = :quote
        @index += 1
      when local_part_chars
        @context = :part
        @buffer += c
        @index += 1
      else
        raise ArgumentError, "invalid email #{@string} (unexpected #{c})"
      end
    when :part
      case c
      when local_part_chars
        @buffer += c
        @index += 1
      when '.', '@'
        return [:part, @buffer]
      else
        raise ArgumentError, "invalid email #{@string} (unexpected #{c})"
      end
    when :quote
      case c
      when '"'
        n = @string[@index + 1]
        raise ArgumentError, "invalid email #{@string} (unexpected #{c})" unless n == '.' || n == '@'

        @index += 1
        return [:part, @buffer]
      else
        @buffer += c
        @index += 1
      end
    end
  end
end