honeycomb.py (2499B)
1 #Embedded file name: C:\BuildAgent\work\20d73f1b24eed06e\eve\release\V24.01\packages\beeline\propagation\honeycomb.py 2 import beeline 3 from beeline.propagation import PropagationContext 4 import base64 5 import json 6 from urllib import quote, unquote 7 8 def http_trace_parser_hook(request): 9 trace_header = request.header('X-Honeycomb-Trace') 10 if trace_header: 11 try: 12 trace_id, parent_id, context, dataset = unmarshal_propagation_context_with_dataset(trace_header) 13 return PropagationContext(trace_id, parent_id, context, dataset) 14 except Exception as e: 15 beeline.internal.log('error attempting to extract trace context: %s', beeline.internal.stringify_exception(e)) 16 17 18 def http_trace_propagation_hook(propagation_context): 19 if not propagation_context: 20 return None 21 return {'X-Honeycomb-Trace': marshal_propagation_context(propagation_context)} 22 23 24 def marshal_propagation_context(propagation_context): 25 if not propagation_context: 26 return None 27 version = 1 28 trace_fields = base64.b64encode(json.dumps(propagation_context.trace_fields).encode()).decode() 29 components = ['trace_id={}'.format(propagation_context.trace_id), 'parent_id={}'.format(propagation_context.parent_id), 'context={}'.format(trace_fields)] 30 if propagation_context.dataset: 31 components.insert(0, 'dataset={}'.format(quote(propagation_context.dataset))) 32 trace_header = '{};{}'.format(version, ','.join(components)) 33 return trace_header 34 35 36 def unmarshal_propagation_context(trace_header): 37 trace_id, parent_id, context, _dataset = unmarshal_propagation_context_with_dataset(trace_header) 38 return (trace_id, parent_id, context) 39 40 41 def unmarshal_propagation_context_with_dataset(trace_header): 42 version, data = trace_header.split(';', 1) 43 if version != '1': 44 beeline.internal.log('warning: trace_header version %s is unsupported', version) 45 return (None, None, None, None) 46 kv_pairs = data.split(',') 47 trace_id, parent_id, context, dataset = (None, None, None, None) 48 for pair in kv_pairs: 49 k, v = pair.split('=', 1) 50 if k == 'trace_id': 51 trace_id = v 52 elif k == 'parent_id': 53 parent_id = v 54 elif k == 'context': 55 context = json.loads(base64.b64decode(v.encode()).decode()) 56 elif k == 'dataset': 57 dataset = unquote(v) 58 59 if context is None: 60 context = {} 61 return (trace_id, 62 parent_id, 63 context, 64 dataset)