email_address_validator 1.0.0 → 2.0.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 40a7903f966cc1c88ea370e25ef041484c4d1fa6
4
- data.tar.gz: d1f7aeafad963a543d4ad128e2a3b1108ea7cc67
3
+ metadata.gz: 2cc3e2b1d36178731391c09de74d8ee9c378f5f6
4
+ data.tar.gz: 30b987b6aed56e55292fea9240f272613d63fc8a
5
5
  SHA512:
6
- metadata.gz: 6f9aa6e4b76be4595fff9ee5c04776bdf7fc6f77bc32ebed9f11167059559252807877c2d32cd6e4f03f87ddcea78a755fa373fd35894f07a424a245ab9fc8c6
7
- data.tar.gz: b9092df595f541c160d68558f4f44b41fc48dfe92763a61bce501e5722a9faeb8df8ac31f2b226a5408306995e5de9787aefb750c1c90c73f37def73b846b0ba
6
+ metadata.gz: 8dd649a91a55f24208cffdfd3f681b80e8b31759c728b2ef8ca355a0a398697d70cd022de075ab61d346e0918255bd8071930ef2f5210dbc7110e63b53f8a162
7
+ data.tar.gz: 8620453673d42a5e172e4afe70af4c84f271780c875a8e1a6f61c71ebf5ef12511af9c74e915493294355df7eaec629fef9238bfe9fefe36a4b3be0e6140eae6
data/Gemfile CHANGED
@@ -2,5 +2,5 @@
2
2
  source "https://rubygems.org"
3
3
 
4
4
  gem "rake"
5
- gem "rspec"
5
+ gem "rspec", "~> 2.0"
6
6
  # gem "rails"
@@ -3,22 +3,18 @@ GEM
3
3
  specs:
4
4
  diff-lcs (1.2.5)
5
5
  rake (10.3.2)
6
- rspec (3.1.0)
7
- rspec-core (~> 3.1.0)
8
- rspec-expectations (~> 3.1.0)
9
- rspec-mocks (~> 3.1.0)
10
- rspec-core (3.1.7)
11
- rspec-support (~> 3.1.0)
12
- rspec-expectations (3.1.2)
13
- diff-lcs (>= 1.2.0, < 2.0)
14
- rspec-support (~> 3.1.0)
15
- rspec-mocks (3.1.3)
16
- rspec-support (~> 3.1.0)
17
- rspec-support (3.1.2)
6
+ rspec (2.99.0)
7
+ rspec-core (~> 2.99.0)
8
+ rspec-expectations (~> 2.99.0)
9
+ rspec-mocks (~> 2.99.0)
10
+ rspec-core (2.99.2)
11
+ rspec-expectations (2.99.2)
12
+ diff-lcs (>= 1.1.3, < 2.0)
13
+ rspec-mocks (2.99.3)
18
14
 
19
15
  PLATFORMS
20
16
  ruby
21
17
 
22
18
  DEPENDENCIES
23
19
  rake
24
- rspec
20
+ rspec (~> 2.0)
@@ -3,7 +3,7 @@
3
3
  %% { attr_accessor :validate_domain }
4
4
 
5
5
  d(num) = <.> &{ text[0] == num }
6
- d_btw(start,fin) = <.> &{ t = text[0]; t >= start && t <= fin }
6
+ d_btw(start,fin) = <.> &{ t = text[0].ord; t >= start && t <= fin }
7
7
 
8
8
  WSP = " " | d(9)
9
9
 
@@ -19,16 +19,16 @@ CRLF = CR LF
19
19
 
20
20
  linear_white_space = (CRLF? LWSP_char)+
21
21
 
22
- atom = /[^\]\x00-\x20 \x7F\x80-\xFF()<>@,;:\\".\[]+/
22
+ atom = /[^\]\x00-\x20 \x7F\x80-\xFF()<>@,;:\\".\[]+/n
23
23
 
24
- ctext = /[^)\\\x0D\x80-\xFF(]+/
24
+ ctext = /[^)\\\x0D\x80-\xFF(]+/n
25
25
  | linear_white_space
26
26
 
27
27
 
28
- dtext = /[^\]\\\x0D\x80-\xFF\[]+/
28
+ dtext = /[^\]\\\x0D\x80-\xFF\[]+/n
29
29
  | linear_white_space
30
30
 
31
- qtext = /[^"\\\x0D\x80-\xFF]+/
31
+ qtext = /[^"\\\x0D\x80-\xFF]+/n
32
32
  | linear_white_space
33
33
 
34
34
 
@@ -52,7 +52,9 @@ module EmailAddressValidator
52
52
  end
53
53
 
54
54
  # Shorthand for +EmailAddressParser.validate_2822_addr
55
- def self.validate_addr(addr, validate_domain=false); self.validate_2822; end
55
+ def self.validate_addr(addr, validate_domain=false)
56
+ validate_2822_addr addr, validate_domain
57
+ end
56
58
 
57
59
  # Validates +addr+ against the addr_spec portion of RFC 2822.
58
60
  # This is what most people actually want out of an email validator
@@ -65,7 +67,9 @@ module EmailAddressValidator
65
67
  end
66
68
 
67
69
  # Shorthand for +EmailAddressParser.validate_2822
68
- def self.validate(addr, validate_domain=false); self.validate_2822; end
70
+ def self.validate(addr, validate_domain=false)
71
+ validate_2822 addr, validate_domain
72
+ end
69
73
 
70
74
  # Validates an email address according to RFC 2822
71
75
  # This validates addresses against the full spec, which
@@ -1,8 +1,19 @@
1
1
  class EmailAddressValidator::DomainParser
2
- # STANDALONE START
2
+ # :stopdoc:
3
+
4
+ # This is distinct from setup_parser so that a standalone parser
5
+ # can redefine #initialize and still have access to the proper
6
+ # parser setup code.
7
+ def initialize(str, debug=false)
8
+ setup_parser(str, debug)
9
+ end
10
+
11
+
12
+
13
+ # Prepares for parsing +str+. If you define a custom initialize you must
14
+ # call this method before #parse
3
15
  def setup_parser(str, debug=false)
4
- @string = str
5
- @pos = 0
16
+ set_string str, 0
6
17
  @memoizations = Hash.new { |h,k| h[k] = {} }
7
18
  @result = nil
8
19
  @failed_rule = nil
@@ -11,22 +22,10 @@ class EmailAddressValidator::DomainParser
11
22
  setup_foreign_grammar
12
23
  end
13
24
 
14
- def setup_foreign_grammar
15
- end
16
-
17
- # This is distinct from setup_parser so that a standalone parser
18
- # can redefine #initialize and still have access to the proper
19
- # parser setup code.
20
- #
21
- def initialize(str, debug=false)
22
- setup_parser(str, debug)
23
- end
24
-
25
25
  attr_reader :string
26
- attr_reader :result, :failing_rule_offset
27
- attr_accessor :pos
26
+ attr_reader :failing_rule_offset
27
+ attr_accessor :result, :pos
28
28
 
29
- # STANDALONE START
30
29
  def current_column(target=pos)
31
30
  if c = string.rindex("\n", target-1)
32
31
  return target - c - 1
@@ -54,12 +53,19 @@ class EmailAddressValidator::DomainParser
54
53
  lines
55
54
  end
56
55
 
57
- #
56
+
58
57
 
59
58
  def get_text(start)
60
59
  @string[start..@pos-1]
61
60
  end
62
61
 
62
+ # Sets the string and current parsing position for the parser.
63
+ def set_string string, pos
64
+ @string = string
65
+ @string_size = string ? string.size : 0
66
+ @pos = pos
67
+ end
68
+
63
69
  def show_pos
64
70
  width = 10
65
71
  if @pos < width
@@ -166,19 +172,19 @@ class EmailAddressValidator::DomainParser
166
172
  return nil
167
173
  end
168
174
 
169
- if "".respond_to? :getbyte
175
+ if "".respond_to? :ord
170
176
  def get_byte
171
- if @pos >= @string.size
177
+ if @pos >= @string_size
172
178
  return nil
173
179
  end
174
180
 
175
- s = @string.getbyte @pos
181
+ s = @string[@pos].ord
176
182
  @pos += 1
177
183
  s
178
184
  end
179
185
  else
180
186
  def get_byte
181
- if @pos >= @string.size
187
+ if @pos >= @string_size
182
188
  return nil
183
189
  end
184
190
 
@@ -189,41 +195,37 @@ class EmailAddressValidator::DomainParser
189
195
  end
190
196
 
191
197
  def parse(rule=nil)
198
+ # We invoke the rules indirectly via apply
199
+ # instead of by just calling them as methods because
200
+ # if the rules use left recursion, apply needs to
201
+ # manage that.
202
+
192
203
  if !rule
193
- _root ? true : false
204
+ apply(:_root)
194
205
  else
195
- # This is not shared with code_generator.rb so this can be standalone
196
206
  method = rule.gsub("-","_hyphen_")
197
- __send__("_#{method}") ? true : false
207
+ apply :"_#{method}"
198
208
  end
199
209
  end
200
210
 
201
- class LeftRecursive
202
- def initialize(detected=false)
203
- @detected = detected
204
- end
205
-
206
- attr_accessor :detected
207
- end
208
-
209
211
  class MemoEntry
210
212
  def initialize(ans, pos)
211
213
  @ans = ans
212
214
  @pos = pos
213
- @uses = 1
214
215
  @result = nil
216
+ @set = false
217
+ @left_rec = false
215
218
  end
216
219
 
217
- attr_reader :ans, :pos, :uses, :result
218
-
219
- def inc!
220
- @uses += 1
221
- end
220
+ attr_reader :ans, :pos, :result, :set
221
+ attr_accessor :left_rec
222
222
 
223
223
  def move!(ans, pos, result)
224
224
  @ans = ans
225
225
  @pos = pos
226
226
  @result = result
227
+ @set = true
228
+ @left_rec = false
227
229
  end
228
230
  end
229
231
 
@@ -231,30 +233,61 @@ class EmailAddressValidator::DomainParser
231
233
  old_pos = @pos
232
234
  old_string = @string
233
235
 
234
- @pos = other.pos
235
- @string = other.string
236
+ set_string other.string, other.pos
236
237
 
237
238
  begin
238
239
  if val = __send__(rule, *args)
239
240
  other.pos = @pos
241
+ other.result = @result
240
242
  else
241
243
  other.set_failed_rule "#{self.class}##{rule}"
242
244
  end
243
245
  val
244
246
  ensure
245
- @pos = old_pos
246
- @string = old_string
247
+ set_string old_string, old_pos
248
+ end
249
+ end
250
+
251
+ def apply_with_args(rule, *args)
252
+ memo_key = [rule, args]
253
+ if m = @memoizations[memo_key][@pos]
254
+ @pos = m.pos
255
+ if !m.set
256
+ m.left_rec = true
257
+ return nil
258
+ end
259
+
260
+ @result = m.result
261
+
262
+ return m.ans
263
+ else
264
+ m = MemoEntry.new(nil, @pos)
265
+ @memoizations[memo_key][@pos] = m
266
+ start_pos = @pos
267
+
268
+ ans = __send__ rule, *args
269
+
270
+ lr = m.left_rec
271
+
272
+ m.move! ans, @pos, @result
273
+
274
+ # Don't bother trying to grow the left recursion
275
+ # if it's failing straight away (thus there is no seed)
276
+ if ans and lr
277
+ return grow_lr(rule, args, start_pos, m)
278
+ else
279
+ return ans
280
+ end
281
+
282
+ return ans
247
283
  end
248
284
  end
249
285
 
250
286
  def apply(rule)
251
287
  if m = @memoizations[rule][@pos]
252
- m.inc!
253
-
254
- prev = @pos
255
288
  @pos = m.pos
256
- if m.ans.kind_of? LeftRecursive
257
- m.ans.detected = true
289
+ if !m.set
290
+ m.left_rec = true
258
291
  return nil
259
292
  end
260
293
 
@@ -262,19 +295,20 @@ class EmailAddressValidator::DomainParser
262
295
 
263
296
  return m.ans
264
297
  else
265
- lr = LeftRecursive.new(false)
266
- m = MemoEntry.new(lr, @pos)
298
+ m = MemoEntry.new(nil, @pos)
267
299
  @memoizations[rule][@pos] = m
268
300
  start_pos = @pos
269
301
 
270
302
  ans = __send__ rule
271
303
 
304
+ lr = m.left_rec
305
+
272
306
  m.move! ans, @pos, @result
273
307
 
274
308
  # Don't bother trying to grow the left recursion
275
309
  # if it's failing straight away (thus there is no seed)
276
- if ans and lr.detected
277
- return grow_lr(rule, start_pos, m)
310
+ if ans and lr
311
+ return grow_lr(rule, nil, start_pos, m)
278
312
  else
279
313
  return ans
280
314
  end
@@ -283,12 +317,16 @@ class EmailAddressValidator::DomainParser
283
317
  end
284
318
  end
285
319
 
286
- def grow_lr(rule, start_pos, m)
320
+ def grow_lr(rule, args, start_pos, m)
287
321
  while true
288
322
  @pos = start_pos
289
323
  @result = m.result
290
324
 
291
- ans = __send__ rule
325
+ if args
326
+ ans = __send__ rule, *args
327
+ else
328
+ ans = __send__ rule
329
+ end
292
330
  return nil unless ans
293
331
 
294
332
  break if @pos <= m.pos
@@ -314,7 +352,9 @@ class EmailAddressValidator::DomainParser
314
352
  RuleInfo.new(name, rendered)
315
353
  end
316
354
 
317
- #
355
+
356
+ # :startdoc:
357
+ # :stopdoc:
318
358
  def setup_foreign_grammar; end
319
359
 
320
360
  # domain = < subdomain > &{ text.size < 255 }
@@ -322,22 +362,22 @@ class EmailAddressValidator::DomainParser
322
362
 
323
363
  _save = self.pos
324
364
  while true # sequence
325
- _text_start = self.pos
326
- _tmp = apply(:_subdomain)
327
- if _tmp
328
- text = get_text(_text_start)
329
- end
330
- unless _tmp
331
- self.pos = _save
365
+ _text_start = self.pos
366
+ _tmp = apply(:_subdomain)
367
+ if _tmp
368
+ text = get_text(_text_start)
369
+ end
370
+ unless _tmp
371
+ self.pos = _save
372
+ break
373
+ end
374
+ _save1 = self.pos
375
+ _tmp = begin; text.size < 255 ; end
376
+ self.pos = _save1
377
+ unless _tmp
378
+ self.pos = _save
379
+ end
332
380
  break
333
- end
334
- _save1 = self.pos
335
- _tmp = begin; text.size < 255 ; end
336
- self.pos = _save1
337
- unless _tmp
338
- self.pos = _save
339
- end
340
- break
341
381
  end # end sequence
342
382
 
343
383
  set_failed_rule :_domain unless _tmp
@@ -350,31 +390,31 @@ class EmailAddressValidator::DomainParser
350
390
  _save = self.pos
351
391
  while true # choice
352
392
 
353
- _save1 = self.pos
354
- while true # sequence
355
- _tmp = apply(:_subdomain)
356
- unless _tmp
357
- self.pos = _save1
358
- break
359
- end
360
- _tmp = match_string(".")
361
- unless _tmp
362
- self.pos = _save1
363
- break
364
- end
365
- _tmp = apply(:_label)
366
- unless _tmp
367
- self.pos = _save1
368
- end
369
- break
370
- end # end sequence
393
+ _save1 = self.pos
394
+ while true # sequence
395
+ _tmp = apply(:_subdomain)
396
+ unless _tmp
397
+ self.pos = _save1
398
+ break
399
+ end
400
+ _tmp = match_string(".")
401
+ unless _tmp
402
+ self.pos = _save1
403
+ break
404
+ end
405
+ _tmp = apply(:_label)
406
+ unless _tmp
407
+ self.pos = _save1
408
+ end
409
+ break
410
+ end # end sequence
371
411
 
372
- break if _tmp
373
- self.pos = _save
374
- _tmp = apply(:_label)
375
- break if _tmp
376
- self.pos = _save
377
- break
412
+ break if _tmp
413
+ self.pos = _save
414
+ _tmp = apply(:_label)
415
+ break if _tmp
416
+ self.pos = _save
417
+ break
378
418
  end # end choice
379
419
 
380
420
  set_failed_rule :_subdomain unless _tmp
@@ -386,31 +426,31 @@ class EmailAddressValidator::DomainParser
386
426
 
387
427
  _save = self.pos
388
428
  while true # sequence
389
- _tmp = apply(:_let_hyphen_dig)
390
- unless _tmp
391
- self.pos = _save
392
- break
393
- end
394
- _text_start = self.pos
395
- while true
396
- _tmp = apply(:_let_hyphen_dig_hyphen_hyp)
397
- break unless _tmp
398
- end
399
- _tmp = true
400
- if _tmp
401
- text = get_text(_text_start)
402
- end
403
- unless _tmp
404
- self.pos = _save
429
+ _tmp = apply(:_let_hyphen_dig)
430
+ unless _tmp
431
+ self.pos = _save
432
+ break
433
+ end
434
+ _text_start = self.pos
435
+ while true
436
+ _tmp = apply(:_let_hyphen_dig_hyphen_hyp)
437
+ break unless _tmp
438
+ end
439
+ _tmp = true
440
+ if _tmp
441
+ text = get_text(_text_start)
442
+ end
443
+ unless _tmp
444
+ self.pos = _save
445
+ break
446
+ end
447
+ _save2 = self.pos
448
+ _tmp = begin; text.size < 63 && (text.size == 0 || text[-1] != ?-) ; end
449
+ self.pos = _save2
450
+ unless _tmp
451
+ self.pos = _save
452
+ end
405
453
  break
406
- end
407
- _save2 = self.pos
408
- _tmp = begin; text.size < 63 && (text.size == 0 || text[-1] != ?-) ; end
409
- self.pos = _save2
410
- unless _tmp
411
- self.pos = _save
412
- end
413
- break
414
454
  end # end sequence
415
455
 
416
456
  set_failed_rule :_label unless _tmp
@@ -422,13 +462,13 @@ class EmailAddressValidator::DomainParser
422
462
 
423
463
  _save = self.pos
424
464
  while true # choice
425
- _tmp = apply(:_let_hyphen_dig)
426
- break if _tmp
427
- self.pos = _save
428
- _tmp = match_string("-")
429
- break if _tmp
430
- self.pos = _save
431
- break
465
+ _tmp = apply(:_let_hyphen_dig)
466
+ break if _tmp
467
+ self.pos = _save
468
+ _tmp = match_string("-")
469
+ break if _tmp
470
+ self.pos = _save
471
+ break
432
472
  end # end choice
433
473
 
434
474
  set_failed_rule :_let_hyphen_dig_hyphen_hyp unless _tmp
@@ -440,13 +480,13 @@ class EmailAddressValidator::DomainParser
440
480
 
441
481
  _save = self.pos
442
482
  while true # choice
443
- _tmp = apply(:_letter)
444
- break if _tmp
445
- self.pos = _save
446
- _tmp = apply(:_digit)
447
- break if _tmp
448
- self.pos = _save
449
- break
483
+ _tmp = apply(:_letter)
484
+ break if _tmp
485
+ self.pos = _save
486
+ _tmp = apply(:_digit)
487
+ break if _tmp
488
+ self.pos = _save
489
+ break
450
490
  end # end choice
451
491
 
452
492
  set_failed_rule :_let_hyphen_dig unless _tmp
@@ -472,19 +512,19 @@ class EmailAddressValidator::DomainParser
472
512
 
473
513
  _save = self.pos
474
514
  while true # sequence
475
- _tmp = apply(:_domain)
476
- unless _tmp
477
- self.pos = _save
515
+ _tmp = apply(:_domain)
516
+ unless _tmp
517
+ self.pos = _save
518
+ break
519
+ end
520
+ _save1 = self.pos
521
+ _tmp = get_byte
522
+ _tmp = _tmp ? nil : true
523
+ self.pos = _save1
524
+ unless _tmp
525
+ self.pos = _save
526
+ end
478
527
  break
479
- end
480
- _save1 = self.pos
481
- _tmp = get_byte
482
- _tmp = _tmp ? nil : true
483
- self.pos = _save1
484
- unless _tmp
485
- self.pos = _save
486
- end
487
- break
488
528
  end # end sequence
489
529
 
490
530
  set_failed_rule :_root unless _tmp
@@ -500,4 +540,5 @@ class EmailAddressValidator::DomainParser
500
540
  Rules[:_letter] = rule_info("letter", "/[A-Za-z]/")
501
541
  Rules[:_digit] = rule_info("digit", "/[0-9]/")
502
542
  Rules[:_root] = rule_info("root", "domain !.")
543
+ # :startdoc:
503
544
  end