1 // Copyright 2011 The Go Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 package json 6 7 import ( 8 "regexp" 9 "testing" 10 ) 11 12 func TestNumberIsValid(t *testing.T) { 13 // From: http://stackoverflow.com/a/13340826 14 var jsonNumberRegexp = regexp.MustCompile(`^-?(?:0|[1-9]\d*)(?:\.\d+)?(?:[eE][+-]?\d+)?$`) 15 16 validTests := []string{ 17 "0", 18 "-0", 19 "1", 20 "-1", 21 "0.1", 22 "-0.1", 23 "1234", 24 "-1234", 25 "12.34", 26 "-12.34", 27 "12E0", 28 "12E1", 29 "12e34", 30 "12E-0", 31 "12e+1", 32 "12e-34", 33 "-12E0", 34 "-12E1", 35 "-12e34", 36 "-12E-0", 37 "-12e+1", 38 "-12e-34", 39 "1.2E0", 40 "1.2E1", 41 "1.2e34", 42 "1.2E-0", 43 "1.2e+1", 44 "1.2e-34", 45 "-1.2E0", 46 "-1.2E1", 47 "-1.2e34", 48 "-1.2E-0", 49 "-1.2e+1", 50 "-1.2e-34", 51 "0E0", 52 "0E1", 53 "0e34", 54 "0E-0", 55 "0e+1", 56 "0e-34", 57 "-0E0", 58 "-0E1", 59 "-0e34", 60 "-0E-0", 61 "-0e+1", 62 "-0e-34", 63 } 64 65 for _, test := range validTests { 66 if !isValidNumber(test) { 67 t.Errorf("%s should be valid", test) 68 } 69 70 var f float64 71 if err := Unmarshal([]byte(test), &f); err != nil { 72 t.Errorf("%s should be valid but Unmarshal failed: %v", test, err) 73 } 74 75 if !jsonNumberRegexp.MatchString(test) { 76 t.Errorf("%s should be valid but regexp does not match", test) 77 } 78 } 79 80 invalidTests := []string{ 81 "", 82 "invalid", 83 "1.0.1", 84 "1..1", 85 "-1-2", 86 "012a42", 87 "01.2", 88 "012", 89 "12E12.12", 90 "1e2e3", 91 "1e+-2", 92 "1e--23", 93 "1e", 94 "e1", 95 "1e+", 96 "1ea", 97 "1a", 98 "1.a", 99 "1.", 100 "01", 101 "1.e1", 102 } 103 104 for _, test := range invalidTests { 105 if isValidNumber(test) { 106 t.Errorf("%s should be invalid", test) 107 } 108 109 var f float64 110 if err := Unmarshal([]byte(test), &f); err == nil { 111 t.Errorf("%s should be invalid but unmarshal wrote %v", test, f) 112 } 113 114 if jsonNumberRegexp.MatchString(test) { 115 t.Errorf("%s should be invalid but matches regexp", test) 116 } 117 } 118 } 119 120 func BenchmarkNumberIsValid(b *testing.B) { 121 s := "-61657.61667E+61673" 122 for i := 0; i < b.N; i++ { 123 isValidNumber(s) 124 } 125 } 126 127 func BenchmarkNumberIsValidRegexp(b *testing.B) { 128 var jsonNumberRegexp = regexp.MustCompile(`^-?(?:0|[1-9]\d*)(?:\.\d+)?(?:[eE][+-]?\d+)?$`) 129 s := "-61657.61667E+61673" 130 for i := 0; i < b.N; i++ { 131 jsonNumberRegexp.MatchString(s) 132 } 133 } 134