Browse Source

Improve clarity about current daemon URL

master
Neil Booth 8 years ago
parent
commit
184fc615bd
  1. 3
      server/controller.py
  2. 32
      server/daemon.py

3
server/controller.py

@ -450,6 +450,7 @@ class Controller(util.LoggedClass):
def getinfo(self): def getinfo(self):
'''A one-line summary of server state.''' '''A one-line summary of server state.'''
return { return {
'daemon': self.daemon.logged_url(),
'daemon_height': self.daemon.cached_height(), 'daemon_height': self.daemon.cached_height(),
'db_height': self.bp.db_height, 'db_height': self.bp.db_height,
'closing': len([s for s in self.sessions if s.is_closing()]), 'closing': len([s for s in self.sessions if s.is_closing()]),
@ -599,7 +600,7 @@ class Controller(util.LoggedClass):
self.daemon.set_urls(self.env.coin.daemon_urls(daemon_url)) self.daemon.set_urls(self.env.coin.daemon_urls(daemon_url))
except Exception as e: except Exception as e:
raise RPCError('an error occured: {}'.format(e)) raise RPCError('an error occured: {}'.format(e))
return 'set daemon URL to {}'.format(daemon_url) return 'now using daemon at {}'.format(self.daemon.logged_url())
def rpc_stop(self): def rpc_stop(self):
'''Shut down the server cleanly.''' '''Shut down the server cleanly.'''

32
server/daemon.py

@ -42,10 +42,27 @@ class Daemon(util.LoggedClass):
'''Set the URLS to the given list, and switch to the first one.''' '''Set the URLS to the given list, and switch to the first one.'''
if not urls: if not urls:
raise DaemonError('no daemon URLs provided') raise DaemonError('no daemon URLs provided')
for url in urls:
self.logger.info('daemon at {}'.format(self.logged_url(url)))
self.urls = urls self.urls = urls
self.url_index = 0 self.url_index = 0
for n, url in enumerate(urls):
self.logger.info('daemon #{:d} at {}{}'
.format(n + 1, self.logged_url(url),
'' if n else ' (current)'))
def url(self):
'''Returns the current daemon URL.'''
return self.urls[self.url_index]
def failover(self):
'''Call to fail-over to the next daemon URL.
Returns False if there is only one, otherwise True.
'''
if len(self.urls) > 1:
self.url_index = (self.url_index + 1) % len(self.urls)
self.logger.info('failing over to {}'.format(self.logged_url()))
return True
return False
async def _send(self, payload, processor): async def _send(self, payload, processor):
'''Send a payload to be converted to JSON. '''Send a payload to be converted to JSON.
@ -72,8 +89,7 @@ class Daemon(util.LoggedClass):
while True: while True:
try: try:
async with self.workqueue_semaphore: async with self.workqueue_semaphore:
url = self.urls[self.url_index] async with aiohttp.post(self.url(), data=data) as resp:
async with aiohttp.post(url, data=data) as resp:
# If bitcoind can't find a tx, for some reason # If bitcoind can't find a tx, for some reason
# it returns 500 but fills out the JSON. # it returns 500 but fills out the JSON.
# Should still return 200 IMO. # Should still return 200 IMO.
@ -99,17 +115,15 @@ class Daemon(util.LoggedClass):
except Exception: except Exception:
self.log_error(traceback.format_exc()) self.log_error(traceback.format_exc())
if secs >= max_secs and len(self.urls) > 1: if secs >= max_secs and self.failover():
self.url_index = (self.url_index + 1) % len(self.urls)
logged_url = self.logged_url(self.urls[self.url_index])
self.logger.info('failing over to {}'.format(logged_url))
secs = 1 secs = 1
else: else:
await asyncio.sleep(secs) await asyncio.sleep(secs)
secs = min(max_secs, secs * 2) secs = min(max_secs, secs * 2)
def logged_url(self, url): def logged_url(self, url=None):
'''The host and port part, for logging.''' '''The host and port part, for logging.'''
url = url or self.url()
return url[url.rindex('@') + 1:] return url[url.rindex('@') + 1:]
async def _send_single(self, method, params=None): async def _send_single(self, method, params=None):

Loading…
Cancel
Save