github.com/digdeepmining/go-atheios@v1.5.13-0.20180902133602-d5687a2e6f43/common/hexutil/json_test.go (about)

     1  // Copyright 2016 The go-ethereum Authors
     2  // This file is part of the go-ethereum library.
     3  //
     4  // The go-ethereum library is free software: you can redistribute it and/or modify
     5  // it under the terms of the GNU Lesser General Public License as published by
     6  // the Free Software Foundation, either version 3 of the License, or
     7  // (at your option) any later version.
     8  //
     9  // The go-ethereum library is distributed in the hope that it will be useful,
    10  // but WITHOUT ANY WARRANTY; without even the implied warranty of
    11  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
    12  // GNU Lesser General Public License for more details.
    13  //
    14  // You should have received a copy of the GNU Lesser General Public License
    15  // along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
    16  
    17  package hexutil
    18  
    19  import (
    20  	"bytes"
    21  	"encoding/hex"
    22  	"math/big"
    23  	"testing"
    24  )
    25  
    26  func checkError(t *testing.T, input string, got, want error) bool {
    27  	if got == nil {
    28  		if want != nil {
    29  			t.Errorf("input %s: got no error, want %q", input, want)
    30  			return false
    31  		}
    32  		return true
    33  	}
    34  	if want == nil {
    35  		t.Errorf("input %s: unexpected error %q", input, got)
    36  	} else if got.Error() != want.Error() {
    37  		t.Errorf("input %s: got error %q, want %q", input, got, want)
    38  	}
    39  	return false
    40  }
    41  
    42  func referenceBig(s string) *big.Int {
    43  	b, ok := new(big.Int).SetString(s, 16)
    44  	if !ok {
    45  		panic("invalid")
    46  	}
    47  	return b
    48  }
    49  
    50  func referenceBytes(s string) []byte {
    51  	b, err := hex.DecodeString(s)
    52  	if err != nil {
    53  		panic(err)
    54  	}
    55  	return b
    56  }
    57  
    58  var unmarshalBytesTests = []unmarshalTest{
    59  	// invalid encoding
    60  	{input: "", wantErr: errNonString},
    61  	{input: "null", wantErr: errNonString},
    62  	{input: "10", wantErr: errNonString},
    63  	{input: `"0"`, wantErr: ErrMissingPrefix},
    64  	{input: `"0x0"`, wantErr: ErrOddLength},
    65  	{input: `"0xxx"`, wantErr: ErrSyntax},
    66  	{input: `"0x01zz01"`, wantErr: ErrSyntax},
    67  
    68  	// valid encoding
    69  	{input: `""`, want: referenceBytes("")},
    70  	{input: `"0x"`, want: referenceBytes("")},
    71  	{input: `"0x02"`, want: referenceBytes("02")},
    72  	{input: `"0X02"`, want: referenceBytes("02")},
    73  	{input: `"0xffffffffff"`, want: referenceBytes("ffffffffff")},
    74  	{
    75  		input: `"0xffffffffffffffffffffffffffffffffffff"`,
    76  		want:  referenceBytes("ffffffffffffffffffffffffffffffffffff"),
    77  	},
    78  }
    79  
    80  func TestUnmarshalBytes(t *testing.T) {
    81  	for _, test := range unmarshalBytesTests {
    82  		var v Bytes
    83  		err := v.UnmarshalJSON([]byte(test.input))
    84  		if !checkError(t, test.input, err, test.wantErr) {
    85  			continue
    86  		}
    87  		if !bytes.Equal(test.want.([]byte), []byte(v)) {
    88  			t.Errorf("input %s: value mismatch: got %x, want %x", test.input, &v, test.want)
    89  			continue
    90  		}
    91  	}
    92  }
    93  
    94  func BenchmarkUnmarshalBytes(b *testing.B) {
    95  	input := []byte(`"0x123456789abcdef123456789abcdef"`)
    96  	for i := 0; i < b.N; i++ {
    97  		var v Bytes
    98  		if err := v.UnmarshalJSON(input); err != nil {
    99  			b.Fatal(err)
   100  		}
   101  	}
   102  }
   103  
   104  func TestMarshalBytes(t *testing.T) {
   105  	for _, test := range encodeBytesTests {
   106  		in := test.input.([]byte)
   107  		out, err := Bytes(in).MarshalJSON()
   108  		if err != nil {
   109  			t.Errorf("%x: %v", in, err)
   110  			continue
   111  		}
   112  		if want := `"` + test.want + `"`; string(out) != want {
   113  			t.Errorf("%x: MarshalJSON output mismatch: got %q, want %q", in, out, want)
   114  			continue
   115  		}
   116  		if out := Bytes(in).String(); out != test.want {
   117  			t.Errorf("%x: String mismatch: got %q, want %q", in, out, test.want)
   118  			continue
   119  		}
   120  	}
   121  }
   122  
   123  var unmarshalBigTests = []unmarshalTest{
   124  	// invalid encoding
   125  	{input: "", wantErr: errNonString},
   126  	{input: "null", wantErr: errNonString},
   127  	{input: "10", wantErr: errNonString},
   128  	{input: `"0"`, wantErr: ErrMissingPrefix},
   129  	{input: `"0x"`, wantErr: ErrEmptyNumber},
   130  	{input: `"0x01"`, wantErr: ErrLeadingZero},
   131  	{input: `"0xx"`, wantErr: ErrSyntax},
   132  	{input: `"0x1zz01"`, wantErr: ErrSyntax},
   133  
   134  	// valid encoding
   135  	{input: `""`, want: big.NewInt(0)},
   136  	{input: `"0x0"`, want: big.NewInt(0)},
   137  	{input: `"0x2"`, want: big.NewInt(0x2)},
   138  	{input: `"0x2F2"`, want: big.NewInt(0x2f2)},
   139  	{input: `"0X2F2"`, want: big.NewInt(0x2f2)},
   140  	{input: `"0x1122aaff"`, want: big.NewInt(0x1122aaff)},
   141  	{input: `"0xbBb"`, want: big.NewInt(0xbbb)},
   142  	{input: `"0xfffffffff"`, want: big.NewInt(0xfffffffff)},
   143  	{
   144  		input: `"0x112233445566778899aabbccddeeff"`,
   145  		want:  referenceBig("112233445566778899aabbccddeeff"),
   146  	},
   147  	{
   148  		input: `"0xffffffffffffffffffffffffffffffffffff"`,
   149  		want:  referenceBig("ffffffffffffffffffffffffffffffffffff"),
   150  	},
   151  }
   152  
   153  func TestUnmarshalBig(t *testing.T) {
   154  	for _, test := range unmarshalBigTests {
   155  		var v Big
   156  		err := v.UnmarshalJSON([]byte(test.input))
   157  		if !checkError(t, test.input, err, test.wantErr) {
   158  			continue
   159  		}
   160  		if test.want != nil && test.want.(*big.Int).Cmp((*big.Int)(&v)) != 0 {
   161  			t.Errorf("input %s: value mismatch: got %x, want %x", test.input, (*big.Int)(&v), test.want)
   162  			continue
   163  		}
   164  	}
   165  }
   166  
   167  func BenchmarkUnmarshalBig(b *testing.B) {
   168  	input := []byte(`"0x123456789abcdef123456789abcdef"`)
   169  	for i := 0; i < b.N; i++ {
   170  		var v Big
   171  		if err := v.UnmarshalJSON(input); err != nil {
   172  			b.Fatal(err)
   173  		}
   174  	}
   175  }
   176  
   177  func TestMarshalBig(t *testing.T) {
   178  	for _, test := range encodeBigTests {
   179  		in := test.input.(*big.Int)
   180  		out, err := (*Big)(in).MarshalJSON()
   181  		if err != nil {
   182  			t.Errorf("%d: %v", in, err)
   183  			continue
   184  		}
   185  		if want := `"` + test.want + `"`; string(out) != want {
   186  			t.Errorf("%d: MarshalJSON output mismatch: got %q, want %q", in, out, want)
   187  			continue
   188  		}
   189  		if out := (*Big)(in).String(); out != test.want {
   190  			t.Errorf("%x: String mismatch: got %q, want %q", in, out, test.want)
   191  			continue
   192  		}
   193  	}
   194  }
   195  
   196  var unmarshalUint64Tests = []unmarshalTest{
   197  	// invalid encoding
   198  	{input: "", wantErr: errNonString},
   199  	{input: "null", wantErr: errNonString},
   200  	{input: "10", wantErr: errNonString},
   201  	{input: `"0"`, wantErr: ErrMissingPrefix},
   202  	{input: `"0x"`, wantErr: ErrEmptyNumber},
   203  	{input: `"0x01"`, wantErr: ErrLeadingZero},
   204  	{input: `"0xfffffffffffffffff"`, wantErr: ErrUint64Range},
   205  	{input: `"0xx"`, wantErr: ErrSyntax},
   206  	{input: `"0x1zz01"`, wantErr: ErrSyntax},
   207  
   208  	// valid encoding
   209  	{input: `""`, want: uint64(0)},
   210  	{input: `"0x0"`, want: uint64(0)},
   211  	{input: `"0x2"`, want: uint64(0x2)},
   212  	{input: `"0x2F2"`, want: uint64(0x2f2)},
   213  	{input: `"0X2F2"`, want: uint64(0x2f2)},
   214  	{input: `"0x1122aaff"`, want: uint64(0x1122aaff)},
   215  	{input: `"0xbbb"`, want: uint64(0xbbb)},
   216  	{input: `"0xffffffffffffffff"`, want: uint64(0xffffffffffffffff)},
   217  }
   218  
   219  func TestUnmarshalUint64(t *testing.T) {
   220  	for _, test := range unmarshalUint64Tests {
   221  		var v Uint64
   222  		err := v.UnmarshalJSON([]byte(test.input))
   223  		if !checkError(t, test.input, err, test.wantErr) {
   224  			continue
   225  		}
   226  		if uint64(v) != test.want.(uint64) {
   227  			t.Errorf("input %s: value mismatch: got %d, want %d", test.input, v, test.want)
   228  			continue
   229  		}
   230  	}
   231  }
   232  
   233  func BenchmarkUnmarshalUint64(b *testing.B) {
   234  	input := []byte(`"0x123456789abcdf"`)
   235  	for i := 0; i < b.N; i++ {
   236  		var v Uint64
   237  		v.UnmarshalJSON(input)
   238  	}
   239  }
   240  
   241  func TestMarshalUint64(t *testing.T) {
   242  	for _, test := range encodeUint64Tests {
   243  		in := test.input.(uint64)
   244  		out, err := Uint64(in).MarshalJSON()
   245  		if err != nil {
   246  			t.Errorf("%d: %v", in, err)
   247  			continue
   248  		}
   249  		if want := `"` + test.want + `"`; string(out) != want {
   250  			t.Errorf("%d: MarshalJSON output mismatch: got %q, want %q", in, out, want)
   251  			continue
   252  		}
   253  		if out := (Uint64)(in).String(); out != test.want {
   254  			t.Errorf("%x: String mismatch: got %q, want %q", in, out, test.want)
   255  			continue
   256  		}
   257  	}
   258  }