Gets entries of `RDFProtoStruct` in a well-defined order.

  Args:
    data: A raw data dictionary of `RDFProtoStruct`.

  Yields:
    Entries of the structured in a well-defined order.

def _GetOrderedEntries(data):
  """Gets entries of `RDFProtoStruct` in a well-defined order.

  Args:
    data: A raw data dictionary of `RDFProtoStruct`.

  Yields:
    Entries of the structured in a well-defined order.
  """

  # The raw data dictionary has two kinds of keys: strings (which correspond to
  # field name) or integers (if the name is unknown). In Python 3 it is not
  # possible to compare integers and strings to each other, so we first tag each
  # with either a 0 or 1 (so named fields are going to be serialized first) and
  # let the lexicographical ordering of the tuples take care of the rest.
  def Tag(field):
    """Tags field name with a number to make comparison possible."""

    # TODO: We use `string_types` here because in Python 2
    # attribute names (which are passed e.g. through keyword arguments) are
    # represented as `bytes` whereas in Python 3 it is `unicode`. This should
    # be replaced with `str` once support for Python 2 is dropped.
    if isinstance(field, string_types):
      return 0, field
    if isinstance(field, int):
      return 1, field

    message = "Unexpected field '{}' of type '{}'".format(field, type(field))
    raise TypeError(message)

  for field in sorted(iterkeys(data), key=Tag):
    yield data[field]