code: def __message_to_schema(self, message_type):
      name = self.__normalized_name(message_type)
      schema = {
          'id': name,
          'type': 'object',
          }
      if message_type.__doc__:
        schema['description'] = message_type.__doc__
      properties = {}
      for field in message_type.all_fields():
        descriptor = {}
        type_info = {}
        if type(field) == messages.MessageField:
          field_type = field.type().__class__
          type_info['$ref'] = self.add_message(field_type)
          if field_type.__doc__:
            descriptor['description'] = field_type.__doc__
        else:
          schema_type = self.__FIELD_TO_SCHEMA_TYPE_MAP.get(
              type(field), self.__DEFAULT_SCHEMA_TYPE)
          if isinstance(schema_type, dict):
            variant_map = schema_type
            variant = getattr(field, 'variant', None)
            if variant in variant_map:
              schema_type = variant_map[variant]
            else:
              schema_type = variant_map[None]
          type_info['type'] = schema_type[0]
          if schema_type[1]:
            type_info['format'] = schema_type[1]
        if type(field) == messages.EnumField:
          sorted_enums = sorted([enum_info for enum_info in field.type],
                                key=lambda enum_info: enum_info.number)
          type_info['enum'] = [enum_info.name for enum_info in sorted_enums]
        if field.required:
          descriptor['required'] = True
        if field.default:
          if type(field) == messages.EnumField:
            descriptor['default'] = str(field.default)
          else:
            descriptor['default'] = field.default
        if field.repeated:
          descriptor['items'] = type_info
          descriptor['type'] = 'array'
        else:
          descriptor.update(type_info)
        properties[field.name] = descriptor
      schema['properties'] = properties
      return schema