docs: def build_registered_span(self, span):
          """ Takes a BasicSpan and converts it into a registered JsonSpan """
          data = Data(baggage=span.context.baggage)
  
          kind = 1 # entry
          if span.operation_name in self.exit_spans:
              kind = 2 # exit
          # log is a special case as it is not entry nor exit
          if span.operation_name == "log":
              kind = 3 # intermediate span
  
          logs = self.collect_logs(span)
          if len(logs) > 0:
              if data.custom is None:
                  data.custom = CustomData()
              data.custom.logs = logs
  
          if span.operation_name in self.http_spans:
              data.http = HttpData(host=span.tags.pop("http.host", None),
                                   url=span.tags.pop(ext.HTTP_URL, None),
                                   params=span.tags.pop('http.params', None),
                                   method=span.tags.pop(ext.HTTP_METHOD, None),
                                   status=span.tags.pop(ext.HTTP_STATUS_CODE, None),
                                   path_tpl=span.tags.pop("http.path_tpl", None),
                                   error=span.tags.pop('http.error', None))
  
          if span.operation_name == "rabbitmq":
              data.rabbitmq = RabbitmqData(exchange=span.tags.pop('exchange', None),
                                           queue=span.tags.pop('queue', None),
                                           sort=span.tags.pop('sort', None),
                                           address=span.tags.pop('address', None),
                                           key=span.tags.pop('key', None))
              if data.rabbitmq.sort == 'consume':
                  kind = 1 # entry
  
          if span.operation_name == "redis":
              data.redis = RedisData(connection=span.tags.pop('connection', None),
                                     driver=span.tags.pop('driver', None),
                                     command=span.tags.pop('command', None),
                                     error=span.tags.pop('redis.error', None),
                                     subCommands=span.tags.pop('subCommands', None))
  
          if span.operation_name == "rpc-client" or span.operation_name == "rpc-server":
              data.rpc = RPCData(flavor=span.tags.pop('rpc.flavor', None),
                                 host=span.tags.pop('rpc.host', None),
                                 port=span.tags.pop('rpc.port', None),
                                 call=span.tags.pop('rpc.call', None),
                                 call_type=span.tags.pop('rpc.call_type', None),
                                 params=span.tags.pop('rpc.params', None),
                                 baggage=span.tags.pop('rpc.baggage', None),
                                 error=span.tags.pop('rpc.error', None))
  
          if span.operation_name == "sqlalchemy":
              data.sqlalchemy = SQLAlchemyData(sql=span.tags.pop('sqlalchemy.sql', None),
                                               eng=span.tags.pop('sqlalchemy.eng', None),
                                               url=span.tags.pop('sqlalchemy.url', None),
                                               err=span.tags.pop('sqlalchemy.err', None))
  
          if span.operation_name == "soap":
              data.soap = SoapData(action=span.tags.pop('soap.action', None))
  
          if span.operation_name == "mysql":
              data.mysql = MySQLData(host=span.tags.pop('host', None),
                                     db=span.tags.pop(ext.DATABASE_INSTANCE, None),
                                     user=span.tags.pop(ext.DATABASE_USER, None),
                                     stmt=span.tags.pop(ext.DATABASE_STATEMENT, None))
              if (data.custom is not None) and (data.custom.logs is not None) and len(data.custom.logs):
                  tskey = list(data.custom.logs.keys())[0]
                  data.mysql.error = data.custom.logs[tskey]['message']
  
          if span.operation_name == "log":
              data.log = {}
              # use last special key values
              # TODO - logic might need a tweak here
              for l in span.logs:
                  if "message" in l.key_values:
                      data.log["message"] = l.key_values.pop("message", None)
                  if "parameters" in l.key_values:
                      data.log["parameters"] = l.key_values.pop("parameters", None)
  
          entity_from = {'e': instana.singletons.agent.from_.pid,
                        'h': instana.singletons.agent.from_.agentUuid}
  
          json_span = JsonSpan(n=span.operation_name,
                               k=kind,
                               t=span.context.trace_id,
                               p=span.parent_id,
                               s=span.context.span_id,
                               ts=int(round(span.start_time * 1000)),
                               d=int(round(span.duration * 1000)),
                               f=entity_from,
                               data=data)
  
          if span.stack:
              json_span.stack = span.stack
  
          error = span.tags.pop("error", False)
          ec = span.tags.pop("ec", None)
  
          if error and ec:
              json_span.error = error
              json_span.ec = ec
  
          if len(span.tags) > 0:
              if data.custom is None:
                  data.custom = CustomData()
              data.custom.tags = span.tags
  
          return json_span