diff --git a/utils/asset_test.go b/utils/asset_test.go index 411b69629..98dde03de 100644 --- a/utils/asset_test.go +++ b/utils/asset_test.go @@ -658,11 +658,16 @@ func TestGetDataToCommitFromJob(t *testing.T) { Url: "https://api.gemini.com/v1/pubticker/ethusd/apiKey=${SAMPLE_API_KEY_NEW}", } - postJob := bindings.StructsJob{Id: 1, SelectorType: 0, Weight: 100, + postJobUniswapV3 := bindings.StructsJob{Id: 1, SelectorType: 0, Weight: 100, Power: 2, Name: "ethusd_sample", Selector: "result", Url: `{"type": "POST","url": "https://rpc.ankr.com/eth","body": {"jsonrpc":"2.0","method":"eth_call","params":[{"to":"0xb27308f9f90d607463bb33ea1bebb41c27ce5ab6","data":"0xf7729d43000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc2000000000000000000000000a0b86991c6218b36c1d19d4a2e9eb0ce3606eb480000000000000000000000000000000000000000000000000000000000000bb80000000000000000000000000000000000000000000000000de0b6b3a76400000000000000000000000000000000000000000000000000000000000000000000"},"latest"],"id":5},"header": {"content-type": "application/json"}, "returnType": "hex"}`, } + postJobUniswapV2 := bindings.StructsJob{Id: 1, SelectorType: 0, Weight: 100, + Power: 6, Name: "ethusd_sample", Selector: "result", + Url: `{"type": "POST","url": "https://rpc.ankr.com/eth","body": {"jsonrpc":"2.0","id":7269270904970082,"method":"eth_call","params":[{"from":"0x0000000000000000000000000000000000000000","data":"0xd06ca61f0000000000000000000000000000000000000000000000000de0b6b3a76400000000000000000000000000000000000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000000000000200000000000000000000000050de6856358cc35f3a9a57eaaa34bd4cb707d2cd0000000000000000000000008e870d67f660d95d5be530380d0ec0bd388289e1","to":"0x7a250d5630b4cf539739df2c5dacb4c659f2488d"},"latest"]},"header": {"content-type": "application/json"}, "returnType": "hexArray[1]"}`, + } + invalidDataSourceStructJob := bindings.StructsJob{Id: 1, SelectorType: 0, Weight: 100, Power: 2, Name: "ethusd_sample", Selector: "result", Url: `{"type": true,"url1": {}}`, @@ -700,7 +705,7 @@ func TestGetDataToCommitFromJob(t *testing.T) { { name: "Test 3: When GetDataToCommitFromJob() executes successfully for a POST Job", args: args{ - job: postJob, + job: postJobUniswapV3, }, wantErr: false, }, @@ -720,6 +725,14 @@ func TestGetDataToCommitFromJob(t *testing.T) { want: nil, wantErr: true, }, + { + name: "Test 6: When GetDataToCommitFromJob() executes successfully for a POST uniswap v2 Job", + args: args{ + job: postJobUniswapV2, + }, + want: nil, + wantErr: false, + }, } for _, tt := range tests { t.Run(tt.name, func(t *testing.T) { diff --git a/utils/math_test.go b/utils/math_test.go index 60d73faaa..9106c9fd7 100644 --- a/utils/math_test.go +++ b/utils/math_test.go @@ -1035,3 +1035,265 @@ func TestConvertHexToBigFloat(t *testing.T) { }) } } + +func TestHandleHexArray(t *testing.T) { + type args struct { + hexStr string + returnType string + } + tests := []struct { + name string + args args + want *big.Float + wantErr bool + }{ + { + name: "Test 1: Valid token price input", + args: args{ + hexStr: "0x000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000de0b6b3a76400000000000000000000000000000000000000000000000000000012aee97c8ee4b8", + returnType: "hexArray[1]", + }, + want: big.NewFloat(0.00525886742), + wantErr: false, + }, + { + name: "Test 2: Valid another token price input", + args: args{ + hexStr: "0x000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000de0b6b3a764000000000000000000000000000000000000000000000000000000000000000ba121", + returnType: "hexArray[1]", + }, + want: big.NewFloat(0.000000000000762145), + wantErr: false, + }, + { + name: "Test 3: Invalid hex string", + args: args{ + hexStr: "0x00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000002", + returnType: "hexArray[1]", + }, + want: big.NewFloat(0), + wantErr: true, + }, + { + name: "Test 4: Invalid return type to extract index", + args: args{ + hexStr: "0x000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000de0b6b3a76400000000000000000000000000000000000000000000000000000012aee97c8ee4b8", + returnType: "hexArray[1a]", + }, + want: big.NewFloat(0), + wantErr: true, + }, + { + name: "Test 5: When decoded value of data is 0, wei to eth conversion will throw error", + args: args{ + hexStr: "0x000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000", + returnType: "hexArray[0]", + }, + want: big.NewFloat(0), + wantErr: true, + }, + { + name: "Test 6: When extracted index is out of bounds", + args: args{ + hexStr: "0x000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000", + returnType: "hexArray[1]", + }, + want: big.NewFloat(0), + wantErr: true, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + got, err := HandleHexArray(tt.args.hexStr, tt.args.returnType) + if (err != nil) != tt.wantErr { + t.Errorf("HandleHexArray() error = %v, wantErr %v", err, tt.wantErr) + return + } + // Use a small tolerance for comparison + tolerance := big.NewFloat(1e-10).SetPrec(1024) + + diff := new(big.Float).Sub(got, tt.want) + diff.Abs(diff) + + // Check if the difference is greater than or equal to tolerance + if diff.Cmp(tolerance) >= 0 { + t.Errorf("HandleHexArray() got = %v, want %v, difference = %v", got, tt.want, diff) + } + }) + } +} + +func Test_decodeHexString(t *testing.T) { + type args struct { + hexStr string + } + tests := []struct { + name string + args args + want []*big.Int + wantErr bool + }{ + { + name: "Valid hex string which is a result from uniswap v2 datasource", + args: args{hexStr: "0x000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000de0b6b3a76400000000000000000000000000000000000000000000000000000012aee97c8ee4b8"}, + want: []*big.Int{ + big.NewInt(1000000000000000000), + big.NewInt(5258867421144248), + }, + wantErr: false, + }, + { + name: "Valid single element", + args: args{hexStr: "0x000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000001"}, + want: []*big.Int{big.NewInt(1)}, + wantErr: false, + }, + { + name: "Valid hex string is provided but length of array doesnt match", + args: args{hexStr: "0x0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000300000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000de0b6b3a7640000"}, + want: nil, + wantErr: true, + }, + { + name: "Invalid hex string", + args: args{hexStr: "0x12345"}, + want: nil, + wantErr: true, + }, + { + name: "Invalid length field", + args: args{hexStr: "0x0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000Z"}, + want: nil, + wantErr: true, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + got, err := decodeHexString(tt.args.hexStr) + if (err != nil) != tt.wantErr { + t.Errorf("decodeHexString() error = %v, wantErr %v", err, tt.wantErr) + return + } + if !reflect.DeepEqual(got, tt.want) { + t.Errorf("decodeHexString() got = %v, want %v", got, tt.want) + } + }) + } +} + +func Test_extractIndex(t *testing.T) { + type args struct { + s string + } + tests := []struct { + name string + args args + want int + wantErr bool + }{ + { + name: "Valid input with index 1", + args: args{s: "hexArray[1]"}, + want: 1, + wantErr: false, + }, + { + name: "Valid input with index 123", + args: args{s: "hexArray[123]"}, + want: 123, + wantErr: false, + }, + { + name: "Invalid input - missing brackets", + args: args{s: "hexArray1"}, + want: 0, + wantErr: true, + }, + { + name: "Invalid input - non-numeric index", + args: args{s: "hexArray[abc]"}, + want: 0, + wantErr: true, + }, + { + name: "Invalid input - negative index", + args: args{s: "hexArray[-1]"}, + want: 0, + wantErr: true, + }, + { + name: "Invalid input - empty string", + args: args{s: ""}, + want: 0, + wantErr: true, + }, + } + + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + got, err := extractIndex(tt.args.s) + if (err != nil) != tt.wantErr { + t.Errorf("extractIndex() error = %v, wantErr %v", err, tt.wantErr) + return + } + if got != tt.want { + t.Errorf("extractIndex() got = %v, want %v", got, tt.want) + } + }) + } +} + +func Test_isHexArrayPattern(t *testing.T) { + type args struct { + s string + } + tests := []struct { + name string + args args + want bool + }{ + { + name: "Valid pattern with index 0", + args: args{s: "hexArray[0]"}, + want: true, + }, + { + name: "Valid pattern with index 123", + args: args{s: "hexArray[123]"}, + want: true, + }, + { + name: "Invalid pattern - missing brackets", + args: args{s: "hexArray1"}, + want: false, + }, + { + name: "Invalid pattern - non-numeric index", + args: args{s: "hexArray[abc]"}, + want: false, + }, + { + name: "Invalid pattern - negative index", + args: args{s: "hexArray[-1]"}, + want: false, + }, + { + name: "Invalid pattern - empty string", + args: args{s: ""}, + want: false, + }, + { + name: "Invalid pattern - extra characters", + args: args{s: "hexArray[10]abc"}, + want: false, + }, + // Additional test cases can be added here. + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + if got := isHexArrayPattern(tt.args.s); got != tt.want { + t.Errorf("isHexArrayPattern() = %v, want %v", got, tt.want) + } + }) + } +}