Merge branch 'download_analytics_v2'
This commit is contained in:
commit
bcf52c3f24
5 changed files with 52 additions and 14 deletions
|
@ -18,6 +18,7 @@ HEARTBEAT = 'Heartbeat'
|
|||
CLAIM_ACTION = 'Claim Action' # publish/create/update/abandon
|
||||
NEW_CHANNEL = 'New Channel'
|
||||
CREDITS_SENT = 'Credits Sent'
|
||||
NEW_DOWNLOAD_STAT = 'Download'
|
||||
|
||||
BLOB_BYTES_UPLOADED = 'Blob Bytes Uploaded'
|
||||
|
||||
|
@ -41,6 +42,32 @@ class Manager:
|
|||
return cls(api)
|
||||
|
||||
# Things We Track
|
||||
def send_new_download_start(self, download_id, name, claim_dict):
|
||||
self._send_new_download_stats("start", download_id, name, claim_dict)
|
||||
|
||||
def send_new_download_success(self, download_id, name, claim_dict):
|
||||
self._send_new_download_stats("success", download_id, name, claim_dict)
|
||||
|
||||
def send_new_download_fail(self, download_id, name, claim_dict, e):
|
||||
self._send_new_download_stats("failure", download_id, name, claim_dict, {
|
||||
'name': type(e).__name__ if hasattr(type(e), "__name__") else str(type(e)),
|
||||
'message': e.message,
|
||||
})
|
||||
|
||||
def _send_new_download_stats(self, action, download_id, name, claim_dict, e=None):
|
||||
self.analytics_api.track({
|
||||
'userId': 'lbry', # required, see https://segment.com/docs/sources/server/http/#track
|
||||
'event': NEW_DOWNLOAD_STAT,
|
||||
'properties': self._event_properties({
|
||||
'download_id': download_id,
|
||||
'name': name,
|
||||
'sd_hash': None if not claim_dict else claim_dict.source_hash,
|
||||
'action': action,
|
||||
'error': e,
|
||||
}),
|
||||
'context': self.context,
|
||||
'timestamp': utils.isonow(),
|
||||
})
|
||||
|
||||
def send_server_startup(self):
|
||||
self.analytics_api.track(self._event(SERVER_STARTUP))
|
||||
|
@ -185,26 +212,18 @@ class Manager:
|
|||
|
||||
@staticmethod
|
||||
def _make_context(platform, wallet):
|
||||
# see https://segment.com/docs/spec/common/#context
|
||||
# they say they'll ignore fields outside the spec, but evidently they don't
|
||||
context = {
|
||||
'app': {
|
||||
'name': 'lbrynet',
|
||||
'version': platform['lbrynet_version'],
|
||||
'python_version': platform['python_version'],
|
||||
'build': platform['build'],
|
||||
'wallet': {
|
||||
'name': wallet,
|
||||
'version': platform['lbrynet_version']
|
||||
},
|
||||
},
|
||||
# TODO: expand os info to give linux/osx specific info
|
||||
'os': {
|
||||
'name': platform['os_system'],
|
||||
'version': platform['os_release']
|
||||
},
|
||||
'library': {
|
||||
'name': 'lbrynet-analytics',
|
||||
'version': '1.0.0'
|
||||
},
|
||||
}
|
||||
if 'desktop' in platform and 'distro' in platform:
|
||||
context['os']['desktop'] = platform['desktop']
|
||||
|
|
|
@ -49,6 +49,20 @@ class InsufficientFundsError(RPCError):
|
|||
code = -310
|
||||
|
||||
|
||||
class CurrencyConversionError(Exception):
|
||||
pass
|
||||
|
||||
|
||||
class FileOpenError(ValueError):
|
||||
# this extends ValueError because it is replacing a ValueError in EncryptedFileDownloader
|
||||
# and I don't know where it might get caught upstream
|
||||
pass
|
||||
|
||||
|
||||
class ResolveError(Exception):
|
||||
pass
|
||||
|
||||
|
||||
class ConnectionClosedBeforeResponseError(Exception):
|
||||
pass
|
||||
|
||||
|
|
|
@ -40,6 +40,7 @@ from lbrynet.core.StreamDescriptor import download_sd_blob
|
|||
from lbrynet.core.Error import InsufficientFundsError, UnknownNameError
|
||||
from lbrynet.core.Error import DownloadDataTimeout, DownloadSDTimeout
|
||||
from lbrynet.core.Error import NullFundsError, NegativeFundsError
|
||||
from lbrynet.core.Error import ResolveError
|
||||
from lbrynet.dht.error import TimeoutError
|
||||
from lbrynet.core.Peer import Peer
|
||||
from lbrynet.core.SinglePeerDownloader import SinglePeerDownloader
|
||||
|
@ -339,12 +340,14 @@ class Daemon(AuthJSONRPCServer):
|
|||
def _download_finished(download_id, name, claim_dict):
|
||||
report = yield self._get_stream_analytics_report(claim_dict)
|
||||
self.analytics_manager.send_download_finished(download_id, name, report, claim_dict)
|
||||
self.analytics_manager.send_new_download_success(download_id, name, claim_dict)
|
||||
|
||||
@defer.inlineCallbacks
|
||||
def _download_failed(error, download_id, name, claim_dict):
|
||||
report = yield self._get_stream_analytics_report(claim_dict)
|
||||
self.analytics_manager.send_download_errored(error, download_id, name, claim_dict,
|
||||
report)
|
||||
self.analytics_manager.send_new_download_fail(download_id, name, claim_dict, error)
|
||||
|
||||
if sd_hash in self.streams:
|
||||
downloader = self.streams[sd_hash]
|
||||
|
@ -353,6 +356,7 @@ class Daemon(AuthJSONRPCServer):
|
|||
else:
|
||||
download_id = utils.random_string()
|
||||
self.analytics_manager.send_download_started(download_id, name, claim_dict)
|
||||
self.analytics_manager.send_new_download_start(download_id, name, claim_dict)
|
||||
self.streams[sd_hash] = GetStream(
|
||||
self.sd_identifier, self.wallet_manager, self.exchange_rate_manager, self.blob_manager,
|
||||
self.dht_node.peer_finder, self.rate_limiter, self.payment_rate_manager, self.storage,
|
||||
|
@ -1851,7 +1855,7 @@ class Daemon(AuthJSONRPCServer):
|
|||
resolved = resolved if 'value' in resolved else resolved.get('claim')
|
||||
|
||||
if not resolved:
|
||||
raise Exception(
|
||||
raise ResolveError(
|
||||
"Failed to resolve stream at lbry://{}".format(uri.replace("lbry://", ""))
|
||||
)
|
||||
|
||||
|
|
|
@ -6,7 +6,7 @@ import treq
|
|||
from twisted.internet import defer
|
||||
from twisted.internet.task import LoopingCall
|
||||
|
||||
from lbrynet.core.Error import InvalidExchangeRateResponse
|
||||
from lbrynet.core.Error import InvalidExchangeRateResponse, CurrencyConversionError
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
|
@ -233,7 +233,7 @@ class ExchangeRateManager:
|
|||
market.rate.currency_pair[0] == from_currency):
|
||||
return self.convert_currency(
|
||||
market.rate.currency_pair[1], to_currency, amount * market.rate.spot)
|
||||
raise Exception(
|
||||
raise CurrencyConversionError(
|
||||
'Unable to convert {} from {} to {}'.format(amount, from_currency, to_currency))
|
||||
|
||||
def fee_dict(self):
|
||||
|
|
|
@ -6,6 +6,7 @@ from binascii import hexlify, unhexlify
|
|||
from lbrynet.core.StreamDescriptor import save_sd_info
|
||||
from lbrynet.cryptstream.client.CryptStreamDownloader import CryptStreamDownloader
|
||||
from lbrynet.core.client.StreamProgressManager import FullStreamProgressManager
|
||||
from lbrynet.core.Error import FileOpenError
|
||||
from lbrynet.lbry_file.client.EncryptedFileMetadataHandler import EncryptedFileMetadataHandler
|
||||
from twisted.internet import defer, threads
|
||||
|
||||
|
@ -153,7 +154,7 @@ class EncryptedFileSaver(EncryptedFileDownloader):
|
|||
self.file_written_to = file_written_to
|
||||
except IOError:
|
||||
log.error(traceback.format_exc())
|
||||
raise ValueError(
|
||||
raise FileOpenError(
|
||||
"Failed to open %s. Make sure you have permission to save files to that"
|
||||
" location." % file_written_to
|
||||
)
|
||||
|
|
Loading…
Reference in a new issue