We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
Bitcoin legacy xpub with too many used address may fail to query balances after restart
## Problem Definition

If a user adds a legacy xpub that generates too many used addresses rotki will properly add the xpub and all its addresses. But then after a restart it will fail to query all balances again.

Error is:

```
Error at querying blockchain balances: bitcoin external API request for balances failed due to https://blockchain.info/multiaddr?active=XXXXXX
```

The failure is due to attempting to query all addresses from blockchain.info using the multiaddr endpoint which seems to have a non-documented limit.

blockchain.info errors with a 502 if too many bitcoin addresses are sent.

## Task

Fix it by experimenting and figuring out a safe limit.
Then apply that limit where we query for multiple legacy bitcoin addresses.

--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `rotkehlchen/chain/bitcoin/__init__.py`
Content:
```
1 from typing import Dict, List, Tuple
2 
3 import requests
4 
5 from rotkehlchen.errors import RemoteError, UnableToDecryptRemoteData
6 from rotkehlchen.fval import FVal
7 from rotkehlchen.typing import BTCAddress
8 from rotkehlchen.utils.misc import satoshis_to_btc
9 from rotkehlchen.utils.network import request_get_dict
10 
11 
12 def _have_bc1_accounts(accounts: List[BTCAddress]) -> bool:
13     return any(account.lower()[0:3] == 'bc1' for account in accounts)
14 
15 
16 def get_bitcoin_addresses_balances(accounts: List[BTCAddress]) -> Dict[BTCAddress, FVal]:
17     """Queries blockchain.info or blockstream for the balances of accounts
18 
19     May raise:
20     - RemotError if there is a problem querying blockchain.info or blockstream
21     """
22     source = 'blockchain.info'
23     balances: Dict[BTCAddress, FVal] = {}
24     try:
25         if _have_bc1_accounts(accounts):
26             # if 1 account is bech32 we have to query blockstream. blockchaininfo won't work
27             source = 'blockstream'
28             balances = {}
29             for account in accounts:
30                 url = f'https://blockstream.info/api/address/{account}'
31                 response_data = request_get_dict(url=url, handle_429=True, backoff_in_seconds=4)
32                 stats = response_data['chain_stats']
33                 balance = int(stats['funded_txo_sum']) - int(stats['spent_txo_sum'])
34                 balances[account] = satoshis_to_btc(balance)
35         else:
36             params = '|'.join(accounts)
37             btc_resp = request_get_dict(
38                 url=f'https://blockchain.info/multiaddr?active={params}',
39                 handle_429=True,
40                 # If we get a 429 then their docs suggest 10 seconds
41                 # https://blockchain.info/q
42                 backoff_in_seconds=10,
43             )
44             for entry in btc_resp['addresses']:
45                 balances[entry['address']] = satoshis_to_btc(FVal(entry['final_balance']))
46     except (
47             requests.exceptions.RequestException,
48             UnableToDecryptRemoteData,
49             requests.exceptions.Timeout,
50     ) as e:
51         raise RemoteError(f'bitcoin external API request for balances failed due to {str(e)}') from e  # noqa: E501
52     except KeyError as e:
53         raise RemoteError(
54             f'Malformed response when querying bitcoin blockchain via {source}.'
55             f'Did not find key {e}',
56         ) from e
57 
58     return balances
59 
60 
61 def _check_blockstream_for_transactions(
62         accounts: List[BTCAddress],
63 ) -> Dict[BTCAddress, Tuple[bool, FVal]]:
64     """May raise connection errors or KeyError"""
65     have_transactions = {}
66     for account in accounts:
67         url = f'https://blockstream.info/api/address/{account}'
68         response_data = request_get_dict(url=url, handle_429=True, backoff_in_seconds=4)
69         stats = response_data['chain_stats']
70         balance = satoshis_to_btc(int(stats['funded_txo_sum']) - int(stats['spent_txo_sum']))
71         have_txs = stats['tx_count'] != 0
72         have_transactions[account] = (have_txs, balance)
73 
74     return have_transactions
75 
76 
77 def _check_blockchaininfo_for_transactions(
78         accounts: List[BTCAddress],
79 ) -> Dict[BTCAddress, Tuple[bool, FVal]]:
80     """May raise RemotError or KeyError"""
81     have_transactions = {}
82     params = '|'.join(accounts)
83     btc_resp = request_get_dict(
84         url=f'https://blockchain.info/multiaddr?active={params}',
85         handle_429=True,
86         # If we get a 429 then their docs suggest 10 seconds
87         # https://blockchain.infoq/
88         backoff_in_seconds=15,
89     )
90     for entry in btc_resp['addresses']:
91         balance = satoshis_to_btc(entry['final_balance'])
92         have_transactions[entry['address']] = (entry['n_tx'] != 0, balance)
93 
94     return have_transactions
95 
96 
97 def have_bitcoin_transactions(accounts: List[BTCAddress]) -> Dict[BTCAddress, Tuple[bool, FVal]]:
98     """
99     Takes a list of addresses and returns a mapping of which addresses have had transactions
100     and also their current balance
101 
102     May raise:
103     - RemoteError if any of the queried websites fail to be queried
104     """
105     try:
106         if _have_bc1_accounts(accounts):
107             source = 'blockstream'
108             have_transactions = _check_blockstream_for_transactions(accounts)
109         else:
110             source = 'blockchain.info'
111             have_transactions = _check_blockchaininfo_for_transactions(accounts)
112     except (
113             requests.exceptions.RequestException,
114             UnableToDecryptRemoteData,
115             requests.exceptions.Timeout,
116     ) as e:
117         raise RemoteError(f'bitcoin external API request for transactions failed due to {str(e)}') from e  # noqa: E501
118     except KeyError as e:
119         raise RemoteError(
120             f'Malformed response when querying bitcoin blockchain via {source}.'
121             f'Did not find key {str(e)}',
122         ) from e
123 
124     return have_transactions
125
```
--- END FILES ---

Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.

Here is an example:

```diff
diff --git a/examples/server_async.py b/examples/server_async.py
--- a/examples/server_async.py
+++ b/examples/server_async.py
@@ -313,4 +313,4 @@
 
 
 if __name__ == "__main__":
-    asyncio.run(run_async_server("."), debug=True)
+    asyncio.run(run_async_server(), debug=True)
diff --git a/examples/server_sync.py b/examples/server_sync.py
--- a/examples/server_sync.py
+++ b/examples/server_sync.py
@@ -313,5 +313,5 @@
 
 
 if __name__ == "__main__":
-    server = run_sync_server(".")
+    server = run_sync_server()
     server.shutdown()

```

diff --git a/rotkehlchen/chain/bitcoin/__init__.py b/rotkehlchen/chain/bitcoin/__init__.py
--- a/rotkehlchen/chain/bitcoin/__init__.py
+++ b/rotkehlchen/chain/bitcoin/__init__.py
@@ -33,16 +33,20 @@
                 balance = int(stats['funded_txo_sum']) - int(stats['spent_txo_sum'])
                 balances[account] = satoshis_to_btc(balance)
         else:
-            params = '|'.join(accounts)
-            btc_resp = request_get_dict(
-                url=f'https://blockchain.info/multiaddr?active={params}',
-                handle_429=True,
-                # If we get a 429 then their docs suggest 10 seconds
-                # https://blockchain.info/q
-                backoff_in_seconds=10,
-            )
-            for entry in btc_resp['addresses']:
-                balances[entry['address']] = satoshis_to_btc(FVal(entry['final_balance']))
+            # split the list of accounts into sublists of 80 addresses per list to overcome:
+            # https://github.com/rotki/rotki/issues/3037
+            accounts_chunks = [accounts[x:x + 80] for x in range(0, len(accounts), 80)]
+            for accounts_chunk in accounts_chunks:
+                params = '|'.join(accounts_chunk)
+                btc_resp = request_get_dict(
+                    url=f'https://blockchain.info/multiaddr?active={params}',
+                    handle_429=True,
+                    # If we get a 429 then their docs suggest 10 seconds
+                    # https://blockchain.info/q
+                    backoff_in_seconds=10,
+                )
+                for entry in btc_resp['addresses']:
+                    balances[entry['address']] = satoshis_to_btc(FVal(entry['final_balance']))
     except (
             requests.exceptions.RequestException,
             UnableToDecryptRemoteData,

{"golden_diff": "diff --git a/rotkehlchen/chain/bitcoin/__init__.py b/rotkehlchen/chain/bitcoin/__init__.py\n--- a/rotkehlchen/chain/bitcoin/__init__.py\n+++ b/rotkehlchen/chain/bitcoin/__init__.py\n@@ -33,16 +33,20 @@\n                 balance = int(stats['funded_txo_sum']) - int(stats['spent_txo_sum'])\n                 balances[account] = satoshis_to_btc(balance)\n         else:\n-            params = '|'.join(accounts)\n-            btc_resp = request_get_dict(\n-                url=f'https://blockchain.info/multiaddr?active={params}',\n-                handle_429=True,\n-                # If we get a 429 then their docs suggest 10 seconds\n-                # https://blockchain.info/q\n-                backoff_in_seconds=10,\n-            )\n-            for entry in btc_resp['addresses']:\n-                balances[entry['address']] = satoshis_to_btc(FVal(entry['final_balance']))\n+            # split the list of accounts into sublists of 80 addresses per list to overcome:\n+            # https://github.com/rotki/rotki/issues/3037\n+            accounts_chunks = [accounts[x:x + 80] for x in range(0, len(accounts), 80)]\n+            for accounts_chunk in accounts_chunks:\n+                params = '|'.join(accounts_chunk)\n+                btc_resp = request_get_dict(\n+                    url=f'https://blockchain.info/multiaddr?active={params}',\n+                    handle_429=True,\n+                    # If we get a 429 then their docs suggest 10 seconds\n+                    # https://blockchain.info/q\n+                    backoff_in_seconds=10,\n+                )\n+                for entry in btc_resp['addresses']:\n+                    balances[entry['address']] = satoshis_to_btc(FVal(entry['final_balance']))\n     except (\n             requests.exceptions.RequestException,\n             UnableToDecryptRemoteData,\n", "issue": "Bitcoin legacy xpub with too many used address may fail to query balances after restart\n## Problem Definition\r\n\r\nIf a user adds a legacy xpub that generates too many used addresses rotki will properly add the xpub and all its addresses. But then after a restart it will fail to query all balances again.\r\n\r\nError is:\r\n\r\n```\r\nError at querying blockchain balances: bitcoin external API request for balances failed due to https://blockchain.info/multiaddr?active=XXXXXX\r\n```\r\n\r\nThe failure is due to attempting to query all addresses from blockchain.info using the multiaddr endpoint which seems to have a non-documented limit.\r\n\r\nblockchain.info errors with a 502 if too many bitcoin addresses are sent.\r\n\r\n## Task\r\n\r\nFix it by experimenting and figuring out a safe limit.\r\nThen apply that limit where we query for multiple legacy bitcoin addresses.\n", "before_files": [{"content": "from typing import Dict, List, Tuple\n\nimport requests\n\nfrom rotkehlchen.errors import RemoteError, UnableToDecryptRemoteData\nfrom rotkehlchen.fval import FVal\nfrom rotkehlchen.typing import BTCAddress\nfrom rotkehlchen.utils.misc import satoshis_to_btc\nfrom rotkehlchen.utils.network import request_get_dict\n\n\ndef _have_bc1_accounts(accounts: List[BTCAddress]) -> bool:\n    return any(account.lower()[0:3] == 'bc1' for account in accounts)\n\n\ndef get_bitcoin_addresses_balances(accounts: List[BTCAddress]) -> Dict[BTCAddress, FVal]:\n    \"\"\"Queries blockchain.info or blockstream for the balances of accounts\n\n    May raise:\n    - RemotError if there is a problem querying blockchain.info or blockstream\n    \"\"\"\n    source = 'blockchain.info'\n    balances: Dict[BTCAddress, FVal] = {}\n    try:\n        if _have_bc1_accounts(accounts):\n            # if 1 account is bech32 we have to query blockstream. blockchaininfo won't work\n            source = 'blockstream'\n            balances = {}\n            for account in accounts:\n                url = f'https://blockstream.info/api/address/{account}'\n                response_data = request_get_dict(url=url, handle_429=True, backoff_in_seconds=4)\n                stats = response_data['chain_stats']\n                balance = int(stats['funded_txo_sum']) - int(stats['spent_txo_sum'])\n                balances[account] = satoshis_to_btc(balance)\n        else:\n            params = '|'.join(accounts)\n            btc_resp = request_get_dict(\n                url=f'https://blockchain.info/multiaddr?active={params}',\n                handle_429=True,\n                # If we get a 429 then their docs suggest 10 seconds\n                # https://blockchain.info/q\n                backoff_in_seconds=10,\n            )\n            for entry in btc_resp['addresses']:\n                balances[entry['address']] = satoshis_to_btc(FVal(entry['final_balance']))\n    except (\n            requests.exceptions.RequestException,\n            UnableToDecryptRemoteData,\n            requests.exceptions.Timeout,\n    ) as e:\n        raise RemoteError(f'bitcoin external API request for balances failed due to {str(e)}') from e  # noqa: E501\n    except KeyError as e:\n        raise RemoteError(\n            f'Malformed response when querying bitcoin blockchain via {source}.'\n            f'Did not find key {e}',\n        ) from e\n\n    return balances\n\n\ndef _check_blockstream_for_transactions(\n        accounts: List[BTCAddress],\n) -> Dict[BTCAddress, Tuple[bool, FVal]]:\n    \"\"\"May raise connection errors or KeyError\"\"\"\n    have_transactions = {}\n    for account in accounts:\n        url = f'https://blockstream.info/api/address/{account}'\n        response_data = request_get_dict(url=url, handle_429=True, backoff_in_seconds=4)\n        stats = response_data['chain_stats']\n        balance = satoshis_to_btc(int(stats['funded_txo_sum']) - int(stats['spent_txo_sum']))\n        have_txs = stats['tx_count'] != 0\n        have_transactions[account] = (have_txs, balance)\n\n    return have_transactions\n\n\ndef _check_blockchaininfo_for_transactions(\n        accounts: List[BTCAddress],\n) -> Dict[BTCAddress, Tuple[bool, FVal]]:\n    \"\"\"May raise RemotError or KeyError\"\"\"\n    have_transactions = {}\n    params = '|'.join(accounts)\n    btc_resp = request_get_dict(\n        url=f'https://blockchain.info/multiaddr?active={params}',\n        handle_429=True,\n        # If we get a 429 then their docs suggest 10 seconds\n        # https://blockchain.infoq/\n        backoff_in_seconds=15,\n    )\n    for entry in btc_resp['addresses']:\n        balance = satoshis_to_btc(entry['final_balance'])\n        have_transactions[entry['address']] = (entry['n_tx'] != 0, balance)\n\n    return have_transactions\n\n\ndef have_bitcoin_transactions(accounts: List[BTCAddress]) -> Dict[BTCAddress, Tuple[bool, FVal]]:\n    \"\"\"\n    Takes a list of addresses and returns a mapping of which addresses have had transactions\n    and also their current balance\n\n    May raise:\n    - RemoteError if any of the queried websites fail to be queried\n    \"\"\"\n    try:\n        if _have_bc1_accounts(accounts):\n            source = 'blockstream'\n            have_transactions = _check_blockstream_for_transactions(accounts)\n        else:\n            source = 'blockchain.info'\n            have_transactions = _check_blockchaininfo_for_transactions(accounts)\n    except (\n            requests.exceptions.RequestException,\n            UnableToDecryptRemoteData,\n            requests.exceptions.Timeout,\n    ) as e:\n        raise RemoteError(f'bitcoin external API request for transactions failed due to {str(e)}') from e  # noqa: E501\n    except KeyError as e:\n        raise RemoteError(\n            f'Malformed response when querying bitcoin blockchain via {source}.'\n            f'Did not find key {str(e)}',\n        ) from e\n\n    return have_transactions\n", "path": "rotkehlchen/chain/bitcoin/__init__.py"}], "after_files": [{"content": "from typing import Dict, List, Tuple\n\nimport requests\n\nfrom rotkehlchen.errors import RemoteError, UnableToDecryptRemoteData\nfrom rotkehlchen.fval import FVal\nfrom rotkehlchen.typing import BTCAddress\nfrom rotkehlchen.utils.misc import satoshis_to_btc\nfrom rotkehlchen.utils.network import request_get_dict\n\n\ndef _have_bc1_accounts(accounts: List[BTCAddress]) -> bool:\n    return any(account.lower()[0:3] == 'bc1' for account in accounts)\n\n\ndef get_bitcoin_addresses_balances(accounts: List[BTCAddress]) -> Dict[BTCAddress, FVal]:\n    \"\"\"Queries blockchain.info or blockstream for the balances of accounts\n\n    May raise:\n    - RemotError if there is a problem querying blockchain.info or blockstream\n    \"\"\"\n    source = 'blockchain.info'\n    balances: Dict[BTCAddress, FVal] = {}\n    try:\n        if _have_bc1_accounts(accounts):\n            # if 1 account is bech32 we have to query blockstream. blockchaininfo won't work\n            source = 'blockstream'\n            balances = {}\n            for account in accounts:\n                url = f'https://blockstream.info/api/address/{account}'\n                response_data = request_get_dict(url=url, handle_429=True, backoff_in_seconds=4)\n                stats = response_data['chain_stats']\n                balance = int(stats['funded_txo_sum']) - int(stats['spent_txo_sum'])\n                balances[account] = satoshis_to_btc(balance)\n        else:\n            # split the list of accounts into sublists of 80 addresses per list to overcome:\n            # https://github.com/rotki/rotki/issues/3037\n            accounts_chunks = [accounts[x:x + 80] for x in range(0, len(accounts), 80)]\n            for accounts_chunk in accounts_chunks:\n                params = '|'.join(accounts_chunk)\n                btc_resp = request_get_dict(\n                    url=f'https://blockchain.info/multiaddr?active={params}',\n                    handle_429=True,\n                    # If we get a 429 then their docs suggest 10 seconds\n                    # https://blockchain.info/q\n                    backoff_in_seconds=10,\n                )\n                for entry in btc_resp['addresses']:\n                    balances[entry['address']] = satoshis_to_btc(FVal(entry['final_balance']))\n    except (\n            requests.exceptions.RequestException,\n            UnableToDecryptRemoteData,\n            requests.exceptions.Timeout,\n    ) as e:\n        raise RemoteError(f'bitcoin external API request for balances failed due to {str(e)}') from e  # noqa: E501\n    except KeyError as e:\n        raise RemoteError(\n            f'Malformed response when querying bitcoin blockchain via {source}.'\n            f'Did not find key {e}',\n        ) from e\n\n    return balances\n\n\ndef _check_blockstream_for_transactions(\n        accounts: List[BTCAddress],\n) -> Dict[BTCAddress, Tuple[bool, FVal]]:\n    \"\"\"May raise connection errors or KeyError\"\"\"\n    have_transactions = {}\n    for account in accounts:\n        url = f'https://blockstream.info/api/address/{account}'\n        response_data = request_get_dict(url=url, handle_429=True, backoff_in_seconds=4)\n        stats = response_data['chain_stats']\n        balance = satoshis_to_btc(int(stats['funded_txo_sum']) - int(stats['spent_txo_sum']))\n        have_txs = stats['tx_count'] != 0\n        have_transactions[account] = (have_txs, balance)\n\n    return have_transactions\n\n\ndef _check_blockchaininfo_for_transactions(\n        accounts: List[BTCAddress],\n) -> Dict[BTCAddress, Tuple[bool, FVal]]:\n    \"\"\"May raise RemotError or KeyError\"\"\"\n    have_transactions = {}\n    params = '|'.join(accounts)\n    btc_resp = request_get_dict(\n        url=f'https://blockchain.info/multiaddr?active={params}',\n        handle_429=True,\n        # If we get a 429 then their docs suggest 10 seconds\n        # https://blockchain.infoq/\n        backoff_in_seconds=15,\n    )\n    for entry in btc_resp['addresses']:\n        balance = satoshis_to_btc(entry['final_balance'])\n        have_transactions[entry['address']] = (entry['n_tx'] != 0, balance)\n\n    return have_transactions\n\n\ndef have_bitcoin_transactions(accounts: List[BTCAddress]) -> Dict[BTCAddress, Tuple[bool, FVal]]:\n    \"\"\"\n    Takes a list of addresses and returns a mapping of which addresses have had transactions\n    and also their current balance\n\n    May raise:\n    - RemoteError if any of the queried websites fail to be queried\n    \"\"\"\n    try:\n        if _have_bc1_accounts(accounts):\n            source = 'blockstream'\n            have_transactions = _check_blockstream_for_transactions(accounts)\n        else:\n            source = 'blockchain.info'\n            have_transactions = _check_blockchaininfo_for_transactions(accounts)\n    except (\n            requests.exceptions.RequestException,\n            UnableToDecryptRemoteData,\n            requests.exceptions.Timeout,\n    ) as e:\n        raise RemoteError(f'bitcoin external API request for transactions failed due to {str(e)}') from e  # noqa: E501\n    except KeyError as e:\n        raise RemoteError(\n            f'Malformed response when querying bitcoin blockchain via {source}.'\n            f'Did not find key {str(e)}',\n        ) from e\n\n    return have_transactions\n", "path": "rotkehlchen/chain/bitcoin/__init__.py"}]}