JSON RPC batch requests load balancing

Hi.

Is there any load-balancing magic behind handling of batch JSON RPC requests (https://www.jsonrpc.org/specification#batch) at Infura? Can I assume that all requests from the batch will be routed and processed by the same RPC node standing behind the load balancer?

Hi @k1rill-fedoseev, and welcome to the Infura community! That should be the case in a batch - are you seeing something else occurring?

Yes. I have tried sending 30 eth_blockNumber requests at a time in a single batch. If I do that close to the latest block mining time, I can receive block X in some of the results and block X + 1 in the remaining results.

I don’t think this can be due to race condition, since I didn’t see such behaviour with direct Geth or OpenEthereum node RPC interaction.

This is how I came up with the original question.

Got it - thanks for the additional information! We’re having some trouble replicating the issue - can you share a code snippet with us from the code that’s producing this behaviour? Thanks!

Here is the curl request I just made:

curl --request POST \
  --url https://mainnet.infura.io/v3/PROJECT_ID \
  --header 'Content-Type: application/json' \
  --data '[
	{"jsonrpc": "2.0", "id": 1, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 2, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 3, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 4, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 5, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 6, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 7, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 8, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 9, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 10, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 12, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 13, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 14, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 15, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 16, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 17, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 18, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 19, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 20, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 21, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 22, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 23, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 24, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 25, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 26, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 27, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 28, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 29, "method": "eth_blockNumber", "params": []},
	{"jsonrpc": "2.0", "id": 30, "method": "eth_blockNumber", "params": []}
]'

And here is the result I got:

[
  {
    "jsonrpc": "2.0",
    "id": 1,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 2,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 3,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 4,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 5,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 6,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 7,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 8,
    "result": "0xc6697e"
  },
  {
    "jsonrpc": "2.0",
    "id": 9,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 10,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 12,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 13,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 14,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 15,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 16,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 17,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 18,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 19,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 20,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 21,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 22,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 23,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 24,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 25,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 26,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 27,
    "result": "0xc6697e"
  },
  {
    "jsonrpc": "2.0",
    "id": 28,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 29,
    "result": "0xc6697f"
  },
  {
    "jsonrpc": "2.0",
    "id": 30,
    "result": "0xc6697f"
  }
]

Here I can see that two different block numbers: 0xc6697e and 0xc6697f, while I expect to see the same block number.

Thanks so much for the additional context! We’re digging into this and will let you know once we have something to share.